Проблема обработки исключений в Delphi с несколькими блоками обработки исключений - PullRequest
7 голосов
/ 01 апреля 2010

Я использую Delphi Pro 6 в Windows XP с FastMM 4.92 и JEDI JVCL 3.0. Учитывая приведенный ниже код, у меня возникла следующая проблема: только первый блок обработки исключений получает действительный экземпляр E. Другие блоки правильно соответствуют классу возбуждаемого исключения, но E не назначено (nil).

Например, учитывая текущий порядок блоков обработки исключений, когда я поднимаю E1, блок для E1 совпадает, а E является допустимым экземпляром объекта. Однако, если я пытаюсь поднять E2, этот блок совпадает, но E не назначен (ноль). Если я переместлю блок захвата E2 в верхнюю часть ордера и подниму E1, то, когда блок E1 совпадает с E, теперь не назначается. С этим новым порядком, если я подниму E2, E назначается правильно, когда этого не было, когда блок E2 не был первым блоком в порядке. Обратите внимание, что я попробовал этот случай с голым проектом, состоящим только из одной формы Delphi.

Я здесь что-то действительно глупо делаю или что-то не так?

Спасибо, Роберт

type
    E1 = class(EAbort)
    end;

    E2 = class(EAbort)
    end;


procedure TForm1.Button1Click(Sender: TObject);
begin
    try
        raise E1.Create('hello');
    except
        On E: E1 do
        begin
            OutputDebugString('E1');
        end;

        On E: E2 do
        begin
            OutputDebugString('E2');
        end;

        On E: Exception do
        begin
            OutputDebugString('E(all)');
        end;
    end; // try()
end;

1 Ответ

8 голосов
/ 01 апреля 2010

Если я прав, то поведение, которое вы видите, засвидетельствовано при оценке E под отладчиком (это я получил аналогичное поведение, проверяя это в отладчике BDS 2006).

Это ошибка разрешения символов в отладчике, но она не влияет на поведение во время выполнения.

Если важно поведение при отладке, просто переименуйте переменные вашего обработчика исключений, чтобы у отладчика не было (потенциальных) неопределенностей, которые нужно было бы устранить:

On E1: E1 do
begin
    OutputDebugString('E1');
end;

On E2: E2 do
begin
    OutputDebugString('E2');
end;

On Ex: Exception do
begin
    OutputDebugString('E(all)');
end;
...