Value Preservation and Polysemy

Andrei Alexandrescu SeeWebsiteForEmail at erdani.org
Mon Dec 1 12:51:08 PST 2008


Don wrote:
> Andrei Alexandrescu wrote:
>> I've had a talk with Walter today, and two interesting things transpired.
>>
>> First off, Walter pointed out that I was wrong about one conversion 
>> rule (google value preservation vs. type preservation). It turns out 
>> that everything that's unsigned and less than int is actually 
>> converted to int, NOT unsigned int as I thought. This is the case in 
>> C, C++, and D.
> 
> That has some interesting consequences.
> 
>   ushort x = 0xFFFF;
>   short y = x;
>   printf("%d %d %d\n", x>>1, y>>1, y>>>1);
> 
> // prints: 32767 -1 2147483647
> 
> What a curious beast the >>> operator is!
> 
>> I'm very excited about polysemy. It's entirely original to D, covers a 
>> class of problems that can't be addressed with any of the known 
>> techniques (subtyping, coercion...) and has a kick-ass name to boot. 
> 
> I agree. By making the type system looser in the one place where you 
> actually need it to be loose, you can tighten it everywhere else. 
> Fantastic.

My enthusiasm about polysemy got quite a bit lower when I realized that 
the promises of polysemy for integral operations can be provided (and 
actually outdone) by range analysis, a well-known method.

The way it's done: for each integral expression in the program assign 
two numbers: the smallest possible value, and the largest possible 
value. Literals will therefore have a salami-slice-thin range associated 
with them. Whenever code asks for a lossy implicit cast, check the range 
and if it fits within the target type, let the code go through.

Each operation computes its ranges from the range of its operands. The 
computation is operation-specific. For example, the range of a & b is 
max(a.range.min, b.range.min) to min(a.range.max, b.range.max). Sign 
considerations complicate this a bit, but not quite much.

The precision of range analysis can be quite impressive, for example:

uint b = ...;
ubyte a = ((b & 2) << 6) | (b >> 24);

typechecks no problem because it can prove no loss of information for 
all values of b.


Andrei



More information about the Digitalmars-d mailing list