为什么在执行下面的代码时会引发EAccessViolation?
uses Generics.Collections; ... var list: TList; ... begin list := TList .Create(); try list.Add(myNotifyEvent); list.Remove(myNotifyEvent); // EAccessViolation at address... finally FreeAndNil(list); end; end; procedure myNotifyEvent(Sender: TObject); begin OutputDebugString('event'); // nebo cokoliv jineho end;
Toon Krijthe.. 5
它看起来像一个bug.
如果使用debug dcu进行编译(通常不要这样做,除非你想要失去理智!)你会看到对比较器的调用出错了.未设置比较函数的(可能是可选的)第三个值并导致访问冲突.
因此,您可能无法将方法指针放在通用列表中.
好的以下工作:
uses Generics.Defaults; type TForm4 = class(TForm) ... private procedure myNotifyEvent(Sender: TObject); end; TComparer= class (TInterfacedObject, IComparer ) public function Compare(const Left, Right: T): Integer; end; implementation uses Generics.Collections; var list: TList ; begin list := TList .Create(TComparer .Create); try list.Add(myNotifyEvent); list.Remove(myNotifyEvent); finally FreeAndNil(list); end; end; procedure TForm4.myNotifyEvent(Sender: TObject); begin ShowMessage('event'); end; { TComparer } function TComparer .Compare(const Left, Right: T): Integer; begin Result := 0; end;
你必须定义自己的比较器,可能有更多的智能;-).
它看起来像一个bug.
如果使用debug dcu进行编译(通常不要这样做,除非你想要失去理智!)你会看到对比较器的调用出错了.未设置比较函数的(可能是可选的)第三个值并导致访问冲突.
因此,您可能无法将方法指针放在通用列表中.
好的以下工作:
uses Generics.Defaults; type TForm4 = class(TForm) ... private procedure myNotifyEvent(Sender: TObject); end; TComparer= class (TInterfacedObject, IComparer ) public function Compare(const Left, Right: T): Integer; end; implementation uses Generics.Collections; var list: TList ; begin list := TList .Create(TComparer .Create); try list.Add(myNotifyEvent); list.Remove(myNotifyEvent); finally FreeAndNil(list); end; end; procedure TForm4.myNotifyEvent(Sender: TObject); begin ShowMessage('event'); end; { TComparer } function TComparer .Compare(const Left, Right: T): Integer; begin Result := 0; end;
你必须定义自己的比较器,可能有更多的智能;-).