programing tip

+0과 -0이 동일합니까?

itbloger 2020. 6. 4. 19:19
반응형

+0과 -0이 동일합니까?


관통 읽기 인 ECMAScript 5.1 규격 , +0-0구별된다.

그렇다면 왜 +0 === -0평가 true합니까?


JavaScript는 IEEE 754 표준사용 하여 숫자를 나타냅니다. 에서 위키 백과 :

부호있는 0 은 연관된 부호와 함께 0 입니다. 일반적인 산술에서는 −0 = +0 = 0입니다. 그러나 계산에서 일부 숫자 표현은 종종 -0 (음수 0)+0 (양수 0)으로 표시되는 두 개의 0을 허용합니다 . 이것은 정수의 부호있는 숫자 표현과 대부분의 부동 소수점 숫자 표현에서 발생합니다. 숫자 0은 일반적으로 +0으로 인코딩되지만 +0 또는 -0으로 표시 될 수 있습니다.

부동 소수점 산술에 대한 IEEE 754 표준 (현재 부동 소수점 숫자를 지원하는 대부분의 컴퓨터 및 프로그래밍 언어에서 사용)에는 +0과 -0이 모두 필요합니다. 0은 1 / -0 = -∞ 및 1 / + 0 = + ∞의 확장 실수 라인의 변형으로 간주 될 수 있으며, 0으로 나눈 값은 ± 0 / ± 0 및 ± ∞ / ± ∞에 대해서만 정의되지 않습니다. .

이 기사에는 다른 표현에 대한 추가 정보가 들어 있습니다.

이것이 기술적으로 두 제로를 구별해야하는 이유입니다.

그러나 +0 === -0true로 평가됩니다. 왜 그런 겁니까 (...) ?

이 동작은 섹션 11.9.6 , 엄격한 평등 비교 알고리즘 (부분적으로 강조 )에 명시 적으로 정의되어 있습니다 .

x === ywhere xyare 값은 비교 에서 true 또는 false를 생성 합니다 . 이러한 비교는 다음과 같이 수행됩니다.

(...)

  • Type (x)가 숫자이면

    1. x가 NaN이면 false를 반환합니다.
    2. y가 NaN이면 false를 반환합니다.
    3. x가 y와 같은 숫자 값이면 true를 반환합니다.
    4. x가 +0이고 y가 −0이면 true를 반환합니다.
    5. x가 -0이고 y가 +0이면 true를 반환합니다.
    6. 거짓을 돌려줍니다.

(...)

( +0 == -0btw도 마찬가지 입니다.)

논리적으로 취급 +0하고 -0동등한 것으로 보입니다 . 그렇지 않으면 우리는 이것을 코드에서 고려해야하며 개인적으로는 그렇게하고 싶지 않습니다.)


노트 :

ES2015는 새로운 비교 방법을 도입했습니다 Object.is. Object.is명시 적 구별 -0+0:

Object.is(-0, +0); // false

@ user113716의 의견을 간과했기 때문에 이것을 답변으로 추가하겠습니다.

다음을 수행하여 -0을 테스트 할 수 있습니다.

function isMinusZero(value) {
  return 1/value === -Infinity;
}

isMinusZero(0); // false
isMinusZero(-0); // true

+0과 -0이 실제로 다르게 동작하는 예제를 보았습니다.

Math.atan2(0, 0);  //returns 0
Math.atan2(0, -0); //returns Pi

주의 : -0.0001과 같은 음수에서 Math.round를 사용할 때도 실제로는 -0이되고 위에 표시된대로 일부 후속 계산을 망칠 수 있습니다.

이 문제를 해결하는 빠르고 더러운 방법은 다음과 같이 smth를 수행하는 것입니다.

if (x==0) x=0;

또는 그냥 :

x+=0;

-0 인 경우 숫자를 +0으로 변환합니다.


에서 IEEE 754 표준 자바 스크립트의 형식 번호를 나타내는 데 사용되는, 부호가 비트에 의해 표현된다 (1 음의 번호를 나타낸다).

결과적으로를 포함하여 각 표현 가능한 숫자에 대해 음수 값과 양수 값이 모두 존재합니다 0.

이 이유는 둘 다 -0+0존재한다.


원래 제목에 답하기 Are +0 and -0 the same?:

brainslugs83(by by answer Spudley)는 JS의 +0과 -0이 함수와 동일하게 구현되지 않은 중요한 경우를 지적했습니다.

var sign = function(x) {
    return 1 / x === 1 / Math.abs(x);
}

표준 이외 Math.sign의 올바른 부호 +0 및 -0을 반환합니다.


0에는 두 가지 가능한 값 (비트 표현)이 있습니다. 이는 고유하지 않습니다. 특히 부동 소수점 숫자에서이 문제가 발생할 수 있습니다. 부동 소수점 숫자는 실제로 일종의 수식으로 저장되기 때문입니다.

정수도 별도의 방식으로 저장할 수 있습니다. 추가 부호 비트가있는 숫자 값을 가질 수 있으므로 16 비트 공간에서 15 비트 정수 값과 부호 비트를 저장할 수 있습니다. 이 표현에서 값 1000 (16 진)과 0000은 모두 0이지만 그 중 하나는 +0이고 다른 하나는 -0입니다.

This could be avoided by subtracting 1 from the integer value so it ranged from -1 to -2^16, but this would be inconvenient.

A more common approach is to store integers in 'two complements', but apparently ECMAscript has chosen not to. In this method numbers range from 0000 to 7FFF positive. Negative numbers start at FFFF (-1) to 8000.

Of course, the same rules apply to larger integers too, but I don't want my F to wear out. ;)


We can use Object.is to distinguish +0 and -0, and one more thing, NaN==NaN.

Object.is(+0,-0) //false

Object.is(NaN,NaN) //true

I'd blame it on the Strict Equality Comparison method ( '===' ). Look at section 4d enter image description here

see 7.2.13 Strict Equality Comparison on the specification


Wikipedia has a good article to explain this phenomenon: http://en.wikipedia.org/wiki/Signed_zero

In brief, it both +0 and -0 are defined in the IEEE floating point specifications. Both of them are technically distinct from 0 without a sign, which is an integer, but in practice they all evaluate to zero, so the distinction can be ignored for all practical purposes.

참고URL : https://stackoverflow.com/questions/7223359/are-0-and-0-the-same

반응형