![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Выполнится ли Beep ?
Ega23 © (2005-01-19 12:12:00)Сразу оговорюсь: то, что ТАК делать нельзя - я прекрасно понимаю. Сейчас как раз занимаюсь "перекраиванием" логики. Но вопрос, тем не менее, остался.
Имеется следующая ситуация:
if (SomeObject.SomeProperty) and (SomeFunction(SomeObject)) then Beep;
function SomeFunction(SomeObject:TSomeObject):Boolean;
begin
...
SomeObject.Free;
Result:=True;
end;
SomeObject.SomeProperty в условии - True.
Изменится ли выполнение условия, после выполнения SomeFunction?
Ega23 (2005-01-19 13:56:00) [1]2 Юрий Зотов © (19.01.05 13:52) [24]
Ну то, что я всё переделаю, это даже не обсуждается... :о)
Юрий Зотов (2005-01-19 13:52:00) [2]> Ega23 © (19.01.05 13:48) [23]
Но полагаться на это все равно не стоит. Компилятор, ясное дело, писали далеко не дураки, но ошибаются ведь и умные тоже.
Ega23 (2005-01-19 13:48:00) [3]2 Юрий Зотов © (19.01.05 13:45) [22]
Вполне исчерпывающе. Спасибо.
Юрий Зотов (2005-01-19 13:45:00) [4]Если компилятор писали не дураки (а в этом вряд ли стоит сомневаться), то в данном случае он должен вычислить выражение строго так, как оно написано, не пытаясь оптимизировать порядок вычислений.
Дело в том, что чтение свойства SomeProperty может приводить к вызову метода Get, в котором могут выполняться любые действия. А в результате этих действий состояние программы на момент вызова функции SomeFunction может измениться и повлиять на ее результат. Таким образом, результаты вычисления всего выражения по схемам "слева направо" и "справа налево" могут оказаться разными - и ни один компилятор не в состоянии определить, может ли такое произойти, или нет.
Это может определить только человек. А компилятор обязан полагать, что программист написал выражение именно так, как ему это нужно, и не вмешиваться.
Аналогичный пример:
var
A, i: integer;
procedure SetA;
begin
A := 0
end;
for i := 1 to 5 do A := 0;
for i := 1 to 5 do SetA;
Оба цикла делают, по сути, одно и то же. Но в первом случае оптимизатор может вынести инвариант за цикл, а затем и исключить сам цикл. Во втором же случае он не имеет права этого делать, потому что он все же не ИИ, и ему неизвестно, что делает процедура SetA.
Ega23 (2005-01-19 13:33:00) [5]глубинный смысл всего этого я так и не понял, поэтому интерпретирую требуемую тебе логику вот в таком варианте исправленного кода
Нет, ничего интерпретировать не надо, я всё совсем по-другому перекраивать буду.
Просто сам вопрос интересен был.
Digitman (2005-01-19 13:32:00) [6]пардон,
procedure SomeFunction( varSomeObject:TSomeObject);
Digitman (2005-01-19 13:29:00) [7]
> Ega23 © (19.01.05 13:19) [18]
ну вообще-то говоря насчет AND можно еще и порассуждать на тему порядка, а вот OR однозначно не подразумевает совпадение порядка.
глубинный смысл всего этого я так и не понял, поэтому интерпретирую требуемую тебе логику вот в таком варианте исправленного кода
if Assigned(SomeObject) and SomeObject.SomeProperty then
begin
SomeFunction(SomeObject);
Beep;
end;
procedure SomeFunction(SomeObject:TSomeObject);
begin
...
FreeAndNil(SomeObject);
end;
в рез-те никаких бипов не будет, если SomeObject на момент выполнения проверки еще/уже не существует
Ega23 (2005-01-19 13:19:00) [8]вообще говоря, мне непонятна конечная логика всего этого кода ..
Переделываю старую программу, получилась такая ситуация. Что так нельзя делать - понимаю.
к тому же полагаться на строго определенный (слева направо, как написано) порядок вычисления выражений в if-условии не следует - компилятор волен принимать эксклюзивное решение, в каком порядке производить вычисление выражений в этом условии ..
Вот. Собственно, именно это и хотел услышать. Т.е. необязательно сначала первое, потом второе и т.д. условия...
Digitman (2005-01-19 13:10:00) [9]
> Да, но вычисление SomeObject.SomeProperty стоит ДО вычисления
> SomeFunction
да, но ты же говоришь что перед этим как минимум однократно ф-ция SomeFunction уже выполнилась !
вообще говоря, мне непонятна конечная логика всего этого кода ..
к тому же полагаться на строго определенный (слева направо, как написано) порядок вычисления выражений в if-условии не следует - компилятор волен принимать эксклюзивное решение, в каком порядке производить вычисление выражений в этом условии .. так что исключение вполне может произойти и на строчке SomeObject.Free, если компилятор примет решение первым делом вычислить выражение SomeFunction(SomeObject), а не SomeObject.SomeProperty
Ega23 (2005-01-19 13:07:00) [10]Понял, спасибо.
default (2005-01-19 13:04:00) [11]Digitman © (19.01.05 12:59) [12]
"полагаться на это не следует"
само собой
Ega32 имел ввиду [9]
Ega23 © (19.01.05 12:48) [11]
"Изменится ли выполнение условия, после выполнения SomeFunction?"
нет
Ega23 (2005-01-19 13:01:00) [12]а как получить св-во уже несуществующего объекта ? ты же убил его собственными руками при первом же вызове SomeFunction !
Да, но вычисление SomeObject.SomeProperty стоит ДО вычисления SomeFunction
Ega23 (2005-01-19 13:01:00) [13]а как получить св-во уже несуществующего объекта ? ты же убил его собственными руками при первом же вызове SomeFunction !
Да, но вычисление SomeObject.SomeProperty стоит ДО вычисления SomeFunction
Digitman (2005-01-19 12:59:00) [14]
> default © (19.01.05 12:33) [6]
> врял-ли будет исключение
> дело в том что память объекта как минимум не затирается
полагаться на это не следует
> Ega23 © (19.01.05 12:36) [8]
> Т.е., насколько я тебя понял, логическое вычисление будет
> производиться дважды?
о каком вычислении ты говоришь ? вычиcлении всего выражении, стоящего в if ?
сколько раз на if-оператор будет передано управление, столько раз и вычисляться будет if-условие
но для того чтобы вычислить условие, заданное тобой в if-операторе, компилятору нужно первым делом получить зн-е св-ва SomeObject.SomeProperty.. а как получить св-во уже несуществующего объекта ? ты же убил его собственными руками при первом же вызове SomeFunction !
Ega23 (2005-01-19 12:48:00) [15]для этого нужно максимум минуты две, а прошло уже как минимум 24
Блин, у нас электричество каждые 5 минут отрубают - электрики что-то химичат. Я кроме Mozillы ничего и не запускаю...
default (2005-01-19 12:37:00) [16]Ega23 © (19.01.05 12:36) [8]
посмотри окно CPU и всё
для этого нужно максимум минуты две, а прошло уже как минимум 24
Ega23 (2005-01-19 12:37:00) [17]Да, забыл сказать: операция сравнения выполняется ОДНОКРАТНО. Второго вхождения в неё уже нет.
Ega23 (2005-01-19 12:36:00) [18]2 Digitman © (19.01.05 12:29) [5]
Т.е., насколько я тебя понял, логическое вычисление будет производиться дважды?
Как я себе представляю данный процесс:
1. Вычисляем первый операнд. Получаем истину.
2. Записываем значение первого операнда в ячейку памяти.
3. Вычисляем второй операнд. Получаем истину. При этом "грохаем" первый операнд.
4. Записываем значение второго операнда в ячейку памяти.
5. Сравниваем 2 ячейки памяти, получаем истину, выполняем Beep.
Будут ли предприняты какие-то действия между 4-м и 5-м пунктами? Зависит ли это от компиллятора?
default (2005-01-19 12:36:00) [19]+ [6]
конечно, всё зависит от времени между проверками условий
вообщем от случая(если проверки идут не через маленькие куски времени)
строго же говорить что будет исключение неверно
default (2005-01-19 12:33:00) [20]Digitman © (19.01.05 12:29) [5]
врял-ли будет исключение
дело в том что память объекта как минимум не затирается
весь код и данные остаются в прежнем состоянии
именно поэтому я упомянул про nil