Questo perché 0x89678456543454345934
è maggiore di std::numeric_limits<unsigned_int>::max()
. Tuttavia, i tipi unsigned
racchiudono il loro valore massimo, quindi se il lato destro è rappresentabile da un tipo intero hai un comportamento ben definito. In tal caso il risultato è 0x89678456543454345934
mod std::numeric_limits<unsigned_int>::max
.
EDIT
Il lato destro del tuo incarico è un integer literal. Per rappresentarlo, il compilatore usa il primo tipo (ordinato in base alla sua dimensione) in cui il letterale intero può andare bene. Se non esiste un tale tipo, quindi il programma è malformato. Il valore decimale della vostra costante è:
648873758694578209446196L
Sulla mia macchina, sia per clang ++ e g ++ std::numeric_limits<unsigned long long>::max()
è 18446744073709551615
, che è più piccolo della tua costante. Sembra che il tuo programma sia malformato, a meno che il compilatore non usi più di 64 bit per rappresentare unsigned long long
, cosa di cui dubito fortemente. Come @juanchopanza osservato, clang ++ rifiuta di compilare il codice, con l'errore
error: integer constant is larger than the largest unsigned integer type
g ++ comunque va avanti e lo compila, emettendo solo un avviso
warning: large integer implicitly truncated to unsigned type
L'avvertimento è piuttosto confusa, in quanto si riferisce a destra, non alla ulteriore conversione a unsigned int
, per il quale si ottiene
warning: large integer implicitly truncated to unsigned type [-Woverflow]
Sulla mia macchina std::numeric_limits<unsigned int>::max()
è 4294967295
, e quindi 648873758694578209446196L % 4294967295
è 3633002191L
. Tuttavia quando eseguo il tuo programma ottengo 1412716852
. Questo accade perché il programma è mal formato e sfortunatamente il compilatore non emette un errore (non è obbligatorio dallo standard) ma solo un avvertimento.
Poiché il comportamento dell'overflow dei numeri interi senza segno è ben definito. O stai chiedendo perché è così, come in, perché i progettisti di C++ non hanno reso questo un errore? – juanchopanza
FWIW probabilmente dovresti aumentare il livello di avviso. –
sì, perché è – wazeeer