2014-07-09 140 views
0

我有一组以下列格式的数据,虽然非常简化:比较两个数据集 - 慢速

  • DealerName,AccountCode,价值
  • Dealer1,A-1,5
  • Dealer2,A -1,10
  • Dealer1,A-2,20
  • Dealer2,A-2,15
  • Dealer3,A-3,5

我想实现一个最终的结果,让我通过AccountCode总结的数据,因此,在上述数据的情况下执行以下操作:

  • AccountCode,价值
  • A-1,15
  • A-2,35
  • A-3,5

我已经通过创建的命名OutputData不同帐户代码的阵列,然后通过比较所述数据去完成这个帐户代码相同的场中SelectedDealerData并将其添加到现有的值:

For i = 0 To UBound(SelectedDealerData) 
    For j = 0 To UBound(OutputData) 
     If SelectedDealerData(i).AccountNumber = OutputData(j).AccountNumber And SelectedDealerData(i).Year = OutputData(j).Year Then 
      OutputData(j).Units = OutputData(j).Units + SelectedDealerData(i).Units 
      Exit For 
     End If 
    Next j 
Next i 

周围有10,00经销商和每个600-1000帐户代码,所以这意味着很多不必要的循环的。

有人能指出我的方向更有效的解决方案吗?我在想某种字典比较,但我不确定如何实现它。

+0

这是在Excel/Access中吗?如果它在Excel中,为什么不使用像'= SUMIFS'这样的工作表函数 – Gareth

回答

1

Microsoft脚本运行时添加引用的解释:

Dim aggregated As Dictionary 
    Set aggregated = New Dictionary 

    For i = 0 To UBound(SelectedDealerData) 
     With SelectedDealerData(i) 
      If aggregated.Exists(.AccountCode) Then 
       aggregated(.AccountCode) = aggregated(.AccountCode) + .Value 
      Else 
       aggregated(.AccountCode) = .Value 
      End If 
     End With 
    Next 

    For Each Key In aggregated.Keys 
     Debug.? Key, aggregated(Key) 
    Next 
0

的代码是缓慢的,因为有1000万间的比较和赋值操作在这里(10,000×1000)正在进行。

此外,通过集合循环并不是非常有效,但由于设计已经按照原样设置和维护,因此无法做到这一点。

有两种方法可以提高效率(您可以立即计算代码并在执行这些步骤后查看节省的成本)。

  1. 有两个条件检查进行And。即使第一个虚假(不短路),VBA也会进行评估。因此,嵌套if then条件,以便如果第一个条件失败,您不会继续检查第二个条件。此外,保持条件更可能在外部if语句失败(所以它快速失败并移动到下一个元素)。最好的情况是,你在这里会遇到一个小的速度颠簸,最糟糕的是,你并没有更糟。

  2. 这里发生了太多的比较。如果您可以对您的集合进行排序或创建一个索引来维护它们的排序顺序(如果您喜欢,可以在电子表格中保存该索引数组),但是您可以根据以下伪代码查看循环。排序应该基于名为Account_Number_Year的复合字段完成(只是连接它们)

  3. 您可以在Alex K.建议的字典结构中使用此连接字段。因此,您可以在第二个字典中查找此联合字段,然后如果需要做操作。

代码,以尝试在VBA充分实现它:

'Assuming both arrays are sorted 
For i = 0 to Ni 
    MatchingIndex = _ 
     BinarySearchForAccNumberYear(SelectedUserData(i).AccountNumberYear) 
Next i 

你可以看一下二进制搜索here

这会将您的时间复杂度从O(n^2)降低到O(n log n),并且您的代码将以更快的速度运行一个数量级。