[fpc-pascal] with in classes/records

Michael Van Canneyt michael at freepascal.org
Mon Sep 3 11:14:25 CEST 2018

On Mon, 3 Sep 2018, Ryan Joseph wrote:

>> On Sep 3, 2018, at 2:41 PM, Michael Van Canneyt <michael at freepascal.org> wrote:
>> 'with' is terribly awkward.
> “with” came to mind because it’s basically a with statement but within a
> class.  Properties had another side effect of requiring naming which is
> redundant (I’d probably just underscore the name always by default to
> prevent thinking).

I strongly feel that preventing thinking is an insult for any intelligent person.

We're not "input monkeys" after all.

> I just learned about the management operator issue recently but my initial interest was for any number of properties to be added and thus “default” didn’t make lots of sense in my mind.
> Properties also didn’t make sense to me because they’re always “read", i.e. “write" doesn’t make sense given the context (write would always be an ambiguous statement).

Properties can be read/write/readwrite as the use case dictates.

> Doesn’t that look kind of redundant? The plus side is at least they get to hook into the property symbol class.
> type
> TMyRec = record
>   delegateA: TSomeManager;
>   delegateB: TOtherManager;
>   property _delegateA: T read delegateA; default;
>   property _delegateB: T read delegateB; default;
> end;

Obviously, only 1 default property should be allowed. Be it an array array or not.

Allowing multiple defaults will wreak havoc on precedence rules:
The order of property declarations would suddenly matter and that would of course be terribly wrong.
So that will certainly not be accepted.

The compiler could perfectly decide to reorder fields in a class if it thinks this is better
for alignment issues or whatnot.

But your example explains why you wanted to call it 'with', I fear that this would be
something very different from the "default" which Maciej had in mind,
although both result in similar possibilities.

My preference definitely goes to Maciej's idea, which allows for much less ambiguity.

Hence, only 1 default property.

>> If it needs to be done, please use 'default', it is in line with the default array property.
> In my first tests I found that indeed “default" was used for array
> properties and the modifier “default” was kind of tangled up for arrays. 
> What is the thinking behind “default” for array properties anyways?  I
> always add it because the compiler requires it but there’s probably more
> to it than that.

?? Default is not required at all. It's only required if you want to write
instead of

> So yeah, the default keyword appeared to be reserved for arrays in the code so I wanted to make sure that’s really the correct approach.

It really is.

>> I suggest you only allow it on properties, not on fields. In the case of records, this will automatically imply the use of advanced records, and would prohibit it on classical records.
> Not sure what you mean exactly. Not sure how it would look on field.s

Same as on a property ?

A = Record
   f : Tfield; Default;

I would not allow this.

>> Make sure you establish precedence rules correctly. The default should only be
>> searched after all other properties/fields were handled.
>> TA = Class
>>  B : Integer;
>> end;
>> TB = record
>> Private
>>  FA : TA;
>> Public
>>  Property A : TA Read FA Write FA; default;
>>  B : Integer;
>> end;
>> Var
>>  C : TB;
>> begin
>>  C.B // Must refer to TB.B, not C.A.B
>> end.
>> I'm sure there are other pitfalls.
> You’re right, no doubt about pitfalls depending on how it works.
> In my first naive test I just did some extra searches in searchsym_in_record and added a csubscriptnode node if a match was found. That works for records but I didn’t try to make generics work. Because this only works with classes/records I think it only makes sense for the property to be “read” right? All it does it basically takes:
> C.B := 100
> and expands it to 
> C.FA.B := 100
> by adding the “FA” subscript node
> if the property was write it would imply:
> C := someA;
> The context of the property “B” is “C” so “write" means assigning to “C” right? That obviously doesn’t make sense.

It depends on type compatibility.

if C and someA are assignment compatible types, then the above will just assign
SomeA to C.

If C and someA are not assigment compatible types, then the compiler can
look for a default property (not an array) which is assignment compatible
with someA, and transform it to


You could decide to make this process recursive, but I would advise against
it, it will most likely have many unwanted side effects.

>>> 2) If there is any plausible way the compiler team will allow this I’m
>>> willing to develop it myself to what every specification the team decides. I already looked into how this could be implemented and did some tests. It’s not complicated and within the range of something I could accomplish.
>> Patches are always plausible.
>> Just dive in and ask questions. Help will surely be provided. When you feel you're done, provide a patch. It will be considered like all
>> other patches.
> Great news! I think there’s still some controversy ahead though about how to implement this.

No doubt - see above - but most of us are grown-up adults and can handle controversy in a civilized manner.


More information about the fpc-pascal mailing list