키가 모두 문자열 일 때 ES6 Map을 사용할 때 요점이 있습니까?


35

일반 객체 키는 문자열이어야하지만, Map어떤 유형의 키도 가질 수 있습니다.

그러나 실제로는 이것을 거의 사용하지 않습니다. 거의 모든 경우에 어쨌든 문자열을 키로 사용합니다. 아마 new Map()보다 느립니다 {}. 그렇다면 Map평범한 물체 대신에 그것을 사용하는 것이 더 좋은 다른 이유가 있습니까?


3
평소와 같이 MDN 은 좋은 비교를합니다.
Chris Hayes

1
참고로, Map 은 설정과 도착 모두에 더 빠릅니다 .
mpen

@mpen – jsperf가 다운되었습니다. 당신은시겠습니까 map.set('foo', 123)빨리보다는 수행 obj.foo = 123? 그렇다면 그것은 매우 놀라운 일입니다
callum

@callum Uhh..no, 긍정적이지 않습니다. 새로운 성능 테스트를 작성하려고 할 수 있습니다.
mpen

답변:


42

런타임 데이터 (캐시 등)를 저장하기 위해 Map일반 객체 ( {}) 보다 s를 선호하는 데는 몇 가지 이유가 있습니다 .

  1. .size속성은이지도에 몇 개의 항목이 있는지 알려줍니다.
  2. 다양한 유틸리티 메소드 - .clear(), .forEach()등;
  3. 기본적으로 반복자를 제공합니다!

함수 인수 전달, 구성 저장 등과 같은 다른 모든 경우는 모두 일반 객체를 사용하여 작성됩니다.

또한, 코드를 너무 일찍 최적화하려고하지 마십시오. 프로젝트에 성능 문제가 발생하지 않는 한 일반 객체와 맵의 벤치 마크를 수행하는 데 시간을 낭비하지 마십시오.


1
Javascript에서 사용하는 아이디 해시 코드 기능은 무엇입니까?
Pacerier

1
@Pacerier ===:)
gustavohenke

요즘지도는 평범한 물체보다 훨씬 빠릅니다.
jayarjo

@gustavohenke 사실이 아닙니다. MapSameValueZero 알고리즘을 사용합니다. developer.mozilla.org/en-US/docs/Web/JavaScript/…
lolmaus-Andrey Mikhaylov

@ lolmaus-AndreyMikhaylov 괜찮습니다.하지만 Map이것 또는 저것을 사용하여 s 에 대해 말했 습니까?
gustavohenke

4

확실하지 않지만 성능이지도를 사용하는 이유는 아니라고 생각합니다. 이 업데이트 된 jsperf 페이지를 살펴보십시오.

http://jsperf.com/es6-map-vs-object-properties/73

(최소한 문자열을 다룰 때) 객체는 기본 설정 및 가져 오기에 대한 맵보다 훨씬 빠릅니다.


2
이것이 성능 테스트를 작성하는 방법이 아닙니다.
Qix

6
유용한 의견을 작성하는 방법은 아닙니다. 제안 할 다른 방법론이 있으면 자유롭게 정교하게 작성하십시오. 구체적으로 이러한 테스트 작성 방식에 어떤 문제가 있습니까? 어떤 식 으로든 유효하지 않거나 도움이되지 않습니까?
starlogodaniel

9
마이크로 벤치 마크를 통해 테스트되는 언어 의미 / 구문은 하나의 변수 만 달라야합니다. 테스트는 반복 횟수에 따라 달라지며 결과 중 일부는 사용되지 않으므로 내부 루프 내용이 최적화됩니다. 일부 테스트는 변수를 미리 선언하는 반면, 다른 테스트는 for 루프와 함께 변수 선언을 가지므로 다른 성능 이상이 발생할 수 있습니다.
Qix

1
그렇습니다, 당신은 절대적으로 맞습니다. 내 방어에서 내 버전은 이전 버전에서 개선되었지만 사전 선언과 내부 루프 내용이 모두 최적화되지 않았다. 나는 초안을 개선 한 동료와 협력하고 있으며 jsperf.com/es6-map-vs-object-properties/88 과 같은 문제를 해결했다고 생각 합니다. 그러나 다른 데이터 구조에 대해 다른 루프 스타일을 갖는 것이 유효하다고 생각합니다. 실제 사용에서 사람들은 최상의 성능을 가진 루프 구조를 선택하게되며 Map과 Object는 다른 "최적의"루프 구조를 갖습니다. 어쨌든 캐치 주셔서 감사합니다.
starlogodaniel

알았어. 이제는 평범한 객체보다 느리지 만 최근 브라우저에서 크게 최적화되었습니다.
jayarjo

0

다른 답변은 객체와 Maps의 마지막 차이점을 언급하지 않습니다 .

Map오브젝트는 키 - 값 쌍을 보유하고 있는 키의 원래의 신청서를 기억한다 .

따라서 반복 할 때 Map 객체는 삽입 순서대로 키를 반환합니다.

MDN 에서 인용 , 광산 강조


이것이 Map최근 프로젝트에서 처음으로 사용하기로 결정한 주된 이유였습니다 . <table>각 속성이 특정 행으로 이동 하여에 표시 해야하는 일반 객체가 있습니다.

let productPropertyOrder = [ "name", "weight", "price", "stocked" ];

let product =
{
    name: "Lasagne",
    weight: "1kg",
    price: 10,
    stocked: true
}

Map원하는 키 순서에 따라 객체를 변환하는 함수를 작성했습니다 .

function objectToMap( obj, order )
{
    let map = new Map();

    for ( const key of order )
    {
        if ( obj.hasOwnProperty( key ) )
        {
            map.set( key, obj[ key ] );
        }
    }

    return map;
}

그런 다음 맵을 원하는 순서로 반복 할 수 있습니다.

let productMap = objectToMap( product, productPropertyOrder );

for ( const value of productMap.values() )
{
    let cell = document.createElement( "td" );
    cell.innerText = value;
    row.appendChild( cell );
}

물론 이것은 Map프로세스에서 생성하지 않고 속성 순서를 반복 할 때 표시 할 수 있기 때문에 약간 고안되었습니다 .

for ( const key of productPropertyOrder )
{
    if ( product.hasOwnProperty( key ) )
    {
        let value = product[ key ];
        // create cell
    }
}

그러나 그러한 객체가 배열되어 있고 많은 장소를 표시하려는 경우 먼저 모든 객체를 맵으로 변환하는 것이 좋습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.