D issues are now tracked on GitHub. This Bugzilla instance remains as a read-only archive.
Issue 1997 - Better type inference for templated types
Summary: Better type inference for templated types
Status: RESOLVED WONTFIX
Alias: None
Product: D
Classification: Unclassified
Component: dmd (show other issues)
Version: D2
Hardware: All All
: P2 enhancement
Assignee: No Owner
URL:
Keywords:
: 21106 (view as issue list)
Depends on:
Blocks:
 
Reported: 2008-04-15 19:36 UTC by Simen Kjaeraas
Modified: 2020-08-04 08:25 UTC (History)
2 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this issue.
Description Simen Kjaeraas 2008-04-15 19:36:24 UTC
In the following code, a shortcoming of current type inference is pointed out:

struct foo(T)
{
  T data;
  
  static foo!(T) opCall(T t)
  {
    foo!(T) result;
    result.data = t;
    return result;
  }
}

auto f = foo(4);

The line with 'f = foo(4)' gives a template instantiation error, while it should be possible for the compiler to infer the template parameters from the call.

auto g = foo!(int)(4);

This works, but is nowhere near as pretty.
Comment 1 Jesse Phillips 2010-03-10 08:46:35 UTC
DMD includes private methods when it tries to match for type inference even though the private function is not available.

.\test.d(10): Error: template bar.Bar(T) does not match any function template declaration
.\test.d(10): Error: template bar.Bar(T) cannot deduce template function from argument types !()(void delegate())

------------------
module bar;

import foo;

void Bar(T)(void delegate(T) call) {
}

void main() {
   auto foo = new Foo();
   Bar(&foo.fish);
}

------------------
module foo;

class Foo {
   private void fish() {
   }
   public void fish(string color) {
   }
}
Comment 2 Simen Kjaeraas 2011-09-16 08:17:12 UTC
It is worth noting here that the workaround is to use a free function:

struct Foo( T ) {
    T data;
    this( T value ) {
        data = value;
    }
}

Foo!T foo( T )( T value ) {
    return Foo!T( value );
}

void main( ) {
	foo( 4 );
}
Comment 3 Simen Kjaeraas 2017-06-28 08:58:11 UTC
This issue is not fixable in the general case - constructor arguments do not necessarily line up with type arguments. As pointed out above, the correct fix is to use a factory function.
Comment 4 Simen Kjaeraas 2020-08-04 08:25:01 UTC
*** Issue 21106 has been marked as a duplicate of this issue. ***