www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - template auto instantiation when parameters empty

reply Erik Smith <erik cruiserhouse.com> writes:
I want to have a struct template auto instantiate when the 
template parameters are defaulted or missing.  Example:

struct Resource(T=int) {
     static auto create() {return Resource(null);}
     this(string s) {}
}

auto resource = Resource.create;

As a plain struct it works, but not as a template:

struct Resource {   // works
struct Resource() {  // fails
struct Resource(T=int) {  // fails

At the call site, this works, but I'm hoping for a few less 
symbols:

auto resource = Resource!().create;

Any ideas?
May 04 2016
next sibling parent Andrea Fontana <nospam example.com> writes:
On Wednesday, 4 May 2016 at 22:10:16 UTC, Erik Smith wrote:
 Any ideas?
Using an alias could be a solution.
May 05 2016
prev sibling parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 5/5/16 12:10 AM, Erik Smith wrote:
 I want to have a struct template auto instantiate when the template
 parameters are defaulted or missing.  Example:

 struct Resource(T=int) {
      static auto create() {return Resource(null);}
      this(string s) {}
 }

 auto resource = Resource.create;

 As a plain struct it works, but not as a template:

 struct Resource {   // works
 struct Resource() {  // fails
 struct Resource(T=int) {  // fails

 At the call site, this works, but I'm hoping for a few less symbols:

 auto resource = Resource!().create;

 Any ideas?
Instead of static method, use an external factory method: static auto createResource(T = int)() { return Resource!T(null); } And I wouldn't bother with making Resource's T have a default, as you'd still have to instantiate it with Resource!() to get the default. -Steve
May 05 2016
parent reply Erik Smith <erik cruiserhouse.com> writes:
On Thursday, 5 May 2016 at 16:12:40 UTC, Steven Schveighoffer 
wrote:
 On 5/5/16 12:10 AM, Erik Smith wrote:
 I want to have a struct template auto instantiate when the 
 template
 parameters are defaulted or missing.  Example:

 struct Resource(T=int) {
      static auto create() {return Resource(null);}
      this(string s) {}
 }

 auto resource = Resource.create;

 As a plain struct it works, but not as a template:

 struct Resource {   // works
 struct Resource() {  // fails
 struct Resource(T=int) {  // fails

 At the call site, this works, but I'm hoping for a few less 
 symbols:

 auto resource = Resource!().create;

 Any ideas?
Instead of static method, use an external factory method: static auto createResource(T = int)() { return Resource!T(null); } And I wouldn't bother with making Resource's T have a default, as you'd still have to instantiate it with Resource!() to get the default. -Steve
Alias works at the cost of adding a 2nd type name: alias Res = Resource!(); auto res = Res.create The other problem is that the alias definition by itself instantiates, which I can't afford. I have createResource() now, it just doesn't fit well with the rest of the calling styles. There is also this approach, which might be slightly more idiomatic struct Resource(T) {} struct Policy {} auto create(alias T)() { T!Policy r; return r; } auto r = create!Resource;
May 05 2016
parent reply Steven Schveighoffer <schveiguy yahoo.com> writes:
On 5/5/16 6:50 PM, Erik Smith wrote:
 Alias works at the cost of adding a 2nd type name:

 alias Res = Resource!();
 auto res  = Res.create

 The other problem is that the alias definition by itself instantiates,
 which I can't afford.

 I have createResource() now, it just doesn't fit well with the rest of
 the calling styles.

 There is also this approach, which might be slightly more idiomatic

 struct Resource(T) {}
 struct Policy {}

 auto create(alias T)() {
      T!Policy r;
      return r;
 }

 auto r = create!Resource;
I believe factory external IFTI functions are quite idiomatic. They are all over phobos. -Steve
May 05 2016
parent Jonathan M Davis via Digitalmars-d-learn writes:
On Thursday, May 05, 2016 19:09:01 Steven Schveighoffer via Digitalmars-d-
learn wrote:
 On 5/5/16 6:50 PM, Erik Smith wrote:
 Alias works at the cost of adding a 2nd type name:

 alias Res = Resource!();
 auto res  = Res.create

 The other problem is that the alias definition by itself instantiates,
 which I can't afford.

 I have createResource() now, it just doesn't fit well with the rest of
 the calling styles.

 There is also this approach, which might be slightly more idiomatic

 struct Resource(T) {}
 struct Policy {}

 auto create(alias T)() {

      T!Policy r;
      return r;

 }

 auto r = create!Resource;
I believe factory external IFTI functions are quite idiomatic. They are all over phobos.
When dealing with the creation of objects that are templatized, they're often practically required for using the object to be sane - particularly when the constructor itself needs to be further templatized. And since IFTI only works with functions, if you want something similar with templated types, wrapping the construction in a function to get IFTI is pretty much your only option if you want to avoid requiring explicit instantiations. - Jonathan M Davis
May 08 2016