2009-07-29 6 views
2

рассмотрит следующий DELPHI паскаль код:DELPHI: как использовать «break» вне цикла или футляра?

var 
    tc: TComponent 
begin 
{ do something to get tc } 
repeat 
    if(tc is TDBEdit)then begin 
    if(check_something_about_edit(tc))then break; 
    do_something_else_edit(tc); 
    break; 
    end else if(tc is TBMemo) then begin 
    if(check_something_about_memo(tc))then break; 
    do_something_else_memo(tc); 
    break; 
    end; 
    raise exception.create('invalid component type'); 
until(true); {single iteration look required to use break } 

Я знаю, что, вероятно, некоторые полиморфные вещи, которые я мог бы сделать с TComponent, но это не мой вопрос. Мне интересно, есть ли способ избавиться от единственного итерационного повторения-до утверждения. Без этого я не могу использовать оператор break в любом месте в блоке обработки, и мне нужно, чтобы остановить обработку в любое время.

+1

Действительно, возможно, существует «полиморфный материал», который вы можете сделать; оба эти типа компонентов сходят с «TCustomEdit». Измените объявление 'tc' на это. –

+2

+1. Хотя код, который вы опубликовали, является жестоким, вы были правы, чтобы спросить, как его улучшить. Всякий раз, когда у вас есть цикл, который никогда не должен выполняться более одного раза, вы делаете что-то неправильно. –

ответ

4

Упакуйте его в функцию и используйте выход, чтобы вернуться назад. если есть больше кода, чтобы следовать за повторное заявление, использовать локальную функцию/процедуру, что-то вроде:

procedure ... 
    procedure testsomething(tc: TComponent); 
    begin 
    if(tc is TDBEdit)then begin 
     if(check_something_about_edit(tc))then exit; 
     do_something_else_edit(tc); 
     exit; 
    end else if(tc is TBMemo) then begin 
     if(check_something_about_memo(tc))then exit; 
     do_something_else_memo(tc); 
     exit; 
    end; 
    raise exception.create('invalid component type'); 
    end; 

var 
    tc: TComponent; 
begin 
{ do something to get tc } 
    try 
    TestSomething(tc); 
    { do something more } 
    except 
    ... 
    end; 
end; 
+0

, в то время как решение if-else более корректно в этом конкретном случае, это решение более применимо к реальному случаю. Это требует перемещения кучи кода, но все в порядке. Я предпочитаю, чтобы все было правильно. –

4

То, что вы на самом деле делаете, используя перерыв как Гото. Предложение Ральфа использовать функцию в качестве области является хорошим. Но в противном случае вы могли бы быть честными и использовать «goto finished». Потеря повторения сделает его более читаемым.

+0

hmmm, случай, когда goto на самом деле/​​меньше/зло, чем перерыв. Странные дни ... –

+0

Ну, вы пришли с очень злым использованием перерыва. И break/continue в любом случае структурированы goto. –

14

Существует еще один простой путь:

if(tc is TDBEdit)then begin 
    if not (check_something_about_edit(tc)) then 
    do_something_else_edit(tc); 
end else if(tc is TBMemo) then begin 
    if not (check_something_about_memo(tc)) then 
    do_something_else_memo(tc); 
end else 
    raise exception.create('invalid component type'); 
end; 
+0

Я думаю, что это намного лучшая альтернатива, чем первая, которую вы опубликовали. –

+0

так же, как и я, но потребовалось некоторое время, чтобы пройти код;) –

+0

Я оставляю другой, возможно, он может быть полезен в аналогичной настройке. –

1

Почему вы хотите использовать перерыв, а не выход? Разрыв в Delphi - это не то же самое, что «перерыв» в курчавых языках.

var 
    tc: TComponent 
begin 
    { do something to get tc } 
    if (tc is TDBEdit) then 
    begin 
    if not (check_something_about_edit(tc)) then 
     do_something_else_edit(tc); 
    Exit; 
    end; 
    if (tc is TBMemo) then 
    begin 
    if not (check_something_about_memo(tc)) then 
     do_something_else_memo(tc); 
    Exit; 
    end; 
    raise exception.create('invalid component type'); 
end; 

Точка о расположении. Если бы вы не пытались уменьшить количество пробелов настолько, что это могло бы привести к тому, что возьмет «еще один час, чтобы убедиться, что все мои if-else выстроены правильно», как вы сказали в предыдущем комментарии.

Если у вас есть код, который вы хотите выполнить после этого, либо используйте предложение Ralph о локальной процедуре, либо завершите попытку. Наконец-то код в конечном итоге будет выполнен.

 Смежные вопросы

  • Нет связанных вопросов^_^