On Friday, 1 December 2017 at 03:39:12 UTC, helxi wrote:
1. Template specialisation.
Why is this useful?:
T getResponse(T = int)(string question); And how does it differ
from
int getResponse(string question); ?
Because you can change the T at the call site. Let me give you a
real world example from my cgi.d
docs:
http://dpldocs.info/experimental-docs/arsd.cgi.Cgi.request.html
source:
https://github.com/adamdruppe/arsd/blob/master/cgi.d#L2057
In the doc example, you'll see:
int a = cgi.request("number", 10);
You can also do:
string name = cgi.request("name");
or something kinda crazy like:
float number = cgi.request!float("brightness");
In the first case, it uses the passed param - 10 - to infer the
type of T you want returned. It sees 10 is an int, so it tries to
convert the value from the URL to an int and return it.
The second case uses the default parameter, described in the link
you gave. The default here is (T = string), so if you don't
specify anything else, it simply returns a string.
The third case shows explicit passing of a new type, instead of
using the default T = string, we get T = float, so the function
converts the value from URL to float and returns that.
All three of these uses are supported by the code.
2. "Generic locking".
Is it possible to specialise templates for a certain group of
types? For example
auto fn(T)(T arg)
auto fn(T : int, double, float, ulong)(T arg); //shares same
behaviour
auto fn(T : char, string, dchar, wchar, dstring, wstring)(T
arg); // shares same behavior
Yeah, that is possible.
class Stack(T)
{
private:
T[] data;
public:
this(T)(T[] data){ /*..*/}
this(T)(){}
//...
}
void main()
{
auto s = new Stack!int;
}
Says:
Error: template app.Stack!int.Stack.__ctor cannot deduce
function from argument types !()(), candidates are:
source/app.d(6,2): app.Stack!int.Stack.__ctor(T)(T[]
data)
source/app.d(9,2): app.Stack!int.Stack.__ctor(T)()
Why is Stack!int a ctor()() instead of a ctor(int)()?
You passed int to the Stack(T) template, but not to the this(T)
template. There's two levels there, the outer argument and the
inner argument.
It is the same as if you did a
void delegate(int) returns_a_function(int);
if you called
returns_a_function(0), it would still return the delegate. If you
want to call both, you need another set of params to pass an
argument to the returned function, too.