custom attribute proposal (yeah, another one)

Piotr Szturmaj bncrbme at jadamspam.pl
Fri Apr 6 15:40:29 PDT 2012


Steven Schveighoffer wrote:
> On Fri, 06 Apr 2012 15:03:39 -0400, Piotr Szturmaj
> <bncrbme at jadamspam.pl> wrote:
>
>> Steven Schveighoffer wrote:
>
>>> What if I have 20 string attributes, I must define a new attribute type
>>> for each one? This seems like unneeded bloat.
>>
>> I don't see advantage of functions here, twenty of them is also a
>> bloat. Different types give you different _names_ for different
>> purposes. Those _names_ are crucial to support the attributes.
>
> Unused function do not make it into the EXE.

Are unused structs compiled into EXE?

>> How do you get list of all attributes with your function based
>> proposal? You can get a string attribute but you don't know which
>> function generated it. You don't know if it was serializable, author
>> or whatever.
>
> foreach(name, value; __traits(getAttributes, symbol)) {...}
>
> hereby added to the proposal.

Ok, but how do you filter that and pass the result to another template? 
It should be easy if __traits(getAttributes, symbol) would return an 
expression tuple, which is what I'd like to see.

>>> BTW, if I wasn't trying to demonstrate that you could store structs, I
>>> would have written:
>>>
>>> @attrubte string author(string name) { return name;}
>>>
>>> and save the extra bloat associated with declaring another type. Maybe
>>> we could even get this someday:
>>
>> As above, declaring another function is also a bloat.
>
> No, it doesn't generate more typeinfo that must go into the EXE. When
> the EXE is built, all associated bloat should disappear, it's only
> needed during compilation.

Those types are only needed during compilation too. However, I don't 
know if they're always included into binary or only when they're used.

>>> @attribute author(string name) => name;
>>>
>>> I just don't see the need to declare a type that can wrap a string.
>>>
>>> You could even add this rule:
>>>
>>> if @attribute is placed on a struct, its constructor becomes an
>>> @attribute qualified function with the name of the struct as the
>>> attribute name.
>>
>> Consider struct constructors as equivalent of functions proposed by
>> you. Here you declare a type, there you declare a function. They're
>> very similar, besides that struct type _describes_ the attribute. A
>> function on the other side just returns a value, which doesn't have
>> any name attached to it.
>
> The name is the function. You seem to be arguing the equivalent of:
>
> "int x is useless. It should really just be int. If you need another
> integer field, make a new type that's just like int, how hard is that?"
>
> Yeah, I know it's a strawman, but this is seriously how it sounds to me ;)

If you have simple attributes in mind, like name = string value, then 
yes, but most attributes are not that simple. Most of the time you will 
be forced to create a struct anyway (and return it from function).

>>> It's an example. you can choose any type you want! I actually just want
>>> the name of the author, I don't care whether that's a struct, or a
>>> string.
>>
>> Yes, but my point is that you get a bool and you don't know which of
>> the functions returned it, as many of them can return bool.
>
> I think you are missing how the metadata is stored as key-value pairs,
> with the key being the name of the function that was used.

Ok, but it needs more work in the compiler, comparing to identifier 
search and remembering expression tuple of a symbol. Also, I just found 
a major drawback of this approach: consider parameterless attributes 
like @NotNull. What would you return from function named NotNull()?

>>> Any CTFE computed value should suffice.
>>
>> I think that list of attributes should be a list of user defined
>> types. You can always write a function to construct them, but anyway
>> you get named user defined type (like struct). Named type easily
>> disambiguates between different attributes without resorting to
>> name-value solutions.
>
> Again, see point above about not naming variables.
>
>> This is how it's done in C# by the way.
>
> Yes I know. I don't think we need to limit ourselves this way, C# does
> not have the compile-time power that D does.

I didn't state that we shouldn't use compile-time :)


More information about the Digitalmars-d mailing list