В C и C ++ очень легко написать следующий код с серьезной ошибкой.
char responseChar = getchar();
int confirmExit = 'y' == tolower(responseChar);
if (confirmExit = 1)
{
exit(0);
}
Ошибка в том, что оператор if должен был быть:
if (confirmExit == 1)
Как закодировано, он будет выходить каждый раз, потому что происходит присвоение confirmExit
переменной, а затем confirmExit
используется как результат выражения.
Есть ли хорошие способы предотвратить такую ошибку?
c++
coding-standards
DeveloperDon
источник
источник
if (confirmExit)
.a = b
либоa == b
условное выражение .Ответы:
Лучший способ - повысить уровень предупреждения вашего компилятора. Затем он предупредит вас о возможном назначении в условном условии.
Убедитесь, что вы компилируете свой код с нулевыми предупреждениями (что вы должны делать в любом случае). Если вы хотите быть педантичным, тогда настройте свой компилятор так, чтобы предупреждения воспринимались как ошибки.
Использование условных выражений Йоды (размещение константы в левой части) было еще одной техникой, которая была популярна около десяти лет назад. Но они затрудняют чтение кода (и, следовательно, поддерживают его из-за неестественного способа чтения (если вы не Йода)) и не дают большей выгоды, чем повышение уровня предупреждений (что также дает дополнительные преимущества при большем количестве предупреждений).
Предупреждения являются действительно логическими ошибками в коде и должны быть исправлены.
источник
if (0 == ret)
ужаса.a == b
!!0==a && 0==b || 1==a && 1==b || 2==a && 2==b || ...
(повторите для всех возможных значений). Не забывайте об обязательной...|| 22==a && 22==b || 23==a && 24==b || 25==a && 25==b ||
... ошибке, иначе программистам не понравится.Вы всегда можете сделать что-то радикальное, например, протестировать свое программное обеспечение Я даже не имею в виду автоматические модульные тесты, просто тесты, которые каждый опытный разработчик делает по привычке: дважды запускает свой новый код, один раз подтверждая выход, а второй - нет. Вот почему большинство программистов считают это не проблемой.
источник
rc=MethodThatRarelyFails(); if(rc = SUCCESS){
более одного раза, особенно если метод дает сбой только в условиях, которые трудно проверить.Традиционный способ предотвратить неправильное использование присваиваний в выражении - поместить константу слева и переменную справа.
Компилятор сообщит об ошибке при неправильном присвоении константы, аналогичной следующей.
Пересмотрено, если условие будет:
Как показано в комментариях ниже, многие считают это неуместным методом.
источник
Я согласен со всеми, кто говорит «предупреждения компилятора», но я хочу добавить еще одну технику: обзоры кода. Если у вас есть политика проверки всего кода, который был зафиксирован, предпочтительно до того, как он будет зафиксирован, то, скорее всего, такого рода вещи будут обнаружены во время проверки.
источник
Во-первых, повышение уровня предупреждения никогда не повредит.
Если вы не хотите, чтобы ваше условное выражение проверяло результат присваивания внутри самого оператора if, а затем много лет работал со многими программистами на C и C ++ и никогда не слышал, что сначала сравнивать константу
if(1 == val)
было плохо, вы мог бы попробовать эту конструкцию.Если ваш руководитель проекта одобряет ваши действия, не беспокойтесь о том, что думают другие люди. Настоящим доказательством является то, сможете ли вы или кто-то еще разобраться в вашем коде через месяцы и годы.
Однако, если вы намеревались проверить результат присваивания, то использование более высоких предупреждений могло бы [вероятно, перехватить] присвоение константе.
источник
if ( auto myPtr = dynamic_cast<some_ptr>(testPtr) ) {
в том, что она позволяет избежать бесполезногоnullptr
охвата в случае сбоя приведения - что, вероятно, является причиной того, что C ++ имеет такую ограниченную способность назначать в условных выражениях. В остальном, да, определение должно иметь свою собственную линию, я бы сказал - намного легче увидеть с первого взгляда и менее склонно к разным промахам.Опоздал на вечеринку, как всегда, но ключом здесь является статический анализ кода.
Большинство IDE теперь предоставляют SCA сверх синтаксической проверки компилятора, и доступны другие инструменты, в том числе те, которые реализуют рекомендации MISRA (*) и / или CERT-C.
Заявление: я являюсь частью рабочей группы MISRA C, но я публикую пост в личном качестве. Я также независим от любого поставщика инструмента
источник
Просто используйте назначение левой рукой, предупреждения компилятора могут помочь, но вы должны убедиться, что вы получаете правильный уровень, иначе вы либо будете забиты бессмысленными предупреждениями, либо вам не скажут те, которые вы хотите увидеть.
источник