Интересует так же что из всего написанного считать дублями, а что нет и почему именно так. Но предвидя что-то вроде "все, что содержит фигурка, God of war и Шуруповерт" отвечу: очень плохая идея искать такие дубли, т.к. Excel не умеет различать настолько правильно все возможные варианты и даже если написать код, который будет делать что-то подобное, то процент ошибок будет непозволительно велик.
Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
До этого работал с надстройкой Fuzzy Lookup, но она сравнивает 2 списка и находит более менее похожие значения. Там тоже бывает много ошибок что в конечном итоге приходится разбирать руками. --- Меня не интересует прям 100% точный результат. Подойдет и более приближенные совпадения. Если макрос сможет из 5000 товаров найти 500 близко похожие значения из которых всего 100 будут реально дублями, уже есть хорошо)
Вы попробуйте на бумаге описать, почему первая пара это дубли, а вторая нет. И полюбуйтесь простыней, которую нужно засунуть в код. А это всего две пары.
DartoArem, вчера Jack Famous создал ТЕМУ. У него там много полезных ссылок на подобные решения, может пригодится. Ну если там ничего не найдете подходящего, то вот написал на скорую руку. Только есть недостаток, долго работает. И ещё если подойдет, то перед началом, желательно удалить знаки пунктуации, скобки, двойные пробелы и т.п. Хотя там это все делается, но с заменой на пробел, поэтому для нормального разбития желательно проконтролировать.
Доброе время суток. Вариант. Сам не понял как работает. Но по представленному примеру где-то что-то группирует Хотя, конечно, лучше через декартово произведение с фильтром идти, но будет, мягко говоря, медленно.
artyrH, PBI, он бесплатный. Или подписывайтесь на О365 с января 2020 по идее во всех планах обновлений он появится, как и многие другие вкусности в PQ.
Андрей VG, где-нибудь есть внятный разбор механики работы кастомного сравнивателя для Table.Group? У Имке Фельдман видел только пример применения, но без погружения в пучины. Очень хочется разобраться. Тем более что там ведь сравнивалка должна отличаться для Local и Global вариантов или от этого параметра только зависит количество переборов до останова набора строк в отдельную группу?
Андрей VG, т.е. я правильно понимаю, что при Локльной группировке алгоритм за один проход последовательных сравнений строк формирует результат, а при глобальной он сначала для первой строки перебирает все остальные, выделяет это в отдельную группу, потом для оставшихся строк начинает перебор по тому же алгоритму. И именно на этом основывается лайфхак от Имке, что сортировка + локальная группировка на большом массиве в разы производительнее чем просто глобальная группировка на неупорядоченном массиве, при этом результат идентичный. Сам пробовал получается сильно шустрее.
PooHkrd написал: И именно на этом основывается лайфхак от Имке, что сортировка + локальная группировка на большом массиве в разы производительнее чем просто глобальная
Как-то не сходится. Таблица: поле f1 создано формулой =СЛУЧМЕЖДУ(1;999999), поле v - формулой =СЛЧИС(). Всего более миллиона строк. Уникальных значений по f1 при группировке по f1 и сумме по v около 650000 строк. Код обычной группировки
Код
let
Source = Excel.CurrentWorkbook(){[Name="Таблица1"]}[Content],
#"Changed Type" = Table.TransformColumnTypes(Source,{{"f1", Int64.Type}, {"v", type number}}),
#"Grouped Rows" = Table.Group(#"Changed Type", {"f1"}, {{"sum", each List.Sum([v]), type number}})
in
#"Grouped Rows"
выполнился за 12 секунд
Код с лайфхак
Код
let
Source = Excel.CurrentWorkbook(){[Name="Таблица1"]}[Content],
#"Changed Type" = Table.TransformColumnTypes(Source,{{"f1", Int64.Type}, {"v", type number}}),
sorted = Table.Sort(#"Changed Type", "f1"),
#"Grouped Rows" = Table.Group(sorted, {"f1"}, {{"sum", each List.Sum([v]), type number}}, GroupKind.Local)
in
#"Grouped Rows"
за 23 секунды. Тогда вопрос - в каком контексте лайфак будет быстрее?
Андрей VG, У меня был вариант когда на массиве 10кк строк группировался по 5 полям, в общей сложности там было порядка 100к уникальных групп. Вариант с обычной группировкой уходил в задумчивость и в себя не возвращался. Вариант от Имке отрабатывает за 10-15 минут в зависимости от загруженности сервака.
PooHkrd написал: Вариант от Имке отрабатывает за 10-15 минут
Да, что-то намутили мелкомягкие. На девяти столбцах группировки f1-f9, созданных формулой =ТЕКСТ(СЛУЧМЕЖДУ(1;10);"0000000000000000"), и v - формулой =СЛЧИС(), получилось для миллиона строк входа и миллиона строк вывода по алгоритму лайфхака
Код
let
groupNames = List.Transform({"1".."9"}, each "f" & _),
groupSort = List.Transform(groupNames, each {_, Order.Ascending}),
Source = Excel.CurrentWorkbook(){[Name="Таблица1"]}[Content],
#"Changed Type" = Table.TransformColumnTypes(Source,{{"f1", type text}, {"f2", type text}, {"f3", type text}, {"f4", type text}, {"f5", type text}, {"f6", type text}, {"f7", type text}, {"f8", type text}, {"f9", type text}, {"v", type number}}),
sorted = Table.Sort(#"Changed Type", groupSort),
result = Table.Group(sorted, groupNames, {{"sum", each List.Sum([v]), Number.Type}}, GroupKind.Local)
in
result
время выполнения 437 секунд. Но, можно и ускорить. Такой подход
Код
let
groupNames = List.Transform({"1".."9"}, each "f" & _),
Source = Excel.CurrentWorkbook(){[Name="Таблица1"]}[Content],
#"Changed Type" = Table.TransformColumnTypes(Source,{{"f1", type text}, {"f2", type text}, {"f3", type text}, {"f4", type text}, {"f5", type text}, {"f6", type text}, {"f7", type text}, {"f8", type text}, {"f9", type text}, {"v", type number}}),
groupTypes = List.Transform(groupNames, each {_, Type.TableColumn(Value.Type(#"Changed Type"), _)}),
addGroupList = Table.AddColumn(#"Changed Type", "group", each Record.FieldValues(Record.SelectFields(_, groupNames))),
result = Table.Group(addGroupList, {"group"}, {{"sum", each List.Sum([v]), Number.Type}}),
listToTable = Table.TransformColumns(result, {"group", each Table.FromRows({_}, groupNames)}),
expanded = Table.ExpandTableColumn(listToTable, "group", groupNames),
return = Table.TransformColumnTypes(expanded, groupTypes)
in
return
Андрей VG, спасибо, интересный вариант. А почему именно список? В запись собирать и по ней группироваться пробовали? На днях по гоняю его на своем массиве - отпишусь. Ранее я сцеплял в текст поля и группировался по тексту, потом расцеплял. Такой вариант отрабатывал примерно за те же 10-15 минут. Но тут надо понимать что 10-15 минут это не чисто группировка, а все преобразования в запросе включая чтение с 800 Гб xlsx файлов. Кстати, перевыгрузка массива в txt не дала каких-то колоссальных результатов, но на 1 - 1.5 минуты стало работать быстрее. Я ждал от этого большего. С другой стороны, если на xlsx нет-нет да и подвиснет (хоть и редко, но приятного мало), с текстовыми выгрузками не было ни одного сбоя - работает как часы.