Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Microsoft Office и VBA программирование > Microsoft Office Excel
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 29.10.2014, 00:08   #11
valerij
Старожил
 
Аватар для valerij
 
Регистрация: 12.05.2007
Сообщений: 2,339
По умолчанию

Цитата:
Сообщение от alex77755 Посмотреть сообщение
Дубли могут быть?
И оставлять как? По порядку в колонке или напротив в колонке А?
Могут и в А, и в В, но если один раз нашёл, в А-А, вторично можно не искать.
Найденное значение, достаточно одного раза.
Не важно, как удобней.

Последний раз редактировалось valerij; 29.10.2014 в 00:13.
valerij вне форума Ответить с цитированием
Старый 29.10.2014, 00:33   #12
alex77755
Форумчанин
 
Аватар для alex77755
 
Регистрация: 14.02.2009
Сообщений: 753
По умолчанию

Ну как-то так.
Твой макрос привёл в читабельный вид.
Но алгоритм = шедевр!
Вложения
Тип файла: rar Кн2.rar (15.7 Кб, 11 просмотров)
помогу решить контрольные VB6, VBA (недорого)
Alex77755@mail.ru
alex77755 вне форума Ответить с цитированием
Старый 29.10.2014, 00:52   #13
valerij
Старожил
 
Аватар для valerij
 
Регистрация: 12.05.2007
Сообщений: 2,339
По умолчанию

Цитата:
Сообщение от alex77755 Посмотреть сообщение
Ну как-то так.
Твой макрос привёл в читабельный вид.
Но алгоритм = шедевр!
Сейчас попробую на полную...

alex77755
Ну поясни мне, че не так я делал?

Проверил, всё ОК, 2 минуты делал.

Та там действительно для меня тёмный лес...
И пояснять не надо.

Спасибо.

(\__/)
(='.'=)
E[:]|||[:]З
(")_(")

Последний раз редактировалось valerij; 29.10.2014 в 01:08.
valerij вне форума Ответить с цитированием
Старый 29.10.2014, 01:05   #14
alex77755
Форумчанин
 
Аватар для alex77755
 
Регистрация: 14.02.2009
Сообщений: 753
По умолчанию

При таких объёмах даже читать построчно нельзя.
А тут в каждой строке два считывания
А строк 531552 да умножить на к-во строк во второй колонке....
Считывание и запись самые медленные операции
Да ещё удаление со сдвигом огромного массива
Только массивы!
Считали одной строкой и выгрузили одной строкой.
Всё остальное в массиве.
Там в коде можно ещё ускорить: не гнать второй цикл до кона строк первого столбца, а выйти из цикла при пустом значении
Код:
    For R = 1 To LR 'идем по второму столбцу
    If M(R, 2) = "" Then Exit For
помогу решить контрольные VB6, VBA (недорого)
Alex77755@mail.ru
alex77755 вне форума Ответить с цитированием
Старый 29.10.2014, 01:32   #15
valerij
Старожил
 
Аватар для valerij
 
Регистрация: 12.05.2007
Сообщений: 2,339
По умолчанию

Цитата:
Сообщение от alex77755 Посмотреть сообщение
При таких объёмах даже читать построчно нельзя.
А тут в каждой строке два считывания
А строк 531552 да умножить на к-во строк во второй колонке....
Считывание и запись самые медленные операции
Да ещё удаление со сдвигом огромного массива
Только массивы!
Считали одной строкой и выгрузили одной строкой.
Всё остальное в массиве.
Там в коде можно ещё ускорить: не гнать второй цикл до кона строк первого столбца, а выйти из цикла при пустом значении
Код:
    For R = 1 To LR 'идем по второму столбцу
    If M(R, 2) = "" Then Exit For
Я подозревал о массивах, даже когда из 531552 оставлял 53, удивился времени работы, как будто и не удалял.
А потом обратил внимание на вертикальную полосу прокрутки, при 53 строк она малюсенькая как и при 531552 и когда удали пустые строки, и прокрутка здоровенная и работал мухой.

Но с массивами не сталкивался, придётся почитать.

Щас код поменяю...

Спасибо за объяснения.
valerij вне форума Ответить с цитированием
Старый 29.10.2014, 01:48   #16
IgorGO
Новичок
СтарожилДжуниор
 
Аватар для IgorGO
 
Регистрация: 05.02.2008
Сообщений: 9,487
По умолчанию

Код:
Sub DelNoFind()
  Dim rgA As Range, r As Long, a()
  a = Cells(1, 2).Resize(WorksheetFunction.CountA(Columns(2)), 1).Value
  Set rgA = Cells(1, 1).Resize(WorksheetFunction.CountA(Columns(2)), 1)
  For r = 1 To UBound(a)
    If WorksheetFunction.CountIf(rgA, a(r, 1)) = 0 Then a(r, 1) = Empty
  Next
  Cells(1, 2).Resize(UBound(a), 1).Value = a
  Columns(2).SpecialCells(xlCellTypeBlanks).Delete shift:=xlUp
End Sub
Валера, пока не вник очень сильно, пробуй может это сработает?
Программисты - это люди, решающие проблемы, о существовании которых Вы не подозревали, методами, которых Вы не понимаете
IgorGO вне форума Ответить с цитированием
Старый 29.10.2014, 05:25   #17
valerij
Старожил
 
Аватар для valerij
 
Регистрация: 12.05.2007
Сообщений: 2,339
По умолчанию

Цитата:
Сообщение от alex77755 Посмотреть сообщение
Там в коде можно ещё ускорить: не гнать второй цикл до кона строк первого столбца, а выйти из цикла при пустом значении
Код:
    For R = 1 To LR 'идем по второму столбцу
    If M(R, 2) = "" Then Exit For
alex77755
Докладаю.
В первом варианте остаётся в В-В из 378 987 строк 179 321 строка.
Во втором варианте, быстрее работает ~ минута, остаётся 281 992 строки.
Кому верить?
Я правильно заменил, вроде по другому и нет?
Код:
For r = 1 To LR 'идем по второму столбцу
    If M(r, 2) = "" Then Exit For
    
    'For r = 1 To LR 'идем по второму столбцу
       'If oD.Exists(M(r, 2)) Then ' если есть в словаре
Цитата:
Сообщение от IgorGO Посмотреть сообщение
Валера, пока не вник очень сильно, пробуй может это сработает?
Игорь, проверил, ждал 6 минут, остановил процесс.
Если надо точное время то завтра, вернее сегодня, пора в люлю.
valerij вне форума Ответить с цитированием
Старый 29.10.2014, 08:31   #18
alex77755
Форумчанин
 
Аватар для alex77755
 
Регистрация: 14.02.2009
Сообщений: 753
По умолчанию

Значит данные во втором столбце идут не по порядку, а где-то есть пустая ячейка. По ней и выход из цикла.
Кстати вчера уже вечером дошло: метки в колонке С не соответствуют.
Не тот индекс я поставил. Сейчас найду файл поправлю. Если метка нужна конечно.
Вот только если нужна и есть дубли, то метить все или только первую, или только последнюю?
помогу решить контрольные VB6, VBA (недорого)
Alex77755@mail.ru
alex77755 вне форума Ответить с цитированием
Старый 29.10.2014, 08:58   #19
alex77755
Форумчанин
 
Аватар для alex77755
 
Регистрация: 14.02.2009
Сообщений: 753
По умолчанию

Что бы не учитывать пустые строки в В, но и не гнать по всему списку добавил строку определения количества записей во второй колонке.
Так же поправил пометки тех кто совпал.
Сейчас помечаются первые из дублей
Цитата:
но если один раз нашёл, в А-А
Вот именно в этом и превосходство словаря: не ищется, а просто проверяется наличие. Причем довольно быстро.
Вот если надо подсчитать количество дублей в А-А, или все дубли пометить, то надо ещё добавить пару строк в код

Код:
Sub QWERT()
Dim oD: Set oD = CreateObject("Scripting.Dictionary")
Dim oE: Set oE = CreateObject("Scripting.Dictionary")
Dim M(), LR, R, D, U(), LR2
With Лист1
    LR = .Cells(.Rows.Count, 1).End(xlUp).Row
    M = .Range("A1:C" & LR) 'грузим в массив
    
    For R = 1 To LR ' берём в словарь столбец А
'       oD(M(R, 1)) = R ' в таком случае метка будет на последнем из дублей
       If Not oD.Exists(M(R, 1)) Then oD(M(R, 1)) = R   ' в таком случае метка будет на первом из дублей
    Next R
'    для расстановки меток по всем дублям надо добавить небольшой блок

    LR2 = .Cells(.Rows.Count, 2).End(xlUp).Row
    For R = 1 To LR2 'идем по второму столбцу
       If oD.Exists(M(R, 2)) Then ' если есть в словаре
            oE(M(R, 2)) = R 'Добавляем в словарь совпавших что бы были по порядку
            M(oD(M(R, 2)), 3) = 0 ' ставим метку
       End If
       M(R, 2) = "" ' удаляем из колонки В
    Next R
    
  .Range("A1:C" & LR) = M ' Выгружаем массив на лист
  
' осталось показать совпавшие. Они в словаре. Можно былобы воспользоваться Transpose
'Но у него ряд ограничений. Так что массивом опять
  U = oE.keys 'словарь  в промежуточный массив
  ReDim M(UBound(U), 1 To 1)
  For R = 0 To UBound(U)
    M(R, 1) = U(R)
  Next R
.Range("B1").Resize(UBound(U) + 1) = M
End With
End Sub
помогу решить контрольные VB6, VBA (недорого)
Alex77755@mail.ru
alex77755 вне форума Ответить с цитированием
Старый 29.10.2014, 09:44   #20
valerij
Старожил
 
Аватар для valerij
 
Регистрация: 12.05.2007
Сообщений: 2,339
По умолчанию

Цитата:
Сообщение от alex77755 Посмотреть сообщение
Значит данные во втором столбце идут не по порядку, а где-то есть пустая ячейка. По ней и выход из цикла.
Кстати вчера уже вечером дошло: метки в колонке С не соответствуют.
Не тот индекс я поставил. Сейчас найду файл поправлю. Если метка нужна конечно.
Вот только если нужна и есть дубли, то метить все или только первую, или только последнюю?
alex77755
Нет там пустой ячейки, это же данные после нашего отсева.
Вот сам взгляни - Rez.txt - В-В, а файл 16_737.txt - А-А
https://yadi.sk/d/iqmxmsN3cLbg8

Метка обязательна нужна или найденные файлы должны быть строго против = ячеек в А-А, это даёт мне ориентацию по адресам в HEX редакторе, тороплюсь на работу, часа через 4 буду.
Спасибо.

alex77755
Проверил макрос всё сошлось с первым - 179 321 строка, время ~ минута, для гарантии ещё можно подсчитать количества нулей, ну я с этим справлюсь - отдельным макросом.
Код:
For x = 1 To 531552
If Cells(x, 3) = "" Then
Else
Z = Z + 1
End If
Next
MsgBox Z
Z = 179 321 Всё ОК!!

Последний раз редактировалось valerij; 29.10.2014 в 12:48.
valerij вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Тормозит программа Кротяка C++ Builder 5 22.05.2013 20:08
Тормозит glebast Помощь студентам 10 27.04.2012 21:48
Тормозит компьютер BlackOff_Max Компьютерное железо 9 10.03.2012 22:46
тормозит макрос после первой печати данного документа SergeiK Microsoft Office Excel 11 12.05.2011 22:50
Системник тормозит Dreanks Компьютерное железо 0 21.08.2010 10:49