printf ()가“% f”만 있으면 괜찮은데 scanf ()에 왜“% lf”가 필요합니까?


179

왜 즉 scanf()필요 l"에 %lf"는 읽을 때 doubleprintf()사용할 수있는 " %f인수가 있는지 여부에 관계없이" double또는를 float?

예제 코드 :

double d;
scanf("%lf", &d);
printf("%f", d);

1
POINTER의 의미를 이해하지 못했습니다. scanf에서는 & variable (즉) 주소 만 전달하므로 포인터는 어디에

7
@deetchanya C에서 단항 &연산자를 사용하여 변수의 "주소를 가져갈"경우 해당 작업의 결과는 메모리의 변수 저장 위치에 대한 포인터입니다. 에 전달되는 포인터입니다 scanf.
zwol

이 인이에 대한 또 다른 포스트 stackoverflow.com/questions/9291348/...
vimalpt

답변:


207

C는 가변 인수를 취하는 함수에 대해 float를 두 배로 올릴 것이기 때문입니다. 포인터는 아무것도 승격되지 않으므로 %lf, %lg또는 %le(또는 %laC99)를 사용하여 이중으로 읽으십시오.


26

С99 때문에 C의 형식 지정 및 부동 소수점 인수 형의 정합과 일치 printf하고 scanf. 그것은

  • %f ...에 대한 float
  • %lf ...에 대한 double
  • %Lf ...에 대한 long double

유형의 float인수가 가변 변수로 전달 될 때 이러한 인수는 암시 적으로 type으로 변환됩니다 double. 이 이유의 이유 printf형식 지정 %f%lf동등 교환 할 수있다. 에서 printf"크로스 사용"할 수 %lffloat%fdouble .

그러나 실제로 실제로 그렇게 할 이유가 없습니다. 사용하지 마십시오 %fprintf형의 인수 double. 그것은 C89 / 90 시대에 태어난 광범위한 습관이지만 나쁜 습관입니다. for에 사용 %lf하고 인수를 위해 예약 하십시오 .printfdouble%ffloat


1
나는 %fprintf에서 사용 하는 것이 좋은 습관 이라고 말하고 %lf컴파일러가 C99 호환 라이브러리를 가지고 있지 않으면 사용하지 못할 수도 있습니다. 불행히도 그 상황은 실제로 발생합니다.
MM

С99 때문에 C의 형식 지정 및 부동 소수점 인수 형의 정합과 일치 printf하고 scanf. 똑같은 형식 지정자를 사용한다는 것은을 사용하여 쓴 데이터를 [f]printf()읽을 수 있음을 의미하지는 않습니다 [f]scanf(). 일반적으로 사용한 것과 동일한 형식 지정자를 scanf()사용 하면 데이터를 읽을 printf()없습니다 . 예를 들어 prinf()"%d"형식 지정자에 의해 삽입 될 수있는 공간 패딩 "%d"scanf()호출 에서 동일한 형식 지정자에 의해 건너 뜁니다 .
Andrew Henle

16

scanf요구 사항은 데이터의 크기가 가리키는되는 알고 &d가변 기능 (전적으로 있는지 왜) 복식에 수레를 추진하는 반면 때문에, 제대로을 채우기 위해 printf항상을 받고있다 double.


1
variadic 함수는 전달 된 모든 매개 변수의 정확한 유형과 크기를 알아야하고 컴파일시이를 실행할 수 없기 때문에 매우 취약합니다. 변수가 잘못된 유형이면 잘못된 값을 읽습니다. 크기가 잘못되면 이후의 모든 변수도 잘못 읽습니다. 두 개의 다른 크기의 플로트를 전달할 수 있다면 모든 종류의 불쾌하고 놓치기 쉬운 문제가 발생할 수 있습니다.
mwfearnley 12

7

그렇지 않으면 scanf는 double보다 작은 크기의 float에 포인터를 전달한다고 생각하고 잘못된 값을 반환합니다.


2

C 표현식에서 float 또는 double 값을 사용하면 어쨌든 double 값이 생성되므로 printf는 그 차이를 알 수 없습니다. 포인터가 가리키는 것이 중요하기 때문에 double에 대한 포인터는 포인터와 구별되는 scanf로 명시 적으로 신호를 보내야합니다.


5
플로트가 이중으로 변환됩니다 이 경우 인수가 가변 길이 인수 목록의 일부이기 때문에, 수레는 항상 C에서 더블로 변환되지 않습니다
로버트 갬블에게

1
사전 표준 버전의 C 언어 float값은 double표현식에서 자동으로 승격되었습니다 . 이 규칙은 표준 C에서 폐기되었습니다. 일반적으로 표현에서는 float승격되지 않습니다 double. doublevariadic 인수로 전달 될 때만 승격됩니다 .이 경우에 발생합니다.
AnT
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.