Eiffel: недействительная безопасность, краткий способ проверить, существует ли объект, а затем вызвать его функцию.

Мне было интересно, есть ли более четкое утверждение, чем

if not attached foo then
    create foo
end
if attached foo as l_foo then
    l_foo.bark
end

as

if not attached foo then
    create foo
    foo.bark
else
    foo.bark
end

будет повторять foo.bark, и, очевидно, я хочу этого избежать... и даже последний оператор не будет скомпилирован с недействительной безопасностью, поскольку foo on else может быть недействительным...


person Pipo    schedule 24.01.2019    source источник


Ответы (1)


Чтобы избежать дублирования кода и множественных тестов, можно использовать следующий код:

l_foo := foo
if not attached l_foo then
    create l_foo
    foo := l_foo
end
l_foo.bark
person Alexander Kogtenkov    schedule 24.01.2019
comment
А l_foo — это локальная переменная, объявленная как l_foo: like foo. - person Eric Bezault; 25.01.2019
comment
Есть ли причина, по которой компилятор не может увидеть, что объект был создан несколькими строками выше? Проверяет ли проверка создания объекта на компиляторе не только оператор if, но и содержимое оператора if, если тест включает случай, отличный от Void? Спасибо - person Pipo; 25.01.2019
comment
@Pipo Не совсем понятно, о чем вы спрашиваете, поэтому, я полагаю, вы ссылаетесь на второй пример своего исходного вопроса. Причина, по которой компилятор сообщает о вызовах foo.bark как небезопасных, заключается в том, что в параллельной среде другой поток может изменить foo на Void до того, как текущий поток сможет выполнить вызов. Если атрибут всегда меняется с Void на прикрепленный, его можно пометить как stable, тогда код будет скомпилирован. - person Alexander Kogtenkov; 25.01.2019