generic functions

Chris Nicholson-Sauls ibisbasenji at gmail.com
Fri Apr 27 06:20:11 PDT 2007


Frits van Bommel wrote:
> orgoton wrote:
>> I've been trying to create a function that would receive a single 
>> variable of any type, like a "abs" function, so that I won't have to 
>> code the same function for "real" and "long" var types. What's the 
>> most straightforward way to do it? I've seen templates at the D 
>> documentation, but those require me to instantiate the function. Is 
>> there anyway to bypass this?
> 
> No, I don't think there's a good way to bypass this. D is a statically 
> typed language, so a function needs to know the types of the arguments.
> 
> ---
> // Note: doesn't handle byte.min, short.min, int.min and
> // long.min correctly because their positive values don't
> // fit into the corresponding type... :(
> // (This could be fixed by having abs() return the unsigned
> // variant of those types, but I don't feel like typing
> // that much)
> T abs(T)(T val) { return val >= 0 ? val : -val; }
> ---

On the other hand, template functions with a single parameter like this are practically 
guaranteed IFTI (implicit function template instantiation) so he needn't explicitly 
instantiate it.  I think that may be enough for what he seems to be wanting.  So given the 
function above, 'abs(myvar)' will work just fine.

I'm also not sure if there's any way to account for the .min issue without writing the 
function as a member of a normal template and using a chain of static-if's.

template abs (T) {
        static if (is(T == byte )) alias ubyte  R;
   else static if (is(T == short)) alias ushort R;
   else static if (is(T == int  )) alias uint   R;
   else static if (is(T == long )) alias ulong  R;
   else                            alias T      R;

   R abs (T val) {
     static if (is(R : ulong)) const ZERO = 0_UL  ;
     else                      const ZERO = 0.0_L ;

     return val >= ZERO ? val : -val;
   }
}

Just a quick something, I make no claims toward perfection.  If he doesn't mind always 
returning a ulong, I'm sure he could replace all those static-if's with one 'static 
if(is(T:long))'.


-- Chris Nicholson-Sauls


More information about the Digitalmars-d-learn mailing list