int/long
compare always works. The 2 operands are converted to a common type, in this case long
and all int
can be converted to long
with no problems.
int ii = ...;
long ll = ...;
if (ii < ll)
doSomethings();
unsigned/long
compare always works if long
ranges exceeds unsigned
. If unsigned
range was [0...65535]
and long
was [-2G...2G-1]
, then the operands are converted to long
and all unsigned
can be converted to long
with no problems.
unsigned uu16 = ...;
long ll32 = ...;
if (uu16 < ll32)
doSomethings();
unsigned/long
compare has trouble when long
ranges does not exceed unsigned
. If unsigned
range was [0...4G-1]
and long
was [-2G...2G-1]
, then the operands are converted to long
, a common type that does not encompass both ranges and problems ensue.
unsigned uu32 = ...;
long ll32 = ...;
// problems
if (uu32 < ll32)
doSomethings();
// corrected solution
if (uu32 <= LONG_MAX && uu32 < ll32)
doSomethings();
// wrong solution
if (ll32 < 0 || uu32 < ll32)
doSomethings();
If type long long
includes all the range of unsigned
, code could use do the compare with at least long long
width.
unsigned uu;
long ll;
#if LONG_MAX >= UINT_MAX
if (uu < ll)
#if LLONG_MAX >= UINT_MAX
if (uu < ll*1LL)
#else
if (uu32 <= LONG_MAX && uu32 < ll32)
// if (ll < 0 || uu < ll)
#endif
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…