2011-10-22 16 views
52

Mentre guardando attraverso alcuni esempio di codice C, mi sono imbattuto in questo:Cosa significa y - = m <3?

y -= m < 3; 

Cosa fare? È una specie di loop condensato o qualcosa del genere? È impossibile google per quanto ne so.

+1

Che grande domanda – xsari3x

+11

E 'importante notare che '<' ha precedenza più alta (si lega più strettamente) di '- =', quindi 'y - = m <3' significa' y - = (m <3) '. –

+19

È praticamente l'equivalente di 'if (m <3) y = y-1;' – mpen

risposta

75

m < 3 è 1 o 0, a seconda del valore di verità.

Così y=y-1 quando m<3 è true o y=y-0 quando m>=3

+1

Ok, grazie, non mi ero reso conto che si potevano usare le dichiarazioni booleane come un valore del genere. – TheTedinator

+0

@ TheTedinator: questo è possibile in qualsiasi linguaggio che convertirà il valore "falso" booleano all'intero "0" e "vero" booleano all'intero "1". –

+0

Java si è arrabbiato con me quando l'ho provato, ma ero in grado di usare solo un'istruzione if. – TheTedinator

10

m < 3 vale 1 se m è inferiore a 3. Quindi, y viene diminuita per uno in questo caso. Quindi, un'istruzione if evitata.

+0

Se si desidera mantenerlo leggibile ed evitare comunque 'if', utilizzare y - = (m <3? 1: 0); Le parentesi sono facoltative, ma migliorano un po 'la leggibilità. – AttishOculus

25

Se si scomposizione per ordine di precedenza per ciascuna operazione, si ottiene:

y = (y - (m < 3)); 

m < 3 viene valutato e restituisce un risultato booleano 1 o 0, quindi l'espressione può essere semplificata come

y = y - 1; // if m < 3 is true 

o

y = y - 0; // if m < 3 is false 

Lo scopo di ciò è evitare una clausola if.

+2

No, lo scopo è quello di mettere in mostra e confondere i futuri programmatori di manutenzione. – Justsalt

+0

^hehehe! Mi piace quella risposta :) –

2

Non posso dire che si desidera è per, ma posso dirvi che cosa fa:

m < 3 restituisce un int di 0 o 1 che rappresenta un valore booleano.

se m è inferiore a 3, la dichiarazione viene valutata come: y -= 1 o y = y - 1;

se m è maggiore o uguale a 3, l'istruzione viene valutata come y -= 0 o y = y - 0. Nel complesso, in questo caso, la dichiarazione non fa nulla.

+6

In C, 'm <3' non produce un valore booleano (cioè un valore di tipo' bool' o '_Bool'). Produce un valore di tipo 'int', con il valore 0 o 1. Quel valore può essere usato come condizione o, come in questo caso, come valore aritmetico. –

+0

Punto valido. Editato –

14

I indica if (m < 3) { y -=1; }, poiché (m < 3) è 1 se m è minore di 3, 0 altrimenti.

Il codice appare in qualche vecchia implementazione di riferimento di qualcosa che ha a che fare con gli anni bisestili o Pasqua, o forse entrambi: i primi due mesi gennaio e febbraio sono speciali perché si verificano prima del giorno bisestile. Non c'è davvero alcuna scusa per scrivere un codice del genere, a meno che non ti piaccia davvero l'aspetto di esso. La maggior parte delle persone no.

-1

Sono d'accordo che il codice è equivalente a if(m<3) y=y-1;

Tuttavia è codice non sicuro perché mentre FALSE è sempre 0, TRUE ha avuto un paio di definizioni. Al giorno d'oggi TRUE è uguale a 1 nella maggior parte dei sistemi di programmazione, ma nei sistemi più vecchi era uguale a -1 (dove tutti i bit erano impostati su on, non solo l'ultimo). Quindi, se questo codice è in esecuzione su una piattaforma precedente, potrebbe essere convertito in if(m<3) y=y-(-1); o if(m<3) y=y+1; La compatibilità tra sistemi incrociati è un grande motivo per evitare codice "intelligente" come questo.

+9

-1 In The C99 Standard (guardando N1256) garantisce in 6.5.8.6 che: "Ciascuno degli operatori <, >, <=, and > = restituirà 1 se la relazione specificata è vera e 0 se è falsa.". Questo comportamento è stato garantito anche dalla C89 e in effetti riporta tutto a K & R ... Quindi dovrebbe essere considerato sufficientemente portatile :) –

0

< ha una priorità più alta al segno delle pari = così m<3 1 se m è inferiore a 3, e il resto è 0

allora y = y - 1 o y = y - 0