【问题标题】:Avoiding a circular reference in Delphi在 Delphi 中避免循环引用
【发布时间】:2011-07-05 08:09:08
【问题描述】:

我有一个名为 RCLowPass 的单元,它使用 Unit2。它使用对象 TForm2。

Unit2 也使用 RCLowPass。

Delphi 抱怨循环引用,因为一个模块需要另一个模块。

以下是相关单位的相关样本。

RCLowPass:

unit RCLowPass;

interface

uses
  ComplexMath, ExtraMath, Unit2;

procedure SelectRCLowPassFilter;

implementation

{ This is why I need Unit2. }
procedure SelectRCLowPassFilter;
begin
  // Setup form for RC Low Pass
  TForm2.Prop1Name.Caption := 'R1';
  TForm2.Prop1Name.Visible := true;
  TForm2.Prop2Name.Caption := 'C1';
  TForm2.Prop2Name.Visible := true;
  TForm2.Prop3Name.Visible := false;
  TForm2.Prop4Name.Visible := false;
  TForm2.Prop5Name.Visible := false;
  TForm2.Prop6Name.Visible := false;
  TForm2.Prop7Name.Visible := false;
  TForm2.Prop8Name.Visible := false;
  TForm2.Prop1Value.Visible := true;
  TForm2.Prop2Value.Visible := true;
  TForm2.Prop3Value.Visible := false;
  TForm2.Prop4Value.Visible := false;
  TForm2.Prop5Value.Visible := false;
  TForm2.Prop6Value.Visible := false;
  TForm2.Prop7Value.Visible := false;
  TForm2.Prop8Value.Visible := false;
end;

end.

单元2:

unit Unit2;

interface

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

var
  Form2: TForm2;

implementation

uses RCLowPass;

{$R *.dfm}

{ This is why I need RCLowPass. }
procedure TForm2.Button1Click(Sender: TObject);
var
  v : real;
begin
  ShowMessage('Output of RC lowpass with R=1k, C=100n');
  v := RCLowPassZAtFreq(1000, 100e-9, 10);
  ShowMessage('@10Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 10);
  ShowMessage('@20Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 20);
  ShowMessage('@50Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 50);
  ShowMessage('@100Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 100);
  ShowMessage('@200Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 200);
  ShowMessage('@500Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 500);
  ShowMessage('@1000Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 1000);
  ShowMessage('@2000Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 2000);
  ShowMessage('@5000Hz: ' + FormatFloat('#.########', v));
  v := RCLowPassZAtFreq(1000, 100e-9, 5000);
  ShowMessage('@10000Hz: ' + FormatFloat('#.########', v));
end;

procedure SelectFilter(filter : integer);
begin
  if filter = 0 then
    SelectRCLowPassFilter();
end;

end.

如何修复循环引用?

【问题讨论】:

  • 尝试将Unit2的使用中的RCLowPass单元移动到Unit2单元的实现部分。
  • 您的示例有缺陷,因为没有循环引用。由于您没有明确说明为什么在实际代码中RCLowPassRCLowPass 的接口部分使用Unit2,因此无法建议您。
  • @RRUZ 现在我得到:[DCC Error] RCLowPass.pas(29): E2096 Method identifier expected for TForm2.Prop1Name.Caption := 'R1' 和相关行。
  • @Thomas,这个问题太具体了,不知道以后会不会对别人有帮助。在 S.O 中存在更多关于 circular references 的一般问题,例如 stackoverflow.com/questions/2644973/…stackoverflow.com/questions/6579602/…,所以我认为如果你删除这个问题哪个更好:)
  • @Thomas 我强烈建议您将 UI 代码移出执行过滤器的 RCLowPass 单元,并将其全部保留在 Unit2 中。

标签: delphi


【解决方案1】:
unit RCLowPass;
interface

uses
  ComplexMath, ExtraMath;

procedure SelectRCLowPassFilter;

implementation
uses
  Unit2; // <<-- HERE

{ This is why I need Unit2. }
procedure SelectRCLowPassFilter;
begin
  // Setup form for RC Low Pass
  TForm2.Prop1Name.Caption := 'R1';
  TForm2.Prop1Name.Visible := true;
  ...

【讨论】:

  • 这个答案对我来说似乎很可疑。查看代码和名称,我希望带有低通滤波器的代码 RCLowPass 中没有 UI 代码。并且 Unit2 应该有对 RCLowPass 的引用,以及所有的 UI 代码。换句话说,RCLowPass 应该没有对 Unit2 的引用。
  • 不是答案,但代码是可疑的。首先不要以 RCLowPass 为单位设置特定的 Form。设置过滤器属性。
  • 在 unit2.TForm2 中设置一个 Filter 属性,该属性执行 SelectRCLowPassFilter。如果 SelectRCLowPassFilter 用于多个表单,则将过程设置为具有基本表单值的新单元。但是如果该过程只针对表单(unit2.TForm2),则将表单中的过程设置为私有。
  • 在unit2中RCLowPass被声明了两次,在实现使用中去掉
猜你喜欢
  • 1970-01-01
  • 2015-09-05
  • 1970-01-01
  • 1970-01-01
  • 2011-01-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多