问题
Consider the following code:
namespace ConsoleApplication1 {
class Program
{
static void Main(string[] args)
{
Console.WriteLine(100.CompareTo(200)); // prints -1
Console.WriteLine(((decimal)100).CompareTo((decimal)200)); // prints -1
Console.WriteLine(((short)100).CompareTo((short)200)); // prints -100
Console.WriteLine(((float)100).CompareTo((float)200)); // prints -1
Console.ReadKey();
}
}
}
My question is, are there any specific reasons the CompareTo-method on Int16 returns values other than -1, 0 and 1?
ILSpy shows it is implemented this way
public int CompareTo(short value)
{
return (int)(this - value);
}
whereas the method is implented on Int32 this way
public int CompareTo(int value)
{
if (this < value)
{
return -1;
}
if (this > value)
{
return 1;
}
return 0;
}
回答1:
The difference is that for short
, there's no chance of the result overflowing. For instance, short.MinValue - (short) 1
is still negative - whereas int.MinValue - 1
is int.MaxValue
.
In other words, the specific reason is that you can get away with a shortcut with short
(no pun intended) whereas the same shortcut doesn't work with int
. You should definitely not require IComparable<T>.CompareTo implementations to return -1, 0 or 1. The documentation is pretty clear that the result is only meaningful in terms of being negative, zero, or positive.
回答2:
Well, you should only really check the sign anyway, but for reasons: I guess for int
etc there would be a risk of overflow/wrap (when handling 2 large-magnitude numbers) that would reverse the sign, meaning it must check the operators.
I'd rather it was consistent, but it doesn't seem to be a problem. More likely an optimisation that is atypical but within the documented API. In particular, optimising short
here doesn't feel like it is going to get a massive amount of use (I use short
, but not anything like as much as I do int
).
来源:https://stackoverflow.com/questions/6579966/why-is-compareto-on-short-implemented-this-way