NaN
Baseline Widely available
This feature is well established and works across many devices and browser versions. It’s been available across browsers since July 2015.
Please take two minutes to fill out our short survey.
전역 NaN
속성은 Not-A-Number(숫자가 아님)를 나타냅니다.
시도해 보기
function sanitize(x) {
if (isNaN(x)) {
return NaN;
}
return x;
}
console.log(sanitize("1"));
// Expected output: "1"
console.log(sanitize("NotANumber"));
// Expected output: NaN
값
Number.NaN
와 동일한 숫자 값입니다.
Property attributes of NaN | |
---|---|
쓰기 가능 | 불가능 |
열거 가능 | 불가능 |
설정 가능 | 불가능 |
설명
NaN
은 전역 객체의 속성입니다. 즉 전역 범위의 변수입니다.
최신 브라우저에서 NaN
은 설정 불가, 쓰기 불가 속성입니다. 그렇지 않다고 하더라도 덮어쓰는 건 피하는 게 좋습니다.
NaN
을 반환하는 연산에는 다섯 가지 종류가 있습니다.
- 숫자로 변환 실패 (예시:
parseInt("blabla")
,Number(undefined)
와 같은 명시적인 것 또는Math.abs(undefined)
와 같은 암시적인 것) - 결과가 허수인 수학 계산식 (예시:
Math.sqrt(-1)
) - 정의할 수 없는 계산식 (예시:
0 * Infinity
,1 ** Infinity
,Infinity / Infinity
,Infinity - Infinity
) - 피연산자가
NaN
이거나NaN
으로 강제 변환되는 메서드 또는 표현식 (예시:7 ** NaN
,7 * "blabla"
) - 이것은NaN
이 전염성 있다는 것을 의미합니다. - 유효하지 않은 값이 숫자로 표시되는 기타 경우 (예시: 잘못된 날짜
new Date("blabla").getTime()
,"".charCodeAt(1)
)
NaN
과 NaN
의 동작은 JavaScript에서 발명한 것이 아닙니다. 부동 소수점 산술의 의미(NaN !== NaN
포함)는 IEEE 754에 의해 지정됩니다. NaN
의 동작은 다음과 같습니다.
NaN
이 수학 연산에 포함된 경우 (그러나 비트 연산는 아님) 결과도 일반적으로NaN
입니다. (아래의 counter-example 참조)NaN
이 관계 비교(>
,<
,>=
,<=
)의 피연산자 중 하나인 경우 결과는 항상false
입니다.NaN
은 (==
,!=
,===
및!==
를 통해) 다른NaN
값을 포함하여 다른 값과 같지 않은 것으로 비교됩니다.
NaN
은 JavaScript의 falsy 값 중 하나이기도 합니다.
예제
NaN
판별
값이 NaN
인지 확인하려면, Number.isNaN()
또는 isNaN()
를 사용하여 값이 NaN
인지 여부를 확인 할 수 있습니다. 또는 NaN
은 자신과 같지 않다고 비교되는 유일한 값이므로 x !== x
와 같은 자체 비교를 수행할 수 있습니다.
NaN === NaN; // false
Number.NaN === NaN; // false
isNaN(NaN); // true
isNaN(Number.NaN); // true
function valueIsNaN(v) {
return v !== v;
}
valueIsNaN(1); // false
valueIsNaN(NaN); // true
valueIsNaN(Number.NaN); // true
그러나 isNaN()
과 Number.isNaN()
의 차이를 유의해야 합니다. isNaN
은 현재 값이 NaN
이거나, 숫자로 변환했을 때 NaN
이 되면 참을 반환하지만, Number.isNaN
은 현재 값이 NaN
이어야만 참을 반환합니다.
isNaN("hello world"); // true
Number.isNaN("hello world"); // false
같은 이유로 BigInt 값을 사용하면 Number.isNaN()
이 아닌 isNaN()
에서 오류가 발생합니다.
isNaN(1n); // TypeError: Conversion from 'BigInt' to 'number' is not allowed.
Number.isNaN(1n); // false
또한 일부 배열 메서드는 NaN
을 찾을 수 없는 반면에 다른 배열 메서드들은 찾을 수 있습니다. 즉, (indexOf()
, lastIndexOf()
)는 NaN
을 찾을 수 없지만, includes()
는 값을 찾을 수 있습니다.
const arr = [2, 4, NaN, 12];
arr.indexOf(NaN); // -1
arr.includes(NaN); // true
// 적절하게 정의된 조건자를 허용하는 메서드는 항상 NaN을 찾을 수 있습니다.
arr.findIndex((n) => Number.isNaN(n)); // 2
NaN
과 그 비교에 대한 자세한 내용은 평등 비교 및 동일성를 참조.
눈에 띄게 구별되는 NaN 값
NaN
이 자신과 동등하지 않은 데는 동기가 있습니다. IEEE 754 인코딩에서 지수 0x7ff
와 0이 아닌 가수부가 있는 부동 소수점 숫자는 NaN
이기 때문에 서로 다른 이진 표현을 가진 두 개의 부동 소수점 숫자를 생성할 수 있지만 둘 다 NaN
입니다. JavaScript에서 typed arrays를 사용하여 비트 수준 조작을 수행할 수 있습니다.
const f2b = (x) => new Uint8Array(new Float64Array([x]).buffer);
const b2f = (x) => new Float64Array(x.buffer)[0];
// NaN의 byte 표현을 가져옵니다.
const n = f2b(NaN);
// 부호 비트이고 NaN에 중요하지 않은 첫 번째 비트를 변경합니다.
n[0] = 1;
const nan2 = b2f(n);
console.log(nan2); // NaN
console.log(Object.is(nan2, NaN)); // true
console.log(f2b(NaN)); // Uint8Array(8) [0, 0, 0, 0, 0, 0, 248, 127]
console.log(f2b(nan2)); // Uint8Array(8) [1, 0, 0, 0, 0, 0, 248, 127]
조용히 NaN 탈출
NaN
은 수학적 연산을 통해 전파되므로 일반적으로 오류 조건을 감지하기 위해 계산이 끝날 때 한 번 NaN
을 테스트하는 것으로 충분합니다. NaN
이 자동으로 이스케이프되는 유일한 경우는 지수가 0
인 거듭제곱을 사용할 때입니다. 그러면 기본값을 검사하지 않고 즉시 1
이 반환됩니다.
NaN ** 0 === 1; // true
명세
Specification |
---|
ECMAScript® 2026 Language Specification # sec-value-properties-of-the-global-object-nan |