우리는 모두 알고 0/0
있다 Undefined
내가 계산기에 넣어한다면 오류를 반환, 내가 프로그램을 작성한다면 내가 0으로 분할 할 때 (C에서 이상) 운영 체제가 종료됩니다.
그러나 내가 궁금해했던 것은 컴퓨터 가 0으로 나누려고 시도 하거나 "보호 기능이 내장되어" 0/0
있는지 계산하여 계산하기 전에 오류를 반환하는지 여부입니다.
우리는 모두 알고 0/0
있다 Undefined
내가 계산기에 넣어한다면 오류를 반환, 내가 프로그램을 작성한다면 내가 0으로 분할 할 때 (C에서 이상) 운영 체제가 종료됩니다.
그러나 내가 궁금해했던 것은 컴퓨터 가 0으로 나누려고 시도 하거나 "보호 기능이 내장되어" 0/0
있는지 계산하여 계산하기 전에 오류를 반환하는지 여부입니다.
답변:
CPU가 내장되어 있습니다. 대부분의 명령어 세트 아키텍처는 CPU가 0으로 정수를 나누기 위해 예외 처리기로 트랩하도록 지정합니다 (배당이 0인지 상관하지 않습니다).
나누기 시도와 함께 제로 제수가 제로에 대한 검사가 병렬로 발생할 수 있지만, 위반 조건을 감지하면 효과적으로 나누기와 트랩을 취소하므로 일부 부품이 있는지 실제로 알 수 없습니다 그것의 사단을 시도했다.
(하드웨어는 종종 여러 작업을 병렬로 수행 한 다음 적절한 결과를 선택하여 적절한 작업 선택에 따라 직렬화하는 대신 각 작업을 즉시 시작할 수 있기 때문에 종종 그렇게 작동합니다.)
오버 플로우 감지가 켜질 때 예외 메커니즘에 대한 동일한 트랩도 사용되며, 일반적으로 다른 add / sub / mul 명령어 (또는 해당 명령어의 플래그)를 사용하여 요청합니다.
부동 소수점 나누기도 0으로 나누기위한 감지 기능이 내장되어 있지만 예외 핸들러에 트래핑하는 대신 다른 값 ( IEEE 754는 NaN 지정)을 반환 합니다.
가설 적으로 CPU가 0으로 나누려는 시도를 생략하면 문제는 다음과 같습니다.
언어, 컴파일러, 정수 또는 부동 소수점 숫자 등을 사용하는지 여부에 따라 다릅니다.
부동 소수점 수의 경우 대부분의 구현은 IEEE 754 표준을 사용하며 0으로 나누기가 잘 정의되어 있습니다. 0 / 0은 잘 정의 된 NaN (숫자가 아님)의 결과를 제공하고 x ≠ 0의 x / 0은 x의 부호에 따라 + Infinity 또는 -Infinity를 제공합니다.
C, C ++ 등의 언어에서 0으로 나누면 정의되지 않은 동작이 발생합니다. 언어 정의에 따르면 모든 일이 발생할 수 있습니다. 특히 당신이 일어나고 싶지 않은 것들. 코드를 작성할 때 모든 것이 완벽하게 작동하고 고객이 코드를 사용할 때 데이터가 파괴되는 것처럼. 따라서 언어 관점 에서이 작업을 수행하지 마십시오 . 일부 언어 는 응용 프로그램이 중단되도록 보장 합니다. 이것이 어떻게 구현되는지는 그들에게 달려 있습니다. 이러한 언어의 경우 0으로 나누면 충돌이 발생합니다.
많은 프로세서에는 일종의 내장 "분할"명령이 있으며, 이는 프로세서에 따라 다르게 동작합니다. Intel 32 비트 및 64 비트 프로세서에서 0으로 나누려고하면 "나누기"명령어가 응용 프로그램과 충돌합니다. 다른 프로세서는 다르게 작동 할 수 있습니다.
컴파일러가 일부 코드를 실행할 때 0으로 나누기가 발생하고 컴파일러가 사용자에게 친절하다는 것을 감지하면 경고 메시지를 표시하고 내장 "분할"명령을 생성하여 동작이 같은.
EXCEPTION_INT_DIVIDE_BY_ZERO
가치 EXCEPTION_RECORD
에 의해 처리 될 것입니다 (희망) 설치 Structed 예외 처리 핸들러를
그러나 내가 궁금했던 것은 컴퓨터가 0으로 나누려고 시도하거나 "보호 기능이 내장되어"있고 0/0을 "보면"계산하기 전에도 오류를 반환하는지 여부입니다.
때문에 x/0
아무 의미, 기간을하지 않으며, 컴퓨터는 항상 0으로 나누기를 확인해야합니다. 여기에 문제가 있습니다. 프로그래머 (a+b)/c
는 계산이 타당한 지 확인하지 않아도 계산 을 원합니다 . CPU + 숫자 유형 + 운영 체제 + 언어에 의해 0으로 나누는 것에 대한 생생한 반응은 다소 과감한 것 (예 : 프로그램 충돌)을 수행하거나 지나치게 양성적인 것 (예 : IEEE 부동 소수점과 같은 의미 ( NaN
숫자가 아님)
일반적인 환경에서 프로그래머는 (a+b)/c
의미 가 있는지 알아야합니다 . 이와 관련하여 0으로 나누기를 확인할 이유가 없습니다. 0으로 나누기가 발생하고 기계 언어 + 구현 언어 + 데이터 유형 + 운영 체제에 대한 응답이 프로그램 충돌을 일으키는 것이라면 괜찮습니다. 응답이 결국 프로그램의 모든 숫자를 오염시킬 수있는 값을 작성하는 것이라면 괜찮습니다.
"신뢰할 수있는 것"또는 "과도한 양성"이 높은 신뢰성의 컴퓨팅 세계에서 올바른 일이 아닙니다. 이러한 기본 응답으로 인해 환자가 사망하거나 여객기가 추락하거나 폭탄이 잘못된 곳에서 폭발 할 수 있습니다. 신뢰성이 높은 환경 (a+b)/c
에서 코드를 작성하는 동안 또는 현대에 글을 쓰는 프로그래머는 죽어가는 구조를 확인하는 도구에 의해 자동으로 죽을 것이다. 이 환경에서 해당 프로그래머는 대신 줄을 따라 무언가를 작성 했어야 div(add(a,b),c)
하고 오류 상태를 확인해야합니다. 후드 아래에서 div
(및 add
) 기능 / 매크로는 0으로 나눠지는 것을 방지합니다 (또는 경우에는 오버플로 add
). 그 보호가 수반하는 것은 구현에 따라 다릅니다.
우리는 지금 알고 x/0
하고 0/0
잘 정의 된 답변이 없습니다. 0/0
어쨌든 계산을 시도하면 어떻게됩니까?
최신 시스템에서는 계산이 CPU 내의 MPU로 전달되고을 반환하는 잘못된 작업으로 플래그가 지정됩니다 NaN
.
온칩 부서가없는 80 년대 가정용 컴퓨터와 같은 훨씬 오래된 시스템에서 계산은 실행중인 소프트웨어에 따라 수행되었습니다. 몇 가지 가능한 선택 사항이 있습니다.
0
1
log(0)
있으며 소프트웨어에서 오류 처리 루틴을 사용하거나 충돌합니다0
e 0 = 1이되며 결과는 다음과 같습니다.1
다시 말해, 구현에 따라 구현이 달라질 수 있으며, 모든 값에 대해 정확하고 예측 가능한 결과를 생성하지만 그에 대한 이상한 값은 0/0
여전히 내부적으로 일관성이있는 소프트웨어를 작성할 수 있습니다 .
NaN
.
very inefficient
나누기위한 것이라고 말했습니다 . 산술 비용은 (더하기 = 빼기) <= 곱셈 <= 나누기입니다. 더하기 (보통 1 개)와 동일한 수의 클럭 주기로 나눌 수있는 MPU가없는 경우 나누기는 더하기와 빼기보다 비싸고 일반적으로 곱셈보다 비쌉니다.