![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
В чём отличие статического связывания и виртульного?
MegaVolt © (2004-08-26 15:38:00)Какая разница когда прога проведёт определение адреса по которому нужно идти. Тем более статическое связывание как я понимаю быстрее. Зачем тогда применяется виртуальное переопределение?
DiamondShark (2004-08-27 13:17:00) [1]Блин... А ведь хороший токарь мог бы быть.
MegaVolt (2004-08-26 17:26:00) [2]Спасибо :)
jack128 (2004-08-26 17:21:00) [3]
> Так? Я правильно понял?
да, правильно.
MegaVolt (2004-08-26 17:11:00) [4]что то типа такого?
TDev = class
procedure Test1;
procedure Test2; virtual;
end;
TDev1 = class(TDev)
procedure Test1;
procedure Test2; override;
end;
TDev2 = class(TDev)
procedure Test1;
procedure Test2; override;
end;
procedure TDev.Test1;
begin
ShowMessage('TDev.Test1');
end;
procedure TDev.Test2;
begin
ShowMessage('TDev.Test2');
end;
procedure TDev1.Test1;
begin
ShowMessage('TDev1.Test1');
end;
procedure TDev1.Test2;
begin
ShowMessage('TDev1.Test2');
end;
procedure TDev2.Test1;
begin
ShowMessage('TDev2.Test1');
end;
procedure TDev2.Test2;
begin
ShowMessage('TDev2.Test2');
end;
procedure TForm1.Button1Click(Sender: TObject);
var
D:TDev;
D1:TDev1;
D2:TDev2;
begin
D:=TDev.Create;
D1 := TDev1.Create;
D2 := TDev2.Create;
D.Test1; //TDev.Test1
D.Test2; //TDev.Test2
D1.Test1; //TDev1.Test1
D1.Test2; //TDev1.Test2
D2.Test1; //TDev2.Test1
D2.Test2; //TDev2.Test2
D.Free;
D:=D1;
D.Test1; //TDev.Test1
D.Test2; //TDev1.Test2
D:=D2;
D.Test1; //TDev.Test1
D.Test2; //TDev2.Test2
D1.Free;
D2.Free;
end;
И в результатае получаем что для виртуального метода мы получим вызов процедуры из метода потомка а для статического метод предка. Так? Я правильно понял?
jack128 (2004-08-26 16:49:00) [5]
> Статические методы тоже можно перекрыть в потомке,
Фактически это создание нового метода с тем же именем..
Amoeba (2004-08-26 16:49:00) [6]Адреса статических методов определяются еще на стадии компиляции.
Адреса же виртуальных (а также и динамических) методов определяются только на стадии выполнения программы (они берутся из VMT - таблицы виртуальных методов класса).
GuAV (2004-08-26 16:45:00) [7]
> В книге они запросто перекрывали конструктор в потомке и
> он вызывался.
В примере VMcL © мы не знаем класс, когда вызываем test1/test2, но знаем когда создаём, поэтому конструктор статический. Виртуальный нужен, когда мы не знаем заранее что создавать будем.
Читай d?dlr.hlp
Amoeba (2004-08-26 16:45:00) [8]
> MegaVolt (26.08.04 16:38) [13]
Читай литературу! Тогда и распутаешься. Никто тебе в форуме не будет писать целую статью. Так, чтобы все стало понятно в нескольких словах не ответить.
P.S. Статические методы тоже можно перекрыть в потомке, но директива override не применяется.
MegaVolt (2004-08-26 16:40:00) [9]А про единичку согласен лишняя. Это я описался. Так есть литературка. Я вьехать не могу. Но похоже начинаю понимать.
MegaVolt (2004-08-26 16:38:00) [10]Так я совсем запутался. В книге они запросто перекрывали конструктор в потомке и он вызывался. Или конструктор чем то отличается?
Amoeba (2004-08-26 16:37:00) [11]
> TDevice=Class
> procedure Vkl; Virtual;
> end;
>
> TDevice1=Class(TDevice);
> procedure Vkl1; Override;
> end;
Ерунда! Компилятор такой код обматерит. У предков TDevice1 нет виртуального метода Vkl1, который ты пытаешься перекрыть. Должно быть тогда уж
procedure Vkl; Override;
или
procedure Vkl1; virtual;
А вообще, как уже настоятельно советовали, читай "букварь". Кстати, на сайте Анатолия Подгорецкого полно хорошей литературы в электронном виде.
Гаврила (2004-08-26 16:36:00) [12]Если ты заранее знаешь, какой у тебя реально созданный экземпляр класса, используй статические методы, если не знаешь, а знаешь только, что это один из потомков базового класса - используй виртуальные - будет вызван метод того класса, который реально создан
MegaVolt (2004-08-26 16:28:00) [13]Т.е. получается что я в потомке не могу перекрыть статический метод? Так что ли?
MegaVolt (2004-08-26 16:21:00) [14]Люди подскажите.
вот код:
TDevice=Class
procedure Vkl;
end;
TDevice1=Class(TDevice);
procedure Vkl1;
end;
или
TDevice=Class
procedure Vkl; Virtual;
end;
TDevice1=Class(TDevice);
procedure Vkl1; Override;
end;
VMcL (2004-08-26 16:18:00) [15]>> MegaVolt (26.08.04 15:55) [7]
type
TDaddy = class
procedure Test1;
procedure Test2; virtual;
end;
TSon = class(TDaddy)
procedure Test1;
procedure Test2; override;
end;
procedure TDaddy.Test1;
begin
ShowMessage('TDaddy.Test1');
end;
procedure TDaddy.Test2;
begin
ShowMessage('TDaddy.Test2');
end;
procedure TSon.Test1;
begin
ShowMessage('TSon.Test1');
end;
procedure TSon.Test2;
begin
ShowMessage('TSon.Test2');
end;
procedure TForm1.Button1Click(Sender: TObject);
var
D, S: TDaddy;
begin
D := TDaddy.Create;
try
S := TSon.Create;
try
D.Test1;
D.Test2;
S.Test1;
S.Test2;
finally
S.Free;
end;
finally
D.Free;
end;
end;
P.S. Общие вопросы нужно в книгах вычитывать, а не на форум с ними ломиться.
MegaVolt (2004-08-26 15:55:00) [16]Поставлю вопрос по другому. Что изменится если я перекрою статический метод и виртуальный? И там и там я смогу достучатся как до предка так и до потомка. И там и там я могу присваивать несколько классов переменной типа предка. В чём фишка?
default (2004-08-26 15:53:00) [17]для гибкости
полиморфизм обеспечивает работу с разными сущностями единообразно
MegaVolt (2004-08-26 15:52:00) [18]Я почитал но так и не просёк :( Там сказано что позволяет работать с класами о которых на момент разработки базового не было извесно. Чесно говоря это я не совсем понял :(
jack128 (2004-08-26 15:51:00) [19]любая книга по любому ОО - языку..
MegaVolt (2004-08-26 15:48:00) [20]Я имел в виду статические и виртуальные методы.