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

Вниз

ошибка Circular unit reference   Найти похожие ветки 

 
kilya ©   (2007-07-03 14:14) [0]

Здравствуйте. Вот такая проблема - Дельфи не дает двум модулям видеть друг друга, вроде с помощью директив это должно исправляться, сделал их даже в двух вариантах, но  Дельфи все равно не пропускает.
-------------- Unit1 ----------------
{$IFNDEF flag1}
{$DEFINE flag1}
unit Map;
interface
uses Graphics, Windows {$IFNDEF flag2}, Unit2{$ENDIF};
...
{$ENDIF}

-------------- Unit2 ----------------
{$IFNDEF flag2}
{$DEFINE flag2}
unit Unit2;
interface
{$IFNDEF flag1}uses Unit1;{$ENDIF}
...
{$ENDIF}

Выдается ошибка [Fatal Error] Unit1.pas: Circular unit reference to "Unit1"


 
Johnmen ©   (2007-07-03 14:21) [1]

Circular unit reference + F1


 
Dimaxx ©   (2007-07-03 14:25) [2]

А без DEFINE нормально работает? И зачем нужны они? Пусть себе ссылки на модули работают постоянно, а не только при наличии флагов.


 
Сергей М. ©   (2007-07-03 14:26) [3]


> Дельфи не дает двум модулям видеть друг друга


Не вижу здесь никакого "друг друга".

Задумано тобой так - либо первый использует второй, либо второй использует первый, в зависимости от определенности flag1 или flag2.

Но flag1 не видим за пределами Unit2, а flag2 - соответственно за пределами Гтше1. Оттого и проблема.

Решается просто - убираются директивы DEFINE, а flag1 или flag2 указываются в conditional defines на уровне проекта в целом (см. свойства проекта)

т.е.

-------------- Unit1 ----------------
..
uses .. {$IFNDEF flag2}, Unit2{$ENDIF};
...

-------------- Unit2 ----------------
{$IFNDEF flag1}uses Unit1;{$ENDIF}


 
Gydvin ©   (2007-07-03 14:28) [4]

А так

unit Unit1;

interface

uses
 Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
 Dialogs, StdCtrls;

type
 TForm1 = class(TForm)
   Button1: TButton;
   procedure Button1Click(Sender: TObject);
 private
   { Private declarations }
 public
   { Public declarations }
 end;

var
 Form1: TForm1;

implementation
uses
  unit3;


{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
 MyCoolProcedure;
end;

end.

unit Unit3;
interface
uses
 Windows;

  procedure MyCoolProcedure;

implementation

 uses unit1;

 procedure MyCoolProcedure;
 begin
    form1.Caption:="ddd";
 end;
end.


 
kilya ©   (2007-07-03 14:35) [5]

в интерфейсе unit1 описан класс, использующий Unit2, а в интерфейсе unit2 описан класс, используюший unit1. Если uses ставить а Implementetion, не прокатывает


 
Германн ©   (2007-07-03 14:39) [6]


> kilya ©   (03.07.07 14:35) [5]
>
> в интерфейсе unit1 описан класс, использующий Unit2, а в
> интерфейсе unit2 описан класс, используюший unit1.

Облом. :(
Хотя бы одно из этих описаний вынеси в третий модуль. Или объедини оба модуля в один, если это возможно.


 
Gydvin ©   (2007-07-03 14:50) [7]

unit Unit1;

interface

uses
 Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
 Dialogs, unit2, StdCtrls;

type
 TForm1 = class(TForm)
   Button1: TButton;
   procedure Button1Click(Sender: TObject);
 private
   { Private declarations }
 public
   { Public declarations }
 end;

var
 Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
 a: class_1;
begin
 a := class_1.create;
 a.Free;
end;

end.

------------------------

unit Unit2;

interface
uses
 windows;

type
 class_1 = class
 private
 public
   constructor create;

 end;
type
 class_3 = class
 private
 public
   procedure mess_1;
   constructor create;

 end;

implementation
uses
 unit3;
{ class_1 }

constructor class_1.create;
var
 a: class_2;
begin
 a := class_2.create;
 a.mess_2;
 a.Free;
end;

{ class_3 }

constructor class_3.create;
begin
///
end;

procedure class_3.mess_1;
begin
 MessageboxA(0, "1", "", 0);
end;

end.

-----------------------------------------------

unit Unit3;
interface
uses
 windows;

type
 class_2 = class
 private
 public
   constructor create;
   procedure mess_2;
 end;

implementation
uses
 unit2;
{ class_2 }

constructor class_2.create;
var
 a: class_3;
begin
 a := class_3.create;
 a.mess_1;
 a.Free;
end;

procedure class_2.mess_2;
begin
 MessageboxA(0, "2", "", 0);
end;

end.

-------------------------------------------


Что я делаю не так?  unit2 и unit3 "видят друг друга


 
kilya ©   (2007-07-03 15:01) [8]


> Что я делаю не так?  unit2 и unit3 "видят друг друга

------------------------
unit Unit2;

interface
uses uni3;

type
class_1 = class
    parent: class_2;
end;
...
---------------
unit Unit3;
interface
uses Unit2
type
 field: class_1;
end;
...
--------------


 
Gydvin ©   (2007-07-03 15:18) [9]

и те?

unit Unit2;
interface
uses windows;
type
class_1=class
public
procedure mess;
end;
implementation
uses
unit3;

procedure bbb;
var
a:class_2;
begin
a:=class_2.Create;
end;

{ class_1 }

procedure class_1.mess;
begin
messageboxa(0,"1","",0);
end;

end.

--------------------

unit Unit3;
interface

uses windows, unit2;

type
class_2=class
field: class_1;
public
procedure mess ;
end;
implementation

{ class_2 }

procedure class_2.mess;
begin
field:=class_1.Create;
field.mess;
field.Free;
messageboxa(0,"2","",0);
end;

end.


 
kilya ©   (2007-07-03 15:30) [10]

ухх, сорри, пропустил строчку
------------------------
unit Unit2;

interface
uses uni3;

type
class_1 = class
   parent: class_2;
end;
...

---------------

unit Unit3;
interface
uses Unit2
type
class_2 = class         // вот эту
field: class_1;
end;
...

--------------


> и те?

в твоем классе class_1 добавь поле типа class_2


 
Gydvin ©   (2007-07-03 15:40) [11]

Ух ты какой хитрый )))

У тя в любом случае ничего не выйдет. Классы ссылаясь друг на друга создавали бы бесконечное множество экземпляров друг друга в геометрической прогресии, Что в конечном итоге вызовет оут оф мемори.
Во всяком случае мастера, возможно, более точно опишут эту ситуевину, или поправят меня, еслия не прав.


 
Плохиш ©   (2007-07-03 15:41) [12]


> kilya ©   (03.07.07 14:35) [5]
> в интерфейсе unit1 описан класс, использующий Unit2, а в
> интерфейсе unit2 описан класс, используюший unit1. Если
> uses ставить а Implementetion, не прокатывает

Рекомендую поменять консерваторию...


 
kilya ©   (2007-07-03 15:50) [13]


> Классы ссылаясь друг на друга создавали бы бесконечное множество
> экземпляров

насколько я понимаю, описывая field: TClass никаких экземпляров не создается, т.к. field хранит всего лишь адрес, а не сам объект (помоему в Делфи так, в отличии от c++)


 
kilya ©   (2007-07-03 16:15) [14]


> Решается просто - убираются директивы DEFINE, а flag1 или
> flag2 указываются в conditional defines на уровне проекта
> в целом (см. свойства проекта)

не получается что-то так :(
Наверное в делфи так незя :((


 
Сергей М. ©   (2007-07-03 16:23) [15]


> Наверное в делфи так незя


Чего "незя" ?

Изволь выражаться конкретнее и понятнее ...


 
kilya ©   (2007-07-03 16:31) [16]


> Изволь выражаться конкретнее и понятнее ...

в uses"ы интерфесов двух модулей указывать включение друг друга


 
Сергей М. ©   (2007-07-03 16:39) [17]


> в uses"ы интерфесов двух модулей указывать включение друг
> друга
>


Да, это действительно "незя".

А оно и нафих не нужно, да и, судя по примеру кода, содержащего условные дефиниции, преследовал ты явно иные цели.

А ограничение циркулярной ссылки с легкостью снимается разносом uses-ссылок по разделам interface и implementation.


 
kilya ©   (2007-07-03 17:53) [18]

Сергей М., ну скажи мне, как ты тут разнесешь uses-ссылки?

unit Unit1; // главный модуль приложения
interface
uses unit2;
...
--------------------------------
unit Unit2;
interface
uses uni3;
type
  class_1 = class // класс, содержащий объект класса class_2
     field: class_2;
  end;
...
---------------
unit Unit3;
interface
uses Unit2;
type
  class_2 = class
     parent: class_1; // адрес родителя class_1
  end;
...
--------------


 
Сергей М. ©   (2007-07-04 08:28) [19]

А так ли уж необходима глобальная область видимости обоих идентификаторов - class_1 и class_2 ?

Если нужна, то почему не поместить их декларацию в интерфейсный раздел одного и того же юнита ?

Если не нужна, то почему не поместить декларацию одного из идентификаторов в раздел имплементации соотв.юнита и сослаться на юнит с декларацией другого идентификатора в uses раздела имплементации этого юнита, т.е. понизить область видимости одного из идентификаторов до локальной ?


 
kilya ©   (2007-07-04 13:32) [20]

> А так ли уж необходима глобальная область видимости обоих
> идентификаторов - class_1 и class_2 ?

Нужна
> Если нужна, то почему не поместить их декларацию в интерфейсный
> раздел одного и того же юнита ?

Хорошо все в одном интерфейсе:

 class_1=class
    field: class_2;
 end;
 class_2=class
    parent:class_1;
 end;


Так класс class_1  тоже не видит класс class_2 :)
Вот так чтоли сделать?:

 TNewtype = ^class_2;
 class_1=class
    field: TNewtype;
 end;
 class_2=class
    parent:class_1;
 end;

Так видит :/


 
Плохиш ©   (2007-07-04 13:34) [21]


> kilya ©   (04.07.07 13:32) [20]


>  TNewtype = ^class_2;
>  class_1=class
>     field: TNewtype;
>  end;
>  class_2=class
>     parent:class_1;
>  end;

Афигенное знание основ :-(

class_2=class;
class_1=class
   field: TNewtype;
end;
class_2=class
   parent:class_1;
end;


 
Плохиш ©   (2007-07-04 13:35) [22]

TNewtype --> class_2


 
kilya ©   (2007-07-04 14:19) [23]

гы )))



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

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

Наверх




Память: 0.51 MB
Время: 0.04 c
15-1182947588
TruePunk
2007-06-27 16:33
2007.07.29
wap ресурсы


15-1182915959
Pohil
2007-06-27 07:45
2007.07.29
Есть здесь абаперы?


8-1162468735
toboom
2006-11-02 14:58
2007.07.29
Проблема использования таймера из MMSystem


5-1158053164
demonnnn
2006-09-12 13:26
2007.07.29
тут вобще в создании компонентов кто нибудь понимает


15-1181868630
Ш-К
2007-06-15 04:50
2007.07.29
Как подключиться к компьютеру в локальной сети?





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
Английский Французский Немецкий Итальянский Португальский Русский Испанский