could someone explain to me what is the reason that when creating a generic class I must move my private constans to the interface section? This is killing my design, I don't want others to see something that should be private.
unit Unit38;
interface
uses
Generics.Collections;
type
TSimpleClass<T> = class(TObject)
private
procedure DoSomethingInternal(const SomeString: string);
public
procedure DoSomething;
end;
implementation
const
MyString = 'some string'; //Why this must be public?
{ TSimpleClass<T> }
procedure TSimpleClass<T>.DoSomething;
begin
DoSomethingInternal(MyString); //Compiler error
end;
procedure TSimpleClass<T>.DoSomethingInternal(const SomeString: string);
begin
//-------
end;
end.
Thanks.
Same error in D2010, so the generics fixes of D2010 did not address this. It is a bug: http://qc.embarcadero.com/wc/qcmain.aspx?d=79747
Fixed in build 15.0.3863.33207. Which I think is XE
Another QC on this is: http://qc.embarcadero.com/wc/qcmain.aspx?d=78022 which involves an enum and is still open.
The documentation on the error isn't very clear by the way. See:
E2506 Method of parameterized type declared in interface section must not use local symbol '%s'
It involves a class var in a generic class which cannot be assigned a literal (!) value in the class' constructor, the fix being to parameretrize the constructor... No idea why, but I guess it has to do with a compiler limitation.
It's a consequence of the generics implementation in Delphi. When you instantiate a class by supplying a concrete T in another unit, code for the concrete class is written into that other unit. But that other unit can no longer see your private string constant. It's rather frustrating.
My understanding of the generics implementation suggests that Mikael's workaround will solve the problem because the class const will be visible when you instantiate your concrete type in another unit.
Not an answer but a possible workaround could be to use private const in the class declaration.
TSimpleClass<T> = class(TObject)
private
procedure DoSomethingInternal(const SomeString: string);
const MyString = 'some string'; //Why this must be public?
public
procedure DoSomething;
end;
This works in Delphi 2010, XE and XE2, not in Delphi 2009.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With