C'è una differenza su come java esegue le operazioni usando operatori di scorciatoia da quelli normali?

StackOverflow https://stackoverflow.com/questions/1803854

Domanda

Sto lavorando a un programma Java relativo al triangolo di Pascal.

Ecco come è codificato:

for(int i = 0; i < 5; i++){
    for(int j = 0, x = 1; j <= i; j++){
        System.out.print(x + " ");
        x = x * (i - j) / (j + 1);
    }
    System.out.println();
}

e mostra:
1
1 1
1 2 1
1 3 3 1
1 4 6 4 1

Ma quando ho provato a cambiare il codice in:

for(int i = 0; i < 5; i++){
    for(int j = 0, x = 1; j <= i; j++){
        System.out.print(x + " ");
        x *= (i - j) / (j + 1);
    }
    System.out.println();
}

e come avrai notato, solo l'operatore è cambiato in * =, ma il risultato è:

1
1 1
1 2 0
1 3 3 0
1 4 4 0 0

Qualche idea su cosa deve essere successo? Grazie in anticipo!

È stato utile?

Soluzione

È perché stai usando l'aritmetica dei numeri interi nell'ordine sbagliato.

x *= (i - j) / (j + 1);

è uguale a

x = x * ((i - j) / (j + 1));

Le parentesi sono importanti. (i - j) / (j + 1) nella maggior parte dei casi non è un numero intero, ma java lo arrotonda comunque ad un numero intero.

Il modo in cui l'hai fatto prima

x = x * (i - j) / (j + 1);

la moltiplicazione avviene prima della divisione, quindi non si ottengono errori di arrotondamento.

Altri suggerimenti

Hai cambiato la precedenza alta * con una precedenza bassa * = risultante

x = x * ((i - j) / (j + 1)); 

invece di

x = (x * (i - j)) / (j + 1);

che probabilmente volevi.

Sembra una divisione intera rispetto all'ordine delle operazioni. Prova ad aggiungere alcune parentesi e penso che alla fine otterrai gli stessi risultati. Se, diciamo, dividi 2/3 in numeri interi, ottieni 0. Quindi è importante se prima fai un po 'di moltiplicazioni.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top