2016-10-10 4 views
5

전달 된 인수가 Map 인 경우 true을 반환하는 함수를 작성했습니다.개체가 JavaScript의지도인지 확인

짐작 하시겠지만 typeof new Map()object 문자열을 반환하며 편리한 Map.isMap 메서드는 제공하지 않습니다. 여기

는 내가 지금까지 무엇을 가지고 :

function isMap(v) { 
 
    return typeof Map !== 'undefined' && 
 
    // gaurd for maps that were created in another window context 
 
    Map.prototype.toString.call(v) === '[object Map]' || 
 
    // gaurd against toString being overridden 
 
    v instanceof Map; 
 
} 
 

 
(function test() { 
 
    const map = new Map(); 
 

 
    write(isMap(map)); 
 

 
    Map.prototype.toString = function myToString() { 
 
    return 'something else'; 
 
    }; 
 

 
    write(isMap(map)); 
 
}()); 
 

 
function write(value) { 
 
    document.write(`${value}<br />`); 
 
}

지금까지 너무 좋아 하지만 프레임 사이에 맵을 테스트 할 때 toString()를 오버라이드 (override) 된 경우, isMap이 (I do understand why) 실패합니다. 예를 들어

:

<iframe id="testFrame"></iframe> 
<script> 
    const testWindow = document.querySelector('#testFrame').contentWindow; 
    // false when toString is overridden 
    write(isMap(new testWindow.Map())); 
</script> 

Here is a full Code Pen Demonstrating the issue

모두 toString가 무시되고지도 객체가 다른 프레임에서 유래 때 true 을 반환하도록 isMap 함수를 작성하는 방법이 있나요?

+0

@Bergi, 어떻게 이것을 복제합니까? 당신의 답변 옹호자는 'instanceof' 내 질문을 사용하여'instanceof' 또한 당신이 세트에서 확인하고있는 내부 메서드와 함께 가지고있는 문제점을 말하고,'Map' 프로토 타입에는 적용되지 않습니다. – robbmj

+0

세트와 맵은 정확히 같습니다. 나는 canonical이되도록 답을 더 잘 편집 할 것입니다. – Bergi

+0

@Bergi 내 의견에 위의 편집을 참조하십시오. – robbmj

답변

2

Object.prototype.toString.call(new testWindow.Map)을 확인할 수 있습니다.

오버라이드 된 경우 운이 좋지 않은 것 같습니다.

+0

흥미 롭다. 나는 그런 생각을하지 못했다. 나는 그것이 확실한 추가 단계를 추가한다고 생각합니다. – robbmj

+0

'toString'이 오버라이드되는 것에 대해 걱정하지 않아도됩니다. (처음에는 캐시 할 수 있지만,'Symbol.toStringTag'에 대해서는). – Bergi