При ошибке resume next перестал работать
В своей нынешней роли я унаследовал (должно быть, в прошлой жизни я был злом) некоторый MS Access VBA, который работал в течение многих лет.
Сегодня он случайно начал выбрасывать ошибки. Я отследил его до фрагмента кода, который использует старый трюк on-error-resume-next, который программисты VB6 и VBA должны были использовать в отсутствие приличной обработки ошибок.
Минимальный код, с помощью которого я могу воссоздать эту проблему, таков...
On Error Resume Next ws.Range("A1:K18").Replace "", "0" On Error GoTo 0Где
ws
это рабочий лист в книге Excel (который был добавлен в Access VBA), и диапазон заполнен данными (нет пустых ячеек) (так как, если есть пустые ячейки, то Replace не выдает сообщение "Я не могу найти ничего для замены", которого я пытаюсь избежать)Я перепробовал все обычные вещи (см. ниже), но безрезультатно. Интересно, что MS Excel, похоже, не пострадала.
Способ обойти эту конкретную проблему, очевидно, состоит в том, чтобы сначала выполнить поиск и только при необходимости выполнить команду Replace. Тем не менее, я осознаю, что в бизнесе существуют сотни решений EUP, и я хотел бы найти общее решение, если это возможно.
Это Windows 10, Office 365 ProPlus с версией доступа 1803 (сборка 9126.2351), т. е. VBA Retail 7.1, никаких обновлений Office не применялось с момента его последней работы.
Что я уже пробовал:
- Проверка IDE,инструменты, опции, Общие сведения, Перехват ошибок не были изменены на "Break on All Errors"
- Перепробовал все комбинации этой настройки
- Компактная и отремонтированная база данных
- Полностью декомпилирована рассматриваемая база данных и перекомпилирована
- применить команду GPUpdate /Force и перезагрузку
Maciej Los
Кэролайн, много лет назад я был в таком же положении. Причина была очень странной, потому что что-то случилось с модулями (я нашел неопознанный знак/символ).
Как пройти мимо этого? Экспортируйте и удалите все модули (пользовательские формы тоже), затем уплотните и восстановите базу данных. Проверьте файлы. Наконец, импортируйте модули и снова компактуйте и ремонтируйте. Дай мне знать, если это поможет.
CHill60
Ну а 47 модулей спустя .. Боюсь, это не сработало. :-(
У меня нет прав администратора на моей машине, поэтому я не могу запустить sfc, но одна и та же проблема может быть воспроизведена на разных машинах. По иронии судьбы, если я просто помещаю абсолютный минимум кода в новую базу данных, она не воспроизводит ошибку!
Теперь я совершенно уверен, что все остальное не развалится внезапно, поэтому я только что выпустил исправление "посмотрите, есть ли оно там, прежде чем пытаться заменить".
Хотя странно.
Спасибо за попытку
С
Maciej Los
У меня есть еще одна идея. Пожалуйста, проверьте, есть ли ситуация, которая была описана MSDN: "If the calling procedure has an enabled error handler, it is activated to handle the error.
"
On Error statement (VBA) | Microsoft Docs[^]
CHill60
Поэтому я убрал всю обработку ошибок, за исключением кусочка вокруг моего крошечного фрагмента - боюсь, он все еще не работал.
Maciej Los
Ну что ж, тебе придется расколоть крепкий орешек...
Я бы позвонил обслуживающему персоналу, чтобы обеспечить процедуру с:
- проверка файловой системы,
- Проверка и ремонт области жесткого диска
- очистка системы (удаление ненужных точек восстановления, )
- прием.
Это должно помочь!
Если это не поможет, то будет последнее, что нужно сделать:
Создайте новую базу данных. Вставьте новый модуль и вставьте свой короткий фрагмент кода. Импортируйте все таблицы и запросы. Затем импортируйте модули (UserForms), но не все за это время. Импортируйте один за другим и после каждого импорта компилируйте код, компактируйте и восстанавливайте базу данных и, наконец, проверяйте, работает ли ваш фрагмент кода. Должно быть что-то, что вызывает такое странное поведение.
Я сохраню свои пальцы для тебя, Кэролайн. Я надеюсь, что это поможет вам решить вашу проблему.
Овации
Мацей
CHill60
Твое здоровье, приятель. Я принял прагматичный подход к изменению способа работы кода, чтобы
If Not r.Find(What:="", After:=ws.Range("A1"), LookIn:=xlValues) Is Nothing Then r.Replace "", "0" End IfЭто занимает немного больше времени, но, по крайней мере, это работает :-)
Maciej Los
- Подожди минутку...
Вы заменяете пустую строку в ячейках на "нули" перед импортом/экспортом?
Вы пробовали захватить/сбросить данные из Excel через ADODB.Recordset:
sSQL = "SELECT IIF(Field1 IS NULL, "0", Field1) AS Field1, ..." & vbCrLf & _ "FROM [Sheet1]" Set oRst = New ADODB.Recordset() oRst.Open(sSql, ...) 'further ws.Range("A2").CopyFromRecordset(oRst)
CHill60
Честно говоря, все это скоро будет выброшено. Это настоящий бардак. Он заменяется базой данных sql server :аплодисменты: :-)
Maciej Los
Кэролайн, похоже, ты не заинтересована в поиске решения....
Я бы предложил удалить этот вопрос.
CHill60
Привет, Мацей. Я все еще заинтересован в решении ... оказывается, что "скоро" в том, чтобы быть выброшенным, - это один из тех относительных терминов. "Недостаточно скоро" - вот мое нынешнее чувство! Похоже он будет здесь дольше чем я думал
Maciej Los
К сожалению, я должен признать, что не могу воспроизвести вашу проблему. Вы можете поделиться своим файлом?
CHill60
Боюсь, что не смогу, так как он содержит конфиденциальную информацию и к тому же очень велик.
Вы хотите опубликовать решение, которое суммирует все предложения, которые вы придумали (на случай, если у кого - то еще есть подобные проблемы) - я знаю, что у меня все еще есть проблема, но все, что вы придумали, было действительным, поэтому я все равно приму решение
Maciej Los
Хм...
Я не искал решения для публикации. Мне было очень интересно решить вашу проблему.
Если вы считаете, что мои идеи по решению проблемы хороши, я могу опубликовать их в качестве решения.
CHill60
Я думаю, что идеи очень хорошие. В своих исследованиях я сталкивался с ними всеми ... просто не все в одном и том же месте!
Maciej Los
Я был воодушевлен ;)
Готово!
Maciej Los
И еще одно примечание: пожалуйста, проверьте, все ли в порядке с ОС. Запустите [cmd] от имени администратора и введите sfc /scannnow
CHill60
Спасибо Мацей. Я попробую это сделать завтра