두 개의 부호있는 정수가 있고이를 뺍니다. 오버플로인지 알아야합니다.C에서 부호있는 32 비트 숫자 두 개를 뺄 때 오버플로를 감지하는 방법은 무엇입니까?
int one;
int two;
int result = two-one;
if (OVERFLOW) {
printf("overflow");
} else {
printf("no overflow");
}
그런 것. 이것을 할 수있는 좋은 방법이 있습니까?
두 개의 부호있는 정수가 있고이를 뺍니다. 오버플로인지 알아야합니다.C에서 부호있는 32 비트 숫자 두 개를 뺄 때 오버플로를 감지하는 방법은 무엇입니까?
int one;
int two;
int result = two-one;
if (OVERFLOW) {
printf("overflow");
} else {
printf("no overflow");
}
그런 것. 이것을 할 수있는 좋은 방법이 있습니까?
첫째, 서명 계산에 오버 플로우가 잠시 UB 잊고과 2의 보수 기계의 전형적인 오버 플로우 행동을 고집,
둘째 C.에서 정의되지 않은 동작이 발생합니다 : 오버 플로우가 발생할 사실로 밝혀 " 첫 번째 피연산자에서 첫 번째 피연산자보다 더 큰 결과가 나오거나 두 번째 피연산자가 음수 인 첫 번째 피연산자보다 크면 결과가 "잘못된 방향"으로 이동합니다. 귀하의 경우
int one, two;
int result = two - one;
if ((result < two) != (one > 0))
printf("overflow");
더 높은 정밀도로 비교할 수 있습니다. 32 비트 정수라고 가정 해보십시오. 64 비트 정수로 승격하고 빼고 그 결과를 32 비트로 캐스팅 한 다음 64 비트까지 다시 비교할 수 있습니다.
언어가 ... 크기에 당신에게 어쩌면 int32_t
및 <inttypes.h>
에서 (C99)에서 int64_t
을 보증을 제공하지 않기 때문에 내가 int
으로이 방법을 수행하지 않을 것입니다.
Windows를 사용하는 경우 ULongSub()
등을 사용할 수 있으며 오버플로시 오류 코드가 반환됩니다.
에서
당신은 그런 일이 전에 overlow (또는 언더 플로우)를 잡을 필요가있다. 일이 생기면 미정의 행동 땅과 모든 내기는 꺼져 있습니다. 내가 32 비트이 경우 않으면
#include <limits.h>
#include <stdio.h>
int sum_invokes_UB(int a, int b) {
int ub = 0;
if ((b < 0) && (a < INT_MIN - b)) ub = 1;
if ((b > 0) && (a > INT_MAX - b)) ub = 1;
return ub;
}
int main(void) {
printf("(INT_MAX-10) + 8: %d\n", sum_invokes_UB(INT_MAX - 10, 8));
printf("(INT_MAX-10) + 100: %d\n", sum_invokes_UB(INT_MAX - 10, 100));
printf("(INT_MAX-10) + INT_MIN: %d\n", sum_invokes_UB(INT_MAX - 10, INT_MIN));
printf("100 + INT_MIN: %d\n", sum_invokes_UB(100, INT_MIN));
printf("-100 + INT_MIN: %d\n", sum_invokes_UB(-100, INT_MIN));
printf("INT_MIN - 100: %d\n", sum_invokes_UB(INT_MIN, -100));
return 0;
}
'int result = two - one; '이 오버 플로우 (또는 언더 플로우)하면 Undefined Behavior 랜드에 있는데 아무 것도 일어나지 않을 수 있습니다. – pmg
내 대답의 맨 처음 문장에서 명시 적으로 언급 한 내용이 있습니다. (비록 전통적인 의미에서 "언더 플로우 (underflow)"라는 용어는 여기에 적용되지 않습니다.) – AnT
나는이 답변을 좋아하지만 주목할 것은 정의되지 않은 행동입니다. 결과가 '잘못된 방향'으로 '움직일'것이라고 가정하는 것이 안전한가요? –