如果未初始化局部变量,则代码运行错误

问题描述 投票:0回答:2

这是一个用于计算素数的小代码,使用gcc(Debian 8.3.0-6)8.3.0进行编译当我使用int64_t p = 0时,它可以正常工作。使用int64_t p,它会工作错误。这是什么问题?

变量p将通过使用scanf分配

int64_t p = 0确定:

gcc t.c && ./a.out
input a prime:3
i:2 < number:3
3 is a prime, again

int64_t p错误:

gcc t.c && ./a.out
input a prime:3
i:2 < number:3
i:3 < number:3
i:4 < number:3
i:5 < number:3
i:6 < number:3
i:7 < number:3
i:8 < number:3
i:9 < number:3
i:10 < number:3
i:11 < number:3
i:12 < number:3
i:13 < number:3
3 not a prime, again
#include <stdint.h>
#include <stdio.h>

int32_t isPrime(int64_t number)
{
    int64_t i = 2;
    for(; i < number; i++)
    {   
        printf("i:%d < number:%d\n",i, number);
        if((number % i) == 0)
            return 0;
        if ((i * i) >= number)
            break;
    }   
    return 1;
}

int32_t main(void)
{
    int64_t t = 0;
    int64_t p;                                                                                                                                                                                                                              
    //int64_t p = 0;

    printf("input a prime:");
    do  
    {   
        scanf("%d",&p);
        getchar();
        if (isPrime(p))
            printf("%d is a prime, again:", p); 
        else
            printf("%d not a prime, again:", p); 
    }while(1);
}
c
2个回答
3
投票

您已将p声明为int64_t,但%d表示intint64_t和其他stdint.h类型的转换说明符位于inttypes.h中:

#include <inttypes.h>
scanf("%" SCNd64, &p);

类似地,在打印时(使用正确的说明符会向您显示问题):

printf("i:%" PRId64 " < number:%" PRId64 "\n", i, number);

这两个错误都是优秀的编译器应该能够警告您的东西-例如,clang默认会这样做。如果您使用的是gcc,请确保至少使用gcc -Wall进行编译。

此外,检查scanf的返回值以确保成功是个好主意。如果您不希望进行更深层次的恢复,则最好退出其他方法。

if (scanf("%" SCNd64, &p) != 1) {
    return EXIT_FAILURE;
}

最后,main的正确返回类型是int,而不是int32_t


3
投票

此(scanf("%d",&p);)是读取int64_t的错误代码。形式上,您需要scanf("%" SCNd64, &p)-和<inttypes.h>(而不是<stdint.h>或与之相同)。

您可能不愿使用scanf("%lld", &p);,因为在大多数计算机上,int64_tlong long的同义词。

使用结果前,您还应检查scanf()返回1

初始化p时,您会得到p调用设置的scanf()的“正确”部分,因为您使用的是低端字节序的计算机,而其余部分则为零。但是这样做会引起不确定的行为。什么事情都可能发生。它是不可移植的(它可能不会在big-endian机器上做您想要的事情),并且由于它的不确定性而完全不可靠。

© www.soinside.com 2019 - 2024. All rights reserved.