Why does D not have generics?

Bruce Carneal bcarneal at gmail.com
Sat Jan 16 17:03:41 UTC 2021


On Saturday, 16 January 2021 at 09:28:22 UTC, Ola Fosheim Grøstad 
wrote:
> On Saturday, 16 January 2021 at 08:45:23 UTC, Ola Fosheim 
> Grøstad wrote:
>> Maybe I am overlooking something... This is like 1-2 cycles.
>
> I haven't tested, so I could be in error, but it seems like 
> these two might work?
>
> ulong x = floatingpoint double value;
>
> 1: x ^ ((0ULL - (x>>63)) | (1ULL<63))
>
> or
>
> 2: x & (1ULL<63) ? ~x : x | (1ULL<63)
>
>
> So basically in generic assembly:
>
> 1:  shift right, sub, or, xor  => 4 very fast ops
>
> 2:  tst, cmp, (neg / or) => 2 fast ops + 1 branch
>
> If this works, then there is really no reason not to use 
> ulong/uint for floating point keys, except -0.0 and 0.0 will be 
> sorted, but that is desirable sometimes, so could be a plus as 
> well. If people don't want that then they should normalize to 
> 0.0 before using the key.

Here's a link on the topic: http://stereopsis.com/radix.html.  
Excerpts from that for the 32 bit float case follow:

Converting over:
	uint32 mask = -int32(f >> 31) | 0x80000000;
	return f ^ mask;
and back:
	uint32 mask = ((f >> 31) - 1) | 0x80000000;
	return f ^ mask;

This form is branchless and is easily (SIMD) vectorized.

As you've noted, there are some oddities that arise when using 
unsigned relops against the mapped values.  Negative and positive 
zeroes are distinct and NaNs take on a definite, and split, 
ordering.  For my current work I prefer this to traditional float 
behavior and find it a useful bijection overall.  YMMV.







More information about the Digitalmars-d mailing list