【问题标题】:Excel VBA Place values in multidimensional arrayExcel VBA将值放在多维数组中
【发布时间】:2016-06-13 03:01:04
【问题描述】:

我有一个这种结构的工作表(实际工作表中有更多列,但不多):

ColumnAValue1   ColumnBValue1   23
ColumnAValue1   ColumnBValue1   45
ColumnAValue1   ColumnBValue1   2.4
ColumnAValue1   ColumnBValue2   1
ColumnAValue1   ColumnBValue2   3
ColumnAValue2   ColumnBValue1   5
ColumnAValue2   ColumnBValue1   6
ColumnAValue2   ColumnBValue1   7
ColumnAValue2   ColumnBValue2   355
ColumnAValue2   ColumnBValue2   221

我想获得每个组合的平均值、项目编号和偏差(例如,ColumnAValue1 ColumnBValue1 将是 23、45 和 2.4 的平均值)。所以我认为在数组、集合或字典中获取所有数据(我不知道是否存在诸如“多维字典”之类的东西)会很有用。我想以一个类似于以下结构的多维数组(或集合)结束:

AllData(
        ColumnAValue1(
                    ColumnBValue1(23,45,2.4)
                    ColumnBValue2(1,3)
                    )
        ColumnAValue2(
                    ColumnBValue1(5,6,7)
                    ColumnBValue2(355,221)
                    )
        )

我知道如何从列中获取唯一值。

我的两个问题: 1) 如何使用正确的键(第一个维度为 ColumnAValue1 和 ColumnAValue2,第二个维度为 ColumnBValue1 和 ColumnBValue2)以及 2) 创建一个数组(或集合) > 然后循环遍历我的所有数据并将值“放置”在相应的子数组中。

【问题讨论】:

    标签: excel multidimensional-array vba


    【解决方案1】:
    Sub Test()
      Dim c As Collection
      Set c = New Collection
    
      Dim ws As Worksheet
      Set ws = ThisWorkbook.Worksheets("Sheet1")
    
      Dim i As Long
      For i = 1 To 10 'Assume 10 rows
        AddToLayeredCollection c, ws.Cells(i, 3).value, ws.Cells(i, 1).value, ws.Cells(i, 2).value 'Assume two columns for keys, A and B
      Next
    
      'Add 'c' to the watch window and examine it
    End Sub
    
    Public Sub AddToLayeredCollection(ByVal root_collection As Collection, ByVal value As Variant, ParamArray keys() As Variant)
      Dim i As Long
      Dim target_collection As Collection
    
      Set target_collection = root_collection
      For i = LBound(keys) To UBound(keys)
        Set target_collection = ResolveToCollection(target_collection, keys(i))
      Next
    
      target_collection.Add value
    End Sub
    
    Private Function ResolveToCollection(ByVal parent_collection As Collection, ByVal key As Variant) As Collection
      On Error Resume Next
      Set ResolveToCollection = parent_collection(key)(1)
      On Error GoTo 0
    
      If ResolveToCollection Is Nothing Then
        Set ResolveToCollection = New Collection
        parent_collection.Add Array(key, ResolveToCollection), key
      End If
    End Function
    

    我使用Array() 的唯一原因是能够retrieve keys from the collection。您可以use Dictionary instead 并删除Array()

    【讨论】:

    • 哇!它可以满足我的要求!仍在尝试获取代码的逻辑,但是在监视窗口中检查 c (如您所说)看起来很棒。我很惊讶,也非常感激。在放弃并在这里询问之前,我已经被困了四天......
    • @GSerg 在字典和数组之间,在这种情况下,哪种方法更受欢迎。寻求您作为爱好者的意见,以从您的宝贵经验和专业知识中学习。
    • @skkakkar 这是个人喜好问题。我倾向于使用Collection,因为它是一个内部类,而且我知道它将可用。使用字典会在代码中更简洁,但这是对外部库的依赖 - 再说一次,该库可能会出现在您运行 Excel 的任何系统上 - 然后再次阅读comments below this answer
    • @GSerg 感谢您对这个问题的启发。
    • @GSerg 如果您不介意,还有一个:如何计算子集合中的元素? CStr(c.Count) 在示例中是两个,我可以访问像 c(1)(1)(1)(1)(1) 这样的元素(它将是 23)。但是我怎么知道第一组有 3 个元素(23,45,2.4),第二组有 2 个(1,3)?
    猜你喜欢
    • 1970-01-01
    • 2014-11-15
    • 1970-01-01
    • 1970-01-01
    • 2017-12-25
    • 1970-01-01
    • 2021-08-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多