Более быстрый метод, чем VLOOKUP, для сравнения двух наборов данных в Excel с использованием VBA: 1 содержит 180 000 элементов, остальные 250 000 - PullRequest
0 голосов
/ 14 июня 2019

Я автоматизирую построение отчета в Excel, используя VBA. Часть этого процесса я использую vlookup для сравнения списков. На вкладке 1 содержится примерно 180 000 позиций с уникальным идентификатором, vlookup берет этот идентификатор и сравнивает с "владельцами" на вкладке 2 примерно с 250 000 позиций. Время выполнения этой операции составляет примерно 25-30 минут, и мне интересно, есть ли более быстрый путь? Может быть, я должен выполнить это сравнение, используя скрипт за пределами Excel, чтобы сократить время расчета?

Работает нормально, поэтому я не пытался устранить неполадки. У меня есть несколько идей, связанных с выполнением работы вне Excel, в фоновом режиме, но я ищу идеи от более широкой группы.

Вот строка, которую я сейчас использую для поиска, она повторяется 5 раз в коде.

Range("Table").Offset(1).Select
ActiveCell.FormulaR1C1 = "=IFNA(VLOOKUP([@ID],table,2,0),""Unassigned"")"

С каждой итерацией вышеприведенной строки в книге пересчитывается, что занимает 30 минут. Я попытался установить расчет на xlManual, а затем обратно на xlAutomatic, не повезло. Думал, что смогу просто запустить калькуляцию одного листа после написания формул.

Любопытно, если кто-нибудь знает более быстрый способ сделать это. Как я уже говорил, время выполнения этого раздела составляет 30 минут, а общее время выполнения - 35-40 минут.

Ответы [ 2 ]

0 голосов
/ 14 июня 2019

Если вы можете СОРТИРОВАТЬ ваши данные, вы можете построить двойной VLOOKUP с параметром range_lookup, установленным в TRUE.Это заставляет VLOOKUP выполнять бинарный поиск, который в большой БД может работать в 100 раз быстрее:

=IF(VLOOKUP(ID,Table,1,TRUE)=ID,VLOOKUP(ID,Table,2,TRUE),NA())

И если вы используете метод VLOOKUP, вы обязательно должны выключить ScreenUpdating, а также установите Calculation в ручную, когда вы заполняете лист формулами.

В качестве альтернативы может быть быстрее просто прочитать данные в массив или словарь VBA и выполнить весь поиск исоответствие в VBA.Опять же, если вы можете отсортировать свой список, вы можете использовать двоичный поиск, который будет намного быстрее.

0 голосов
/ 14 июня 2019

Может быть попытаться преобразовать результат вашей формулы VLOOKUP в значение после каждой итерации, что-то вроде этого:

Sub foo()
    Dim rngCell As Range

    For Each rngCell In Range("Table").Offset(1)
        rngCell.FormulaR1C1 = "=IFNA(VLOOKUP([@ID],table,2,0),""Unassigned"")"
        rngCell.Value = rngCell.Value
    Next rngCell    
End Sub

Это должно помешать ему пересчитать результаты VLOOKUP.В качестве альтернативы используйте комбинацию INDEX + MATCH или - если ваш набор данных отсортирован - используйте VLOOKUP с режимом совпадения TRUE (приблизительный) вместо FALSE (точный).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...