In C++ come in C, i turni sono limitati alla dimensione (in bit) del valore spostato. Ad esempio, se unsigned int è a 32 bit, uno spostamento di oltre 31 non è definito.
In pratica, un risultato comune è che vengono utilizzati i 5 bit meno significativi della quantità di spostamento ei bit di ordine superiore vengono ignorati; questo è dovuto al fatto che il compilatore produce un'istruzione macchina che fa esattamente questo (ad es. SHR su x86).
In questo caso, il valore di spostamento è 100000
(decimale) che risulta essere 11000011010100000
in binario - i 5 bit inferiori sono zero. Quindi, stai effettivamente ottenendo un cambiamento di 0. Non dovresti comunque fare affidamento su questo; tecnicamente, quello che stai vedendo è comportamento non definito.
Riferimenti:
Per C, N1570 sezione 6.5.7:
Se il valore dell'operando destro è negativo o è maggiore o uguale alla larghezza dell'operando sinistro promosso, il comportamento è indefinito.
Per C++, N3690 sezione 5.8 "[expr.shift]":
Il comportamento è indefinito se l'operando destro è negativo, o maggiore o uguale alla lunghezza in bit della promosso operando a sinistra.
N1570 è un progetto, quasi identico allo standard ISO C11 rilasciato; questa clausola è stata pressoché la stessa dallo standard ANSI C del 1989.
N3690 è una bozza recente dello standard C++; Non sono sicuro che sia il migliore da usare, ma ancora una volta, questa clausola non è cambiata.
@ShafikYaghmour: Ciò presuppone il compilatore persino i molestatori che stanno mettendo un'istruzione. È proprio nel suo diritto rifiutare questo programma. – MSalters
@MSalters, in questo momento stiamo entrando nel compilatore/piattaforma/versione specifica ma per le versioni correnti e recenti questo è il caso e, come ho già affermato, non è definito in modo da essere chiaramente da soli, 'gcc' sembra solo produce un 'shr' quando si usa' -O0'. –
@ShafikYaghmour: Intel è solo una delle tante piattaforme supportate da gcc e ha diverse fasi di ottimizzazione. Un trucco comune nell'ottimizzazione consiste nel dire "Questo valore può essere compreso tra 0 e 31 perché è utilizzato in un turno, se seguo il percorso del codice X per ottenere qui il valore non sarà compreso tra 0 e 31, quindi il percorso del codice X è impossibile e non ho nemmeno bisogno di generare istruzioni per questo ". GCC lo fa famosomente per i controlli puntatori nulli. – MSalters