Thread overview | ||||||||||
---|---|---|---|---|---|---|---|---|---|---|
|
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
On 2012-39-05 09:12, Gor Gyolchanyan <gor.f.gyolchanyan@gmail.com> wrote: > Consider this piece of code: > > struct Test > { > template member(Type) > { > Type member; > } > } > > unittest > { > Test test; > test.member!int = 0; > test.member!long = 0; > test.member!short = 0; > import std.stdio; writeln(test.sizeof); > assert(test.sizeof == int.sizeof + long.sizeof + short.sizeof); // fails > assert(test.sizeof == 1); // succeeds > } > > I don't get why the structure's size remains unchanged even after > instantiating 3 members inside it. > How can I get the real size of the structure, including all its members > (template or not)? You have. Its real size is 1, and the template instantiations are not member fields. A template (not a templated function [actually, sorta, but that's a different discussion]) is basically static - if you try instead Test.member!int, you will see that this works perfectly. What we see here is another example of the confusion that can be caused by static names being accessible through an instance: struct Foo { static int n; } Foo f; f.n = 4; -- Simen |
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
Attachments:
| But why aren't they non-static members? If they were non-static members the structure's size would still be compile-time, computed by the sum of sizes of all template instances. the .sizeof would work perfectly well. This would be an incredibly useful feature. Among other use cases this would allow having a fully type-safe and very fast Variant type: struct Variant { public: TypeInfo type() @property { return _type; } ref Type_ as(Type_)() @property { if(typeid(Type_) != _type) throw new Exception("The requested static type doesn't match the available dynamic type."); return _value!Type_; } private: TypeInfo _type; union { template _value(Type_) { Type_ _value; } } } Is there any good reason why this feature wouldn't be a good idea? On Wed, Dec 5, 2012 at 12:51 PM, Simen Kjaeraas <simen.kjaras@gmail.com>wrote: > On 2012-39-05 09:12, Gor Gyolchanyan <gor.f.gyolchanyan@gmail.com> wrote: > > Consider this piece of code: >> >> struct Test >> { >> template member(Type) >> { >> Type member; >> } >> } >> >> unittest >> { >> Test test; >> test.member!int = 0; >> test.member!long = 0; >> test.member!short = 0; >> import std.stdio; writeln(test.sizeof); >> assert(test.sizeof == int.sizeof + long.sizeof + short.sizeof); // fails >> assert(test.sizeof == 1); // succeeds >> } >> >> I don't get why the structure's size remains unchanged even after >> instantiating 3 members inside it. >> How can I get the real size of the structure, including all its members >> (template or not)? >> > > You have. Its real size is 1, and the template instantiations are not > member > fields. > > A template (not a templated function [actually, sorta, but that's a > different > discussion]) is basically static - if you try instead Test.member!int, you > will see that this works perfectly. > > What we see here is another example of the confusion that can be caused by static names being accessible through an instance: > > struct Foo { > static int n; > } > > Foo f; > > f.n = 4; > > -- > Simen > -- Bye, Gor Gyolchanyan. |
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
Attachments:
| Sorry, that was wrong. This is right: struct Variant { public: TypeInfo type() @property { return _type; } ref Type_ as(Type_)() @property { if(typeid(Type_) != _type) throw new Exception("The requested static type doesn't match the available dynamic type."); return _value!Type_; } ref Variant opAssign(Type_)(Type_ value_) { _type = typeid(Type_); _value!Type_ = value_; return this; } private: TypeInfo _type; union { template _value(Type_) { Type_ _value; } } } On Wed, Dec 5, 2012 at 1:06 PM, Gor Gyolchanyan <gor.f.gyolchanyan@gmail.com > wrote: > But why aren't they non-static members? If they were non-static members the structure's size would still be compile-time, computed by the sum of sizes of all template instances. the .sizeof would work perfectly well. This would be an incredibly useful feature. Among other use cases this would allow having a fully type-safe and very fast Variant type: > > struct Variant > { > public: > TypeInfo type() @property > { > return _type; > } > ref Type_ as(Type_)() @property > { > if(typeid(Type_) != _type) > throw new Exception("The requested static type doesn't match the > available dynamic type."); > return _value!Type_; > } > private: > TypeInfo _type; > > union > { > template _value(Type_) > { > Type_ _value; > } > } > } > > Is there any good reason why this feature wouldn't be a good idea? > > > On Wed, Dec 5, 2012 at 12:51 PM, Simen Kjaeraas <simen.kjaras@gmail.com>wrote: > >> On 2012-39-05 09:12, Gor Gyolchanyan <gor.f.gyolchanyan@gmail.com> wrote: >> >> Consider this piece of code: >>> >>> struct Test >>> { >>> template member(Type) >>> { >>> Type member; >>> } >>> } >>> >>> unittest >>> { >>> Test test; >>> test.member!int = 0; >>> test.member!long = 0; >>> test.member!short = 0; >>> import std.stdio; writeln(test.sizeof); >>> assert(test.sizeof == int.sizeof + long.sizeof + short.sizeof); // fails >>> assert(test.sizeof == 1); // succeeds >>> } >>> >>> I don't get why the structure's size remains unchanged even after >>> instantiating 3 members inside it. >>> How can I get the real size of the structure, including all its members >>> (template or not)? >>> >> >> You have. Its real size is 1, and the template instantiations are not >> member >> fields. >> >> A template (not a templated function [actually, sorta, but that's a >> different >> discussion]) is basically static - if you try instead Test.member!int, you >> will see that this works perfectly. >> >> What we see here is another example of the confusion that can be caused by static names being accessible through an instance: >> >> struct Foo { >> static int n; >> } >> >> Foo f; >> >> f.n = 4; >> >> -- >> Simen >> > > > > -- > Bye, > Gor Gyolchanyan. > -- Bye, Gor Gyolchanyan. |
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Simen Kjaeraas | On 12/05/2012 09:51 AM, Simen Kjaeraas wrote:
> On 2012-39-05 09:12, Gor Gyolchanyan <gor.f.gyolchanyan@gmail.com> wrote:
>
>> Consider this piece of code:
>>
>> struct Test
>> {
>> template member(Type)
>> {
>> Type member;
>> }
>> }
>>
>> unittest
>> {
>> Test test;
>> test.member!int = 0;
>> test.member!long = 0;
>> test.member!short = 0;
>> import std.stdio; writeln(test.sizeof);
>> assert(test.sizeof == int.sizeof + long.sizeof + short.sizeof); // fails
>> assert(test.sizeof == 1); // succeeds
>> }
>>
>> I don't get why the structure's size remains unchanged even after
>> instantiating 3 members inside it.
>> How can I get the real size of the structure, including all its members
>> (template or not)?
>
> You have. Its real size is 1, and the template instantiations are not
> member
> fields.
>
> A template (not a templated function [actually, sorta, but that's a
> different
> discussion]) is basically static - if you try instead Test.member!int, you
> will see that this works perfectly.
>
> What we see here is another example of the confusion that can be caused by
> static names being accessible through an instance:
>
> struct Foo {
> static int n;
> }
>
> Foo f;
>
> f.n = 4;
>
> --
> Simen
The confusion is caused by implicitly marking fields static during template instantiation instead of failing compilation.
|
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Gor Gyolchanyan | On 12/05/2012 10:06 AM, Gor Gyolchanyan wrote:
> ...
>
> Is there any good reason why this feature wouldn't be a good idea?
> ...
Determining the size of a struct instance would require knowledge about all the code that uses the struct declaration.
|
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Timon Gehr Attachments:
| Aren't the template instances generated at the place of the template? The external code would instantiate the template, adding the instance information to the structure. Then the sizeof would just read the set of instantiated templates. This wouldn't require knowing about the code which instantiates the template. The only requirement would be to compute the size of the structure AFTER all template instances are generated. The only limitation would be that separate compilation passes could generate different structures due to different template instances, but that's not a problem, because the static templates go through the same limitation. On Wed, Dec 5, 2012 at 1:11 PM, Timon Gehr <timon.gehr@gmx.ch> wrote: > On 12/05/2012 10:06 AM, Gor Gyolchanyan wrote: > >> ... >> >> >> Is there any good reason why this feature wouldn't be a good idea? ... >> > > Determining the size of a struct instance would require knowledge about all the code that uses the struct declaration. > -- Bye, Gor Gyolchanyan. |
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
On 2012-43-05 10:12, Gor Gyolchanyan <gor.f.gyolchanyan@gmail.com> wrote: > Aren't the template instances generated at the place of the template? > The external code would instantiate the template, adding the instance > information to the structure. > Then the sizeof would just read the set of instantiated templates. > This wouldn't require knowing about the code which instantiates the > template. > The only requirement would be to compute the size of the structure AFTER > all template instances are generated. > The only limitation would be that separate compilation passes could > generate different structures due to different template instances, but > that's not a problem, because the static templates go through the same > limitation. How is that not a problem? The static templates get the same mangled name, and thus dupes can be removed by the linker. If a type has variable size, how is one to know that size - be it for argument passing/returning purposes, array creation, or whatever. -- Simen |
December 05, 2012 Re: Where are the template members? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Timon Gehr | On 2012-09-05 10:12, Timon Gehr <timon.gehr@gmx.ch> wrote: > The confusion is caused by implicitly marking fields static during template instantiation instead of failing compilation. That is certainly a valid complaint. -- Simen |
Copyright © 1999-2021 by the D Language Foundation