Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2002.09.26;
Скачать: [xml.tar.bz2];

Вниз

Вспомнить все. Или есть ли у компилятара память.   Найти похожие ветки 

 
id_privin   (2002-09-14 13:52) [0]

Такие вот грабли. Есть два модуля Unit1 просто форма проекта, и Unit2 тут зарыты грабли.

unit Unit2;

interface

uses ComObj,Dialogs,Classes;

type

ParentI = interface
procedure FuckYou; <<
end;

ChildI = interface(ParentI)
procedure WOW;
end;

ChildImpl = class(TInterfacedObject,ChildI)
procedure FuckYou; <<
procedure WOW;
end;

TParent = class(TInterfacedObject,ParentI)
protected
I : ParentI;
public
property A : ParentI read I implements ParentI;
end;

TChild = class(TParent)
public
constructor Create;
end;

implementation

procedure ChildImpl.FuckYou; <<
begin <<
MessageDlg("Fuck You", mtWarning, [], 0); <<
end; <<

procedure ChildImpl.WOW;
begin
MessageDlg("WOW", mtInformation, [mbOK], 0);
end;


constructor TChild.Create;
begin
inherited Create;
I := ParentI(ChildI(ChildImpl.Create));
end;

end.


===========

unit Unit1;

interface
uses
Forms, Classes, Controls, StdCtrls;
type
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
end;
var
Form1: TForm1;

implementation

uses Unit2;

{$R *.DFM}
procedure TForm1.Button1Click(Sender: TObject);
var
P : TParent;
begin
P := TChild.Create;
ChildI(ParentI(P)).WOW; <<<ГРАБЛИ ТУТ >>>
P.Free;
end;

end.


Так вот, если все писать по порядку т.е. сначала Unit2 а потом процедуру в Unit1 то на месте граблей компилятор говорит
Internal Error E 1289

Тогда делаю так, в Unit2 убираю все что связанно с процедурой FuckYou(сторочки помечены << ). Компилирую - все ок. Вставляю строчки обратно - все ок. В том месте где грабли ставлю вместо WOW FuckYou - опять E1289. Снова убираю строки из Unit2. Получаю сообщение что идентификатор не определенн. Вставляю строки. Компилирую - все ок.

Вопросы. Лечиться ли это? У меня ли одного такие грабли? Может я просто тормоз, и чего то делаю не так как задумал Inprise;


 
Fog   (2002-09-14 13:59) [1]

Может не надо ругаться на компилятор, и он не заметит :)


 
drpass   (2002-09-14 15:34) [2]

Подозреваю, что такой программный изврат авторам компилятора просто и присниться не мог


 
Immortal Deach   (2002-09-14 21:42) [3]

да, скорее, это не ты сильно мудрый, а компил. сильно тебя не понимающий....


 
id_privin   (2002-09-16 10:35) [4]

Эти неврахумительные посты, - это все что могут сказать мастаки?

Тогда поставим вопрос по другому,

Есть ли еще варианты реализации шаблонов в Delphi?


 
Separator   (2002-09-16 10:46) [5]

Попробуй удалить *.dcu и по новой откомпилировать


 
Shaman_Naydak   (2002-09-16 11:24) [6]

Родной, сделай так:
После ParentI = interface
и до процедуры вставь строчку и нажми Shift-Ctrl-G, чтобы сгенерировать гуид. Аналогичную операцию проверни у наследуемого интерфейса, и пребудет с тобой счастье.
Ты ж гуиды не задал, и компилятор физически не может отличить интерфейсы..
Пошли дальше.. Настоятельно не рекомендую использовать
явное приведение типов с интерфейсами.. Это идея больна на голову.
Например, вместо
ChildI(ParentI(P)).WOW; <<<ГРАБЛИ ТУТ >>>
лучше сделать так: (P as ChildI).WOW;

Удачи в нелегких извратах


 
id_privin   (2002-09-16 12:01) [7]

Вау спасибо, действительно ГУИД надо писать, а я думал это только Com"у нужно.

А вот второй совет не работает если писать P as ChildI то в run time будет Interface not Supported. Если оставить как есть будет Internal erorror. А вот ((P as ParentI) as ChildI) работает.

Насколько я теперь понял as c интерфейсами работает только если есть GUID? да?


 
id_privin   (2002-09-16 12:11) [8]

хмм. В тестовом проекте все зароботало, но вот в настоящем, все по прежнему. Несмотря на GUID оператор as не работает. При двойном приведении по прежнему Internal error. Может дело в том что интерфейсы объявлены в пакетах, причем в разных?


 
Shaman_Naydak   (2002-09-16 13:07) [9]

да, все интерфейсы надо снабжать guid"aми..
Так как все сводится к QueryInterface, а он без гуида как-то не работает..
Ты прав. Только ((P as ParentI) as ChildI) даст требуемый результат.
Но хочу обратить твое внимание на распространенную ошибку, возникающую при смешивании объектного и интерфейсного подхода:
procedure TForm1.Button1Click(Sender: TObject);
var
P: TParent;
begin
P:=TChild.Create;
((P as ParentI) as ChildI).WOW; // после этой строчки объект уже будет автоматически освобожден
P.Free; // тут ты уже второй раз освобождаешь этот же объект
end;
Наилучшим способом решения этого затруднения является использование только интерфейсной модели:
procedure TForm1.Button1Click(Sender: TObject);
var
P: ParentI;
begin
P:=TChild.Create;
(P as ChildI).WOW;
end;
Объект автоматически уничтожится при выходе из области видимости..

Пойдем дальше, или вернее смотрим еще выше:
ChildImpl = class(TInterfacedObject,ChildI)
procedure FuckYou;
procedure WOW;
end;
Так как ты рассчитываешь работать с ним не через СhildI, а через ParentI, то было бы правильнее определить так:
ChildImpl = class(TInterfacedObject, ParentI, ChildI)
procedure FuckYou;
procedure WOW;
end;
Никаких дополнительных усилий для реализации родительского интерфейса, само-собой, не требуется..

И следующая строка тоже примет человеческий вид:
constructor TChild.Create;
begin
inherited Create;
// I := ParentI(ChildI(ChildImpl.Create));
I:=ChildImpl.Create;
end;

Нет, пакеты влиять не должны.. Где-то ошибка.. Ищи.
Если не справишься, кинь письмом, гляну.




Страницы: 1 вся ветка

Форум: "Основная";
Текущий архив: 2002.09.26;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.47 MB
Время: 0.009 c
4-85741
GROL
2002-08-06 09:28
2002.09.26
ListView от DeskTop


3-85374
delphiwhat
2002-09-05 10:28
2002.09.26
Вопрос про базу (*.db) и Delphi6. Помогите понять.


14-85683
zxas
2002-09-01 20:39
2002.09.26
Документация по ADO


1-85602
Ag2002
2002-09-14 12:13
2002.09.26
TreeView


1-85525
Ина
2002-09-13 11:38
2002.09.26
шрифт Terminal, dbf (foxpro)





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский