Автор Тема: ASSERT  (Прочитано 29321 раз)

vlad

  • Hero Member
  • *****
  • Сообщений: 1391
    • Просмотр профиля
Re:ASSERT
« Ответ #15 : Февраль 19, 2011, 09:48:06 pm »
Этот код я назначил сам, и он имеет смысл только для меня, как для автора программы. От пользователя, у которого сбойнула моя программа, мне нужен только этот код и больше ничего.

Неправда. Первое, что вы захотите от пользователя в случае какой-либо ошибки - это версия.

По памяти, в документации на КП/BB вроде определены стандартные коды, и определён также дииапазон кодов для использования по своему усмотрению. Этими спецификациями я не пользуюсь.

Что лишний раз показывает бессмысленность подобного рода спецификаций...

Представьте, что у Вас много клиентов, которые пользуются различными версиями Вашей программы, и они присылают Вам отчёты, что в такой-то строчке сработал ассерт. В данной ситуации код ошибки надёжнее, потому что в различных версиях программы нумерация строк может поплыть.

Коды тоже могут поплыть. Кроме того, поддерживать уникальность этих кодов в достаточной большей системе - это отдельная задача ;) Но, еще раз, версию вы захотите узнать в любом случае.

Цитировать
В моём примере "199" и есть код ошибки.

Не совсем. Его нельзя нормально обработать потребителю вашего модуля. Если опять говорить о варианте сторонних модулей без исходников...
« Последнее редактирование: Февраль 19, 2011, 09:49:38 pm от vlad »

valexey

  • Administrator
  • Hero Member
  • *****
  • Сообщений: 1990
    • Просмотр профиля
Re:ASSERT
« Ответ #16 : Февраль 19, 2011, 11:39:23 pm »
Нет, я что-то не совсем понимаю зачем это самое целочисленное значение ассерту скармливать. Вот смотрите: сработал ASSERT, отлично. Благодаря наличию метаинформации мы точно знаем CallStack с названиями функции, мы знаем версии всех модулей, знаем структуру функции где оно сработало. В конце концов ничто не мешает также знать и вид логического условия сработавшего ассерта. Всё это мы знаем без наличия исходников.

Если ASSERT сработал на машине пользователя, то среда должна сформировать слепок состояния программы, дамп памяти, в виде пригодном для последующего анализа. Например в виде составного документа. Этот слепок отправляется к разработчику, где он уже спокойно разбирает что там случилось. Благодаря метаинформации (см. выше) он точно будет знать какая версия чего там была установлена. Он будет знать состояние стэка вызовов и т.п. Зачем тут какое-то магическое число?

Если у нас метаинформации нет (скажем у нас не КП а Оберон, а там метаинформации ровно столько же сколько в С++ скажем), то тогда да, ASSERT должен быть поумнее. Но в этом случае опять таки не нужно число. Нужно банально печатать (если у нас нет данных о стэке вызовов): файл, строку, содержимое строки этого самого  ASSERT'a (это будет нечто вроде ASSERT(a#b) ). На этапе исполнения накладных расходов тут будет ровно нуль.
"но сейчас, чтобы компенсировать растущую мощность компьютеров, программисты используют фреймворки"

vlad

  • Hero Member
  • *****
  • Сообщений: 1391
    • Просмотр профиля
Re:ASSERT
« Ответ #17 : Февраль 20, 2011, 03:16:54 am »
Нет, я что-то не совсем понимаю зачем это самое целочисленное значение ассерту скармливать.

Я тут полазил по сообщениям о языках, вот что я нарыл:
оригинальный оберон от Вирта: ASSERT отсутствует, есть HALT
оберон-07: ASSERT есть в двух перегруженных видах - с и без числа.
ББ: ASSERT тоже двух видов, HALT присутствует. Разница между ASSERT(FALSE, n) и HALT(n) не поясняется. HALT очень смахивает на лишнюю сущность ;)

Сделаю предположение, что ASSERT с вторым параметром Вирт оставил для случая, когда компилятор делается настолько простым, что не в состоянии вкомпилить номер строки и имя модуля. О нормальном стэктрэйсе в таком случае тоже говорить не приходится. А отлаживаться как-то надо.

P.S. На форуме мало истинных оберонщиков. Они бы сразу ткнули в ASSERT без второго параметра.


igor

  • Sr. Member
  • ****
  • Сообщений: 438
    • Просмотр профиля
Re:ASSERT
« Ответ #18 : Февраль 20, 2011, 04:58:07 am »
Первое, что вы захотите от пользователя в случае какой-либо ошибки - это версия.
Да, Вы правы. Версия программы в таких случаях по любому важна.

Цитата: vlad
в документации на КП/BB вроде определены стандартные коды, ... . Этими спецификациями я не пользуюсь.
Что лишний раз показывает бессмысленность подобного рода спецификаций...
Наблюдения показывают, что всё, что носит рекомендательный характер, на практике частенько нарушается. Об этом даже сам Н. Вирт говорил, когда рассказывал про "лазейки" в языке. Наличие этих спецификаций может быть оправдано только тем, что разработчики хотели, чтобы коды ошибок были унифицированы. Возможно, это полезно для коллектива разработчиков. Но я пишу один, и для меня это не важно.

igor

  • Sr. Member
  • ****
  • Сообщений: 438
    • Просмотр профиля
Re:ASSERT
« Ответ #19 : Февраль 20, 2011, 05:02:33 am »
Если ASSERT сработал на машине пользователя, то среда должна сформировать слепок состояния программы, дамп памяти, в виде пригодном для последующего анализа.
Стоп. А где в стандарте языка сказано, что среда должна всё это сделать?  ;)

igor

  • Sr. Member
  • ****
  • Сообщений: 438
    • Просмотр профиля
Re:ASSERT
« Ответ #20 : Февраль 20, 2011, 05:14:37 am »
Разница между ASSERT(FALSE, n) и HALT(n) не поясняется. HALT очень смахивает на лишнюю сущность ;)
Не помню, как предписано стандартом языка, но по факту в BB ассерты проверяются не только в run-time, но даже уже на этапе компиляции. Поэтому ASSERT(FALSE) воспринимается компилятором как семантическая ошибка. Когда я это обнаружил, то был немного удивлён. Для безусловного останова вместо такого ассерта предлагается использовать HALT. В этом случае ошибки не возникает, и компиляция пройдёт успешно.

Цитата: vlad
P.S. На форуме мало истинных оберонщиков. Они бы сразу ткнули в ASSERT без второго параметра.
А, так Вы не знали, что ASSERT можно использовать без второго параметра?  :o

Peter Almazov

  • Sr. Member
  • ****
  • Сообщений: 482
    • Просмотр профиля
Re:ASSERT
« Ответ #21 : Февраль 20, 2011, 06:23:18 am »
Нет, я что-то не совсем понимаю зачем это самое целочисленное значение ассерту скармливать. Вот смотрите: сработал ASSERT, отлично. Благодаря наличию метаинформации мы точно знаем CallStack с названиями функции, мы знаем версии всех модулей, знаем структуру функции где оно сработало. В конце концов ничто не мешает также знать и вид логического условия сработавшего ассерта. Всё это мы знаем без наличия исходников.

Если ASSERT сработал на машине пользователя, то среда должна сформировать слепок состояния программы, дамп памяти, в виде пригодном для последующего анализа. Например в виде составного документа. Этот слепок отправляется к разработчику, где он уже спокойно разбирает что там случилось. Благодаря метаинформации (см. выше) он точно будет знать какая версия чего там была установлена. Он будет знать состояние стэка вызовов и т.п. Зачем тут какое-то магическое число?

Если у нас метаинформации нет (скажем у нас не КП а Оберон, а там метаинформации ровно столько же сколько в С++ скажем), то тогда да, ASSERT должен быть поумнее. Но в этом случае опять таки не нужно число. Нужно банально печатать (если у нас нет данных о стэке вызовов): файл, строку, содержимое строки этого самого  ASSERT'a (это будет нечто вроде ASSERT(a#b) ). На этапе исполнения накладных расходов тут будет ровно нуль.
Ну вот смотрите, предположим у вас кусок сложных вычислений. Утверждений ASSERT(x >y) рядом штук 10. От все вышеперечисленно будет мало толку. Нужна строка с объяснением логики. Вполне возможно, что в терминах более высокого уровня, чем x и y.

vlad

  • Hero Member
  • *****
  • Сообщений: 1391
    • Просмотр профиля
Re:ASSERT
« Ответ #22 : Февраль 21, 2011, 02:16:30 pm »
Если ASSERT сработал на машине пользователя, то среда должна сформировать слепок состояния программы, дамп памяти, в виде пригодном для последующего анализа.
Стоп. А где в стандарте языка сказано, что среда должна всё это сделать?  ;)

Вообще в стандарте, который репорт, мало чего сказано (а то в 16 страниц было бы не уложиться). Много чего отдано на откуп здравому смыслу. По факту, найти сейчас современную реализацию ЯП, которая не позволяла бы диагностировать фатальные проблемы в виде стэка/дампа - очень сложно. Для экстремальных случаев, типа выдать рабочий компилятор/рантайм для экзотической железки за человеко-месяц - да, можно сэкономить и использовать второй параметр в ассерте.

vlad

  • Hero Member
  • *****
  • Сообщений: 1391
    • Просмотр профиля
Re:ASSERT
« Ответ #23 : Февраль 21, 2011, 02:20:10 pm »
Не помню, как предписано стандартом языка, но по факту в BB ассерты проверяются не только в run-time, но даже уже на этапе компиляции. Поэтому ASSERT(FALSE) воспринимается компилятором как семантическая ошибка. Когда я это обнаружил, то был немного удивлён. Для безусловного останова вместо такого ассерта предлагается использовать HALT. В этом случае ошибки не возникает, и компиляция пройдёт успешно.

Да, интересно, зачем на практике такое свойство можно использовать? И как далеко компилятор идет в своем рвении? Любое выражение с константами, дающее FALSE? Или жестко FALSE как лексема?

Цитата: igor
А, так Вы не знали, что ASSERT можно использовать без второго параметра?  :o

Да, не знал, в ББ'шных исходниках второй параметр всегда присутствует.

vlad

  • Hero Member
  • *****
  • Сообщений: 1391
    • Просмотр профиля
Re:ASSERT
« Ответ #24 : Февраль 21, 2011, 02:27:07 pm »
Ну вот смотрите, предположим у вас кусок сложных вычислений. Утверждений ASSERT(x >y) рядом штук 10. От все вышеперечисленно будет мало толку. Нужна строка с объяснением логики. Вполне возможно, что в терминах более высокого уровня, чем x и y.

У нас, кстати, есть неотключаемая версия ассерта с вторым параметром в виде строки. И у меня постоянно возникают проблемы с придумыванием этой самой строки. Приходится вбивать что-то на отвяжись. Все равно будет непонятно, пока не полезешь в код и не посмотришь. А чтобы полезть и посмотреть достаточно имени исходника и номера строки. А еще лучше - полноценный дамп стэка.

P.S. Да, если таки у сложного ассерта есть простое объяснение, то оно просто записывается в виде комментария напротив этого ассерта.

Peter Almazov

  • Sr. Member
  • ****
  • Сообщений: 482
    • Просмотр профиля
Re:ASSERT
« Ответ #25 : Февраль 21, 2011, 02:54:07 pm »
У нас, кстати, есть неотключаемая версия ассерта с вторым параметром в виде строки. И у меня постоянно возникают проблемы с придумыванием этой самой строки. Приходится вбивать что-то на отвяжись.
А теперь представьте себе, что вы вбиваете не строку, а число, отдельно в строковых ресурсах прописываете, какая строка ему соответствует, причем на нескольких языках  :)

valexey

  • Administrator
  • Hero Member
  • *****
  • Сообщений: 1990
    • Просмотр профиля
Re:ASSERT
« Ответ #26 : Февраль 21, 2011, 02:56:17 pm »
Да, при этом неплохо бы еще представить, что enum'ов у тебя также нет :-) Это сулит много радости в не маленьких проектах.
"но сейчас, чтобы компенсировать растущую мощность компьютеров, программисты используют фреймворки"

igor

  • Sr. Member
  • ****
  • Сообщений: 438
    • Просмотр профиля
Re:ASSERT
« Ответ #27 : Февраль 22, 2011, 04:11:49 am »
... Поэтому ASSERT(FALSE) воспринимается компилятором как семантическая ошибка.

Да, интересно, зачем на практике такое свойство можно использовать? И как далеко компилятор идет в своем рвении? Любое выражение с константами, дающее FALSE? Или жестко FALSE как лексема?
Любое константное выражение, дающее FALSE. Вообще-то я не проверял, но на 100% уверен что так, ибо все известные мне компиляторы производят свёртку констант. А неконстантное выражение на этапе компиляции в общем случае вычислить невозможно, для этого нужно выполнить программу.

По поводу использользования на практике - не знаю. При такой семантике оператор ASSERT(FALSE) лишён смысла.

valexey

  • Administrator
  • Hero Member
  • *****
  • Сообщений: 1990
    • Просмотр профиля
Re:ASSERT
« Ответ #28 : Февраль 22, 2011, 12:24:34 pm »
Пример использования ASSERT(FALSE):
- (NSEnumerator *)objectEnumerator
{
    NSAssert(NO, @"Must implement a complete subclass of MyMatrix!");
    return nil;
}
(это Objective C)
"но сейчас, чтобы компенсировать растущую мощность компьютеров, программисты используют фреймворки"