Страницы: Пред. 1 2 3 4 5 След.
RSS
Циклы и метки. В каких случаях, что использовать будет эффективнее
 
Еще заметка по поводу глобальных. Не нужно ими злоупотреблять.  Открывается книга - и область памяти занята до самого закрытия. Нет, не отказываться полностью, но и не создавать бездумно.
Как избегать размножения этих тараканов? Много вариантов: переменные передавать из одной процедуры в другую, записывать значение на лист, в имя (.Names), в реестр...
 
vikttur, спасибо - тоже уже задумывался над этим, поэтому пока у меня 1-2 глобальные переменные для хранения справочников, подгружающихся при запуске файла. Если есть своя надстройка (а у меня она есть), то имеет смысл писать такие данные в её листы. Удобно и практично. В планах разобраться с этим - может даже тему создам  :)
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Справочники имеет смысл подгружать сразу, если с ними плотно работают. Если используются раз в 16 минут :), то данные можно подгружать каждый раз перед обрабткой.
 
vikttur, и это тоже использую - спасибо. У меня 1 универсальная форма с поиском а вот массивы в неё передаю, в зависимости от задачи. Справочник подгружаю при запуске, а вот, если списки формируются из динамических данных в активном файле, то их я передаю при инициализации формы.
Изменено: Jack Famous - 05.07.2018 13:49:27
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Irregular Expression, Наверное, нужно определиться, что Вы хотите донести?
Цитата
Irregular Expression написал:
В отличие от префикса WF_ у каждой (каждой!) переменной. Если бы вдруг мне волею судеб пришлось модифицировать/рецензировать этот код, я бы начал с удаления этого префикса совсем,
Цитата
Jack Famous написал:
Irregular Expression  написал:я бы начал с удаления этого префикса совсемиспользую (только в UDF в надстройке) больше для перестраховки, чтобы гарантированно не задублировать переменные при вызове из других процедур и функций
Цитата
Irregular Expression написал:
надо использовать разный синтаксис имён переменных для разных областей видимости
Этим человек и занимался. Вы же начали ему возражать в итоге предлагая собственно то, чему изначально стали оппонировать.
Изменено: Neufazendnik - 05.07.2018 14:38:12
 
Neufazendnik, думаю что Irregular Expression имел ввиду то, что запуская макрос из макроса можно не бояться, что возникнет путаница в переменных, только если они не глобальные. А я перестраховывался. В любом случае надо тестить — Excel полон тайн, загадок, читерских комбинаций и может крашнуться совершенно рандомно (на первый взгляд)  :D
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Цитата
Jack Famous написал:
и может крашнуться совершенно рандомно (на первый взгляд)  
Мой первый учитель информатики многократно нам ученикам повторял: Машина (ЭВМ) никогда не ошибается ;) Он имел ввиду, что нам всегда стоит искать проблемы в своем коде и других вариантов у нас нет :)
А то, что локальный и глобальный контекст как-то должен выделяться в названиях переменных, я тоже нахожу логичным, потому что в противном случае есть немаловероятный риск пересечения названий и путаницы, которая по сути своей и есть дублирование, не смотря на то, что оно четко разделено в алгоритме интерпретатора, у программиста оно в голове по запарке может оказаться вовсе и не разделено и он запросто может применить локальную переменную вместо глобальной, просто по элементарной запарке.
Изменено: Neufazendnik - 05.07.2018 17:00:57
 
Neufazendnik, под "рандомно" я имел ввиду, что очередное обновление может медным тазом прикрыть наработки. Причина хоть и будет, но где и что делать - непонятно  :)
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Цитата
Jack Famous написал:
Удаление строк по критерию
Это да, нисходящее удаление нужно только при экзотических условиях удаления. А вот Вам задачка пореалистичнее (аж даже реально встретившаяся на практике). Нужно залить жёлтым минимальное количество строк, которое достаточно удалить, чтобы "Процент" в строке итогов вошёл в рамки +-10%. По мне так без Do-Loop эта задача не решается в принципе.
 
Цитата
StoTisteg написал:
чтобы "Процент" в строке итогов вошёл в рамки +-10%
Чисто интуитивно ... а  экселевская функция поиска решения с итеративным расчетом и возможностью циклических вычислений тут не поможет без всякого кода???
 
StoTisteg, это вообще дичь какая-то)))) смесь комбинаторики и дьявольского умысла))
а вообще я бы сначала загнал всё в массив, в нём бы разобрался, какие значения удалять (в комбинаторике не силён), загоняя попутно их адреса в массив, например, а потом залил бы всё в обычном цикле (а лучше сформировать Range и залить разом - тогда вообще цикл только по массиву будет, а это скорость света)  :)
Хотелось бы реальный пример и реализацию на Do-Loop посмотреть, потому что сдаётся мне, что метод "удаляй, пока не выйдешь на +-10%" таит в себе массу проблем типа "…ведь не очко обычно губит, а к 11 туз"  :D  :D  :D

UPD: Neufazendnik, разумеется, ручками - это первое, что приходит в голову, но тут весь вопрос, в том - можно ли без колдунства заменить Do-Loop на For-Next
Изменено: Jack Famous - 05.07.2018 17:14:49
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Neufazendnik, поможет. Если обрабатываемых файлов не полторы тысячи :)
 
Цитата
Neufazendnik написал:
Наверное, нужно определиться, что Вы хотите донести?
Наверное, нужно не вырывать фразы из контекста и смотреть кому они адресованы. Конкретно моё сообщение #59 недвусмысленно является ответом на Ваше сообщение #58, а не продолжением дискуссии с Jack Famous (каковой, к слову, не было).

И да, Вы не разобрались в сути нашего диалога, если пишете:
Цитата
Neufazendnik написал:
предлагая собственно то, чему изначально стали оппонировать.
Поскольку изначально я "оппонировал" (и буду оппонировать, если потребуется) использованию избыточных, режущих глаз префиксов в именах локальных переменных внутри одной процедуры (или функции).
А предложил я нечто прямо противоположное: выделять другим синтаксисом только переменные более высоких областей видимости, чем локальная.
Лучше совсем без префиксов. Например, регистром символов.

Проиллюстрирую простым примером по сохранению массива с таблицей умножения в переменную глобальной области видимости
Сравните, какой код лучше читается (и пишется):
Вариант 1 (без лишней информации):
Скрытый текст
Вариант 2 (с префиксами, указывающими на область использования):
Скрытый текст
Изменено: Irregular Expression - 05.07.2018 17:38:11
 
Цитата
Irregular Expression написал:
Сравните, какой код лучше читается (и пишется):
даже без примера очевидно  :D я ж говорю, что перестраховывался))) самому неудобно было при написании  :)
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Jack Famous, всё гораздо проще. Заполнение нулями ячеек Вчера и Сегодня эквивалентно удалению строки. Дальше просто запоминаем удалённое в записи коллекций, крутимся в цикле, пока не выйдем на 10%, восстанавливаем и заливаем количество строк, равное счётчику коллекции :)
Код
Type Del
    Tdy as Collection
    Mnd as Collection
End Type
Dim Deled as Del
With Deled
    Set .Tdy = New Collection
    Set .Mnd = New Collection
    i=2
    Do While Cells(Cells(Rows.Count,1).End(xlUp).Row,5).Value>0.1
        .Tdy.Add Cells(i,2).Value
        Cells(i,2).Value=0
        .Mnd.Add Cells(i,3).Value
        Cells(i,3).Value=0
        i=i+1
    Loop
    For i=2 to .Tdy.Count+1
        Cells(i,2).Value=.Tdy(i-1)
        Cells(i,3).Value=.Mnd(i-1)
    Next i
End With
Range(Rows(2),Rows(i-1)).Interior.Color=vbYellow

Как видите, полный набор — и Do...Loop, и For...Next и использование счётчика после выхода до кучи :)
Изменено: StoTisteg - 05.07.2018 17:46:01
 
Цитата
Jack Famous написал:
можно ли без колдунства заменить Do-Loop на For-Next
Можно. Крутим For-Next до конца таблицы и делаем Exit For при выполнении условия. Заодно в счётчике имеем номер последней закрашиваемой строки. Но зачем?
 
Цитата
StoTisteg написал:
всё гораздо проще
пфффф - да ваще раз плюнуть  :D  :D  :D детская задачка
Type Del объявляется сразу после Sub или перед ним? Нечасто такое вижу, не знаю, зачем и как пользоваться…
Цитата
StoTisteg написал:
Но зачем?
согласен. В любом случае, инструмент нужно знать, а с практикой придёт и понимание - где и что лучше/быстрее/логичнее/удобнее (нужное подчеркнуть) использовать  ;)
Изменено: Jack Famous - 05.07.2018 17:53:04
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Изменил функцию, убрав лишние метки))) оставил только 1 для выхода по непредвиденной ошибке
Код функции
я так понимаю, что без меток реализовать "возврат", как в сообщении #44 будет весьма неудобно. Получается, что для каждой проверки внутри Do-Loop придётся вводить булевую переменную и все их проверять в каждом цикле на предмет вызова сообщения. Это неудобно (если другого способа нет).
Таким образом, можно сказать, что метки более удобны не только для обработки непредвиденных ошибок (не знаю сравнимого аналога On Error GoTo er), но и для осуществления возврата к предыдущим местам кода?…

Для себя пока понял, что метки вполне можно использовать (помимо основных случаев типа вышеописанных) для уменьшения размеров кода, устранения эффекта "поваленного вправо дерева" и общего "облегчения" конструкции кода и её понимания. Везде нужна мера.
Изменено: Jack Famous - 05.07.2018 19:08:20
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Цитата
Irregular Expression написал:
А предложил я нечто прямо противоположное: выделять другим синтаксисом только переменные более высоких областей видимости, чем локальная. Лучше совсем без префиксов. Например, регистром символов.
Это уже другой коленкор. Первое заявление звучало несколько иначе.
 
Цитата
StoTisteg написал:
Если обрабатываемых файлов не полторы тысячи
https://www.youtube.com/watch?v=gKpk4-tAzs4
 
Neufazendnik,  (полномочия) :D
Изменено: Jack Famous - 05.07.2018 19:18:06
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Я стараюсь вообще не использовать подчёркивание в переменных и прочих названиях процедур. Код глазами трудно читается. Ну это так, к слову. Просто открыл код Jack Famous и в глазах зарябило от _ _ _. Очень сложно отделяются переменные от всего остального.  :idea:  
Мастерство программиста не в том, чтобы писать программы, работающие без ошибок.
А в том, чтобы писать программы, работающие при любом количестве ошибок.
 
StoTisteg,
А когда закончит работать этот цикл?
Код
    Do While Cells(Cells(Rows.Count,1).End(xlUp).Row,5).Value>0.1
        .Tdy.Add Cells(i,2).Value
        Cells(i,2).Value=0
        .Mnd.Add Cells(i,3).Value
        Cells(i,3).Value=0
        i=i+1
    Loop

Это либо вечный цикл, либо вообще не рабочий все зависит от значения в ячейке
Код
Cells(Cells(Rows.Count,1).End(xlUp).Row,5).Value>0.1

Либо я что то не понимаю?
"Все гениальное просто, а все простое гениально!!!"
 
Цитата
Jack Famous написал:
Type Del объявляется сразу после Sub или перед ним?
Перед, разумеется. Это всё выглядит страшно, а на самом деле запись обыкновеннейшая, паскалевская.
 
Цитата
Nordheim написал:
А когда закончит работать этот цикл?
Когда в строке итогов процент станет меньше 0,1. Разумеется, это всё грубо, в боевом макросе ещё куча проверок.
 
Цитата
Nordheim написал:
Это либо вечный цикл, либо вообще не рабочий все зависит от значения в ячейке
Это вообще-то строка итогов, там значение меняется при обнулении 2 и 3 столбцов.
 
StoTisteg, благодарю)
Alemox, не могу не согласится - это действительно неудобно. Уже занимаюсь тестированием, чтобы заменить переменные
Изменено: Jack Famous - 06.07.2018 10:34:09
Во всех делах очень полезно периодически ставить знак вопроса к тому, что вы с давних пор считали не требующим доказательств (Бертран Рассел) ►Благодарности сюда◄
 
Цитата
Nordheim написал:
Это либо вечный цикл, либо вообще не рабочий все зависит от значения в ячейке
УМВР.
 
Аналог этого кода
Код
    Do While Cells(Cells(Rows.Count,1).End(xlUp).Row,5).Value>0.1
        .Tdy.Add Cells(i,2).Value
        Cells(i,2).Value=0
        .Mnd.Add Cells(i,3).Value
        Cells(i,3).Value=0
        i=i+1
    Loop

Этот
Код
      For i = 2 To Range("a" & Rows.Count).End(xlUp).Row - 1
        .Tdy.Add Cells(i, 2).Value
        Cells(i, 2).Value = 0
        .Mnd.Add Cells(i, 3).Value
        Cells(i, 3).Value = 0
        If Cells(Cells(Rows.Count, 1).End(xlUp).Row, 5).Value < 0.1 Then Exit For
      Next i
Изменено: Nordheim - 06.07.2018 12:51:39
"Все гениальное просто, а все простое гениально!!!"
 
Ну да. Но Exit For — ненужный костыль. И да, это не аналог, аналог вот:
Код
      For i = 2 To Range("a" & Rows.Count).End(xlUp).Row - 1
 If Cells(Cells(Rows.Count, 1).End(xlUp).Row, 5).Value < 0.1 Then Exit For       
 .Tdy.Add Cells(i, 2).Value
        Cells(i, 2).Value = 0
        .Mnd.Add Cells(i, 3).Value
        Cells(i, 3).Value = 0
      Next i
То есть костыли во всей своей красе — первым делом цикл проверяет, не пора ли на выход :)
Изменено: StoTisteg - 06.07.2018 12:59:55
Страницы: Пред. 1 2 3 4 5 След.
Наверх