Это похоже на тех, кто говорит goto
плохо из-за статьи, написанной Джикстра на эту тему в 60-х годах.При свободном использовании я бы согласился.Но, например, в C-функции, которая не имеет преимущества обработки исключений в C ++ с использованием try
и catch
, преднамеренное и преднамеренное использование goto
может быть очень полезным при создании автономной очистки-up раздел в случае возврата ошибки для функции, которая выделяет память, используя malloc()
.Без оператора goto
вам пришлось бы размещать код очистки в конце каждого оператора if
, который обнаружил ошибку.Например, что выглядит лучше для вас ... это:
int my_func()
{
int* a = malloc(10);
//... some code
if (some_error)
{
free(a);
return -1;
}
//... more code
if (some_other_error)
{
free(a);
return -1;
}
//... more code
if (another_error)
{
free(a);
return -1;
}
//... more code
free(a);
return 0;
}
или код, который выглядит следующим образом:
void my_func()
{
int* a = malloc(10);
//... some code
if (some_error)
goto return_error;
//... more code
if (some_other_error)
goto return_error;
//... more code
if (another_error)
goto return_error;
//... more code
normal_return:
free(a);
return 0;
return_error:
free(a);
return -1;
}
В первом примере каждый раз, когда вы что-то меняли, выпришлось бы управлять всеми возвратами ошибок в каждом из блоков оператора if.Последний подход дает вам хороший отдельный раздел очистки.То же самое верно и для других произвольных правил синтаксиса, таких как «не использовать break
в цикле» ... если это помогает повысить удобство сопровождения кода, надежность и удобочитаемость, используйте его всеми средствами.