2016-05-18 1 views
-1
long long n, prod, i; 
n = 13; 
prod = 1; 

for (i = 1 ; i <= n ; i++) { 
    prod *= i; 
} 
printf("%d\n", prod); 
printf("%d\n", sizeof(long long)); 

戻りはsizeof 8を与えるが、数は2 ** 32

$ 1932053504 
$ 8 

結果が明らかに溢れているにオーバーフロー。しかし、私はこれがなぜ起こっているのか分かりません。long longsizeof(int)は4 [バイト]を返しますが、製品は同じです。私は間違って何をしていますか?

+0

なぜ結果があふれていますか? –

+0

pythonを使用しているので: 'math.factorial(13)-2 ** 32 == 1932053504' – Nimitz14

+0

私の答えを読んでください。 –

答えて

6

正しい指定子を使用する必要があります。 "%d"指定子はintで、あなたはlong long intを渡します。 標準によれば、これは未定義の動作を呼び出すでしょう。観察された振る舞いは説明可能かもしれないが、それは厳密ではないことを意味しない。未定義の振舞い

この

printf("%lld\n", prod); 
printf("%zu\n", sizeof(long long)); 

のようなコードを修正して、意図したとおりにそれが動作するはずです。

注:コンパイルの警告を有効にして、この種の間違いをすばやく見つける必要があります。

+0

ああ、大丈夫です。しかし、ソリューションで2つの異なる指定子を使用する理由を説明できますか? – Nimitz14

+0

'sizeof'は'%zu "指定子を必要とする' size_t'を与えます。それは 'long long int 'ではない。型の安全を保証する他の方法はないので、指定子と渡される型は非常に厳密でなければなりません。 –

+0

意味があります。ありがとう! – Nimitz14

2

結果がはっきりとあふれています。

これは間違った結論です。切り詰められた結果が得られます。

私が実行します。

#include <stdio.h> 

int main() 
{ 
    long long n, prod, i; 
    n = 13; 
    prod = 1; 

    for (i = 1 ; i <= n ; i++) { 
     prod *= i; 
    } 
    int truncated_value = prod; 

    printf("%d\n", prod); 
    printf("%d\n", truncated_value); 
} 

私は

1932053504 
1932053504 

を得る切り捨ては%d書式指定子の使用により起こります。

正しい形式指定子を使用して修正できます。

printf("%lld\n", prod); 
関連する問題