Hallo Hans,
Am 11.01.2017 um 16:39 schrieb Hans.Alborg:
> Ulrich Möller schrieb:
>> Hans.Alborg:
>>> ...Dadurch kommen nur neue Strings zur Verarbeitung und dann in die
>>> Sammeltabelle, was Doubles sowieso ausschließt.
>>
>> Geht prima mit einem Dictionary Objekt und einem kleinen Trick:
>>
>> Erzeuge ein Dictionary Objekt und durch das alleinige Ansprechen eines
>> Elements über einen Key wird dieser Key neu angelegt, wenn er bis dahin
>> noch nicht vorhanden war. Das kann man sich zunutze machen.
>
> Das ist ein ganzes Stück über meinem Horizont. Du meinst mit Key
> bestimmt ganz was anderes als SendKeys.
>
>> Beispiel:
>> ...
>> set objDic = CreateObject(("scripting.dictionary")
>>
>> und dann jeweils z.B. mit
>>
>> vntTemp = objDic.Item("Sample_1")
>> vntTemp = objDic.Item("Sample_2")
>> vntTemp = objDic.Item("Sample_1") ' <--- hier wird keine weitere
>> Key angelegt!
>> objDic.item("Sample_3") = MeinWert ' <--- alternativ: Key mit einem
>> Wert anlegen
>>
>> die Keys "Sample_1" , "Sample_2" und "Sample_3" anlegen. Dieses wären
>> die Strings, die du speichern möchtest.
>>
>> avntUniqueKeys = objDic,keys liefert dann ein Variant-Array aller
>> unique Keys, also ein Array mit den Strings
>
> Aha! Also mit "scripting.dictionary" funktioniert ja auch Claus'
> Lösung die ich erst mißverstanden hatte. Auch dort bekomme ich ein
> Array ohne Doubles.
>
> Nachdem ich so ein Array jetzt erzeugen kann beschäftigt mich, wie ich
> neben den Strings stehende Zeiten (Single) zusammenzählen und dem
> Arrayinhalt zuordnen kann.
> Der erste String X wird ins Array aufgenommen, die weiteren "X" nicht.
> Aber die Zeiten aller "X" müssen dann als Summe in der Sammeltabelle
> neben "String X" stehen.
> Mit "String Y" dann dasselbe usw.
>
> Eignet sich ein mehrdimensionales Array dazu?
ich habe mal ein kleines Beispiel gemacht, wie du mit einem Dictionary
Objekt deine Strings und die akkumulierten Zeiten verwalten könntest:
in eine Modul:
Private m_dicUniqueStorage As Scripting.Dictionary
Public Property Get Store() As Scripting.Dictionary
If m_dicUniqueStorage Is Nothing Then
Set m_dicUniqueStorage = CreateObject("Scripting.Dictionary")
End If
Set Store = m_dicUniqueStorage
End Property
Public Sub ClearStorage()
Store.RemoveAll
End Sub
Public Sub AddToSore(ByRef KeyValuePair() As Variant)
Dim vntValue As Variant
If Store.Exists(KeyValuePair(0)) Then
' Akkumulieren
vntValue = Store.Item(KeyValuePair(0))
Store.Item(KeyValuePair(0)) = vntValue + KeyValuePair(1)
Else
' Neuen Eintrag anfügen
Store.Add KeyValuePair(0), KeyValuePair(1)
End If
End Sub
Hier ein Beispielaufruf, mit dem das Dictionary Objekt gefüllt wird,
wobei in diesem Testfall der zu akkumulierende Wert einfach rechts neben
dem String steht.
Public Sub AkkumulateTimeValues(ByVal DataArea As Range)
Dim c As Range
Dim vntKeyValue(1) As Variant
' (0) - StringValue/Key
' (1) - Timevalue in Minutes
ClearStorage
For Each c In DataArea
vntKeyValue(0) = c.Value
vntKeyValue(1) = c.Offset(ColumnOffset:=1).Value
AddToSore vntKeyValue
Next
End Sub
Der Zugriff auf das Dictionary erfolgt dann mit
Store.Keys - gibt ein Array der eindeutigen Strings zurück
Store.Items - gibt ein Array aller akkumulierten Werte
zurück.
Store("TestStringXX") - gibt den akkumulierten Wert für den
Stringtext "TestStringXX" zurück
und mit Clearstore() oder Store.RemoveAll werden alle Einträge gelöscht.
Meine Testroutine war dann einfach:
Private Sub cmdAction_Click()
Dim rngOut As Range
Dim avnt As Variant
AkkumulateTimeValues Me.Range("TestStrings") - benannter Bereich mit
den Stringtexten und Minuten
' Testoutput
avnt = Store.Items
Set rngOut = Me.Range("C2")
Set rngOut = rngOut.Resize(Store.Count, 1)
rngOut.Value = Application.Transpose(avnt)
End Sub
Natürlich könnte man das auch nach Bedarf erweitern. Bei Interesse kann
ich das Projekt auch hochladen.
Grüße
Ulrich