2015-01-18 3 views
1

아래 프로그램을 실행하면 예상치 못한 숫자가 출력됩니다. C 프로그램 출력에 대한 설명이 필요합니다.

숫자가 9,999,999,999

1410065407 I 출력에서 ​​다른 번호를 소수

을 확인하십시오. 나는 9999999999를 입력했고 나는 출력에서 ​​1410065407을 본다. 누군가 이것이 어떻게 오는지 설명 할 수 있습니까? 정수 영역의 범위를 초과하는 것 같습니다.

#include<stdio.h> 
#include<stdlib.h> 
void main() 
{ 

    int n,i; 

    printf("Enter the number to be checked\n"); 

    scanf("%d",&n); 

    i=2; 

    while(i<n) 
    { 
     if(n%i==0) 
     { 
      printf("%d is not a prime number\n", n); 
      exit(0); 
     } 

     i++; 
    } 

    printf("%d is a prime number\n", n); 

} 
+1

'void main()'은'int main (void)'이어야합니다. 책에서'main()'을 배웠다면, 돈을 돌려서 출판사에 불평을하십시오. –

답변

3

9,999,999,999 (열 명 9들) 귀하의 int 데이터 형식에 맞게 큰하는 것입니다. 당신이 그와 1,410,065,407의 차이를 작업하는 경우, 당신은 랩」에 의해 두 (2 33 정확한 예정), 당신이 그것을 스캔하는 동안 그것을 감싸 것을 의미한다.

의 정확한 전력의 볼 주위에 ", 나는 정수의 속성을 참조하여 단순히 예상치 못한 무언가가되기 위해 최대한의 값으로 둘러 쌉니다.

예를 들어, 0..255을 포함 할 수있는 8 비트 부호없는 정수는 255을 포함하는 변수에 하나를 더하면 0이됩니다 (부호있는 값은 가장 큰 양의 값에서 가장 작은 음의 값으로 감싼 경향이 있습니다. 이 경우 0에서 가장 작은 가장 작은 의미).

유형이 0..255이고 범위의 문자열 표현이 456 인 십진수로 읽고 있다고 가정 해 봅시다. 4 문자를 처리 할 때

def scanNum(s): 
    result = 0 
    for each character c in s: 
     result = result * 10 + value(c) 
    return result 
  • , result는 열, 0 * 10 = 0 곱, 당신은 다음 4을주는 네 가지를 추가 : 다음의 "코드"작동 대략 방법이 될 것입니다.
  • 5 문자를 처리 할 때 result에 10을 곱한 후 4 * 10 = 40을 입력하면 5를 더하여 45이됩니다. 만 0..255을 나타낼 수 있기 때문에
  • 6 문자를 처리, result는 10로 45 * 10 = 450하지만,를 곱, 그것은 당신에게 450 - 256 = 194을주고, 주위에 래핑합니다. 그리고 나서 6을 더한 후 200을줍니다.

당신이 원하는 것과 당신이 얻는 것의 차이가 범위와도 매우 관련되어 있다는 것을 볼 수 있습니다 : 456 - 200 = 256.

당신은 '당신에게, (32 비트 2의 보수로 가장 많은 수를 표현할 수는 2,147,483,647에서 큰 염두에두고, 또는 999,999,999) 9의 그것을 시도, 또는 더 큰 숫자를 개최 할 수있는 데이터 형식을 사용하는 경우 아마 괜찮아 찾아 낼 것이다 :

:

#include <stdio.h> 
#include <stdlib.h> 
int main (void) { 
    long long n; 
    printf("Enter the number to be checked\n"); 
    scanf("%lld",&n); 
    printf("%lld\n", n); 
    return 0; 
} 

내가 원래는 strtol 기능에 연기 C11 7.21.6.2 The fscanf function /12 당이, 이후 표준에 따라 잘못 생각

d 선택적으로 부호가있는 10 진 정수와 일치합니다. 형식은 기본 인수에 대해 값 10 인 strtol 함수의 주제 시퀀스에 대해 예상 한 것과 같습니다. 해당 인수는 부호있는 정수에 대한 포인터입니다.

strtol 기능 C11 7.22.1.4 The strtol, strtoll, strtoul, and strtoull functions /8 상태 : 올바른 값을 표현할 수있는 값의 범위를 벗어나면

, LONG_MIN가 LONG_MAX가 LLONG_MIN가 LLONG_MAX가 ULONG_MAX가 또는 ULLONG_MAX는 (반환에 따른되고 반환 유형 및 값의 부호 (있는 경우).

그러나 실제로는 형식 만 해당 기능을 사용합니다. fscanf 그 형제의 결과C11 7.21.6.2 The fscanf function /10 의해 제어되어 변환 결과는 개체로 표현 될 수없는 경우

이 개체가 적절한 유형 또는 이 없으면 동작이 정의되지 .

그래서, 당신은 다시 얻을 수는 사실, 정의되지 않은 행동의 결과에 대한 제한의 부족을 주어, 아무것도 할 수있다 범위를 벗어나이고 있다면, 그냥 사기를 반환하는 대신 아무것도을 할 수 결과는 디스크를 포맷하고 로컬 시공간을 적나라한 특이점으로 축소시키는 것을 포함합니다 :-)

이 경우에는 코드가 수행하는 가장 간단한 작업 인 스캔 프로세스의 일부로 값을 감싸는 것처럼 보입니다 .

+0

예. 그 차이는 8589934592 \t이며 정확한 힘은 2입니다. 그러나 나는 "랩 어라운드"라는 용어를 얻지 못했습니다. 최종 목록에 도달하면 정수 목록의 처음으로 돌아 간다는 것을 의미합니까? – Zack

+0

@Zack, 네, 그게 본질적입니다. 나는 (실질적으로) 더 많은 정보로 답을 갱신했다. 희망이 도움이됩니다. – paxdiablo

+0

자세한 답변을 주셔서 감사합니다. – Zack

관련 문제