## digitalmars.D - T.zero and T.one for numeric types

• Biotronic (26/26) Apr 17 2015 I've been writing a lot of generic code lately that has to deal
• Adam D. Ruppe (13/15) Apr 17 2015 Does foo(T(0)); work? It seems like it should
• Biotronic (3/19) Apr 17 2015 Man, that actually does work. I guess I've become too used to it
• ketmar (2/8) Apr 17 2015 Omens.sixsixsix...=
• w0rp (10/36) Apr 17 2015 This can be implemented via a library without requiring any
"Biotronic" <simen.kjaras gmail.com> writes:
```I've been writing a lot of generic code lately that has to deal
with various kinds of numbers, and have near been driven nuts by
the fact there is no uniform way to get a zero or one.

Consider:

void foo(T)(T a) {}

foo!T(0);

Does this work with all built-in numeric types? Yes.
Does it work with T=BigInt or Complex!float? No.

Now, those are a limited set of possibilities, and one could
easily enough create a template such that

foo!BigInt(zero!BigInt);

would work. But why can't I instead, for every numeric type,
simply write

foo(BigInt.zero);
foo(float.one);
foo(Complex!float.zero);
foo(Rational!BigInt.one);
foo(Meters.zero);

?

This would also work for strong typedefs and units of
measurement, where simply assigning 0 to a variable might not
work (because it lacks the correct unit).

It's a very simple change, both in the compiler and Phobos, and I
could have a pull request ready tomorrow.

--
Simen
```
Apr 17 2015
"Adam D. Ruppe" <destructionator gmail.com> writes:
```On Friday, 17 April 2015 at 13:27:19 UTC, Biotronic wrote:
void foo(T)(T a) {}

foo!T(0);

Does foo(T(0)); work? It seems like it should

void foo(T)(T a) {}
import std.bigint;
import std.complex;
void main() {
foo(BigInt(0));
foo(float(0));
foo(int(0));
foo(Complex!float(0));
}

as of one of the newish dmds, T(n) works to construct basic types
too.
```
Apr 17 2015
"Biotronic" <simen.kjaras gmail.com> writes:
```On Friday, 17 April 2015 at 13:33:36 UTC, Adam D. Ruppe wrote:
On Friday, 17 April 2015 at 13:27:19 UTC, Biotronic wrote:
void foo(T)(T a) {}

foo!T(0);

Does foo(T(0)); work? It seems like it should

void foo(T)(T a) {}
import std.bigint;
import std.complex;
void main() {
foo(BigInt(0));
foo(float(0));
foo(int(0));
foo(Complex!float(0));
}

as of one of the newish dmds, T(n) works to construct basic
types too.

Man, that actually does work. I guess I've become too used to it
not. Sorry about the noise then, and thanks!
```
Apr 17 2015
ketmar <ketmar ketmar.no-ip.org> writes:
```On Fri, 17 Apr 2015 13:27:18 +0000, Biotronic wrote:

would work. But why can't I instead, for every numeric type, simply
write
=20
foo(BigInt.zero); foo(float.one); foo(Complex!float.zero);
foo(Rational!BigInt.one);
foo(Meters.zero);

Omens.sixsixsix...=
```
Apr 17 2015
"w0rp" <devw0rp gmail.com> writes:
```On Friday, 17 April 2015 at 13:27:19 UTC, Biotronic wrote:
I've been writing a lot of generic code lately that has to deal
with various kinds of numbers, and have near been driven nuts
by the fact there is no uniform way to get a zero or one.

Consider:

void foo(T)(T a) {}

foo!T(0);

Does this work with all built-in numeric types? Yes.
Does it work with T=BigInt or Complex!float? No.

Now, those are a limited set of possibilities, and one could
easily enough create a template such that

foo!BigInt(zero!BigInt);

would work. But why can't I instead, for every numeric type,
simply write

foo(BigInt.zero);
foo(float.one);
foo(Complex!float.zero);
foo(Rational!BigInt.one);
foo(Meters.zero);

?

This would also work for strong typedefs and units of
measurement, where simply assigning 0 to a variable might not
work (because it lacks the correct unit).

It's a very simple change, both in the compiler and Phobos, and
I could have a pull request ready tomorrow.

--
Simen

This can be implemented via a library without requiring any
changes to the language. It would look like Zero!T or One!T
instead. You create a value template for it.

When you are writing less generic code, you can commit to zero or
one in certain types via the prefixes. 1L, 1, 1.0, 1.0f. There's
nothing for short or byte, but you can do short(1), byte(1). You
can also write T(1) or T(0) to get a numeric type T with the
value 0 or 1. That might be better than a template, I haven't
tried it.
```
Apr 17 2015