Array.prototype.map()

概要

与えられた関数を配列のすべての要素に対して呼び出し、その結果からなる新しい配列を生成します。

構文

arr.map(callback[, thisArg]);

パラメータ

callback
現在の配列の要素から新しい配列の要素を生み出すための関数。
currentValue
現在処理中の配列内の要素。
index
現在処理中の配列内の要素のインデックス。
array
map を実行している配列。
thisArg
callback を実行するときに this として使用するオブジェクト。

説明

map は、与えられた callback 関数を配列の各要素に対して順番に一度ずつ呼び出し、その結果から新しい配列を生成します。callback は値が代入されている配列のインデックスに対してのみ呼び出されます。つまり、すでに削除されたインデックスや、まだ値が代入されていないインデックスに対しては呼び出されません。

callback は、要素の値、要素のインデックス、走査されている Array オブジェクトという 3 つの引数をともなって呼び出されます。

mapthisObject パラメータが与えられると、callback の呼び出しのたびにそのオブジェクトが this として使用されます。thisObject が与えられないか null だと、callback に結び付けられたグローバルオブジェクトが代わりに使用されます。

map は呼び出された配列を変化させません。

map によって処理される要素の範囲は、callback が最初に呼び出される前に設定されます。map の呼び出しが開始された後に追加された要素に対しては、callback は実行されません。既存の配列要素が変更されたり、削除された場合、callback に渡される値は map がそれらを訪れた時点での値になり、filter が削除された要素を訪問することはありません。

互換性

map は ECMA-262 標準に最近追加されたものである為、標準準拠を謳う実装中に存在しない場合があります。次のコードをスクリプトの先頭に挿入すると、map がネイティブでサポートされていない ECMA-262 実装でも map を使用できるようになります。このアルゴリズムは ECMA-262 第 5 版で指示されたアルゴリズムと全く同じものです。ObjectTypeErrorArray はそれぞれオリジナルの値を持ち、 またそれらの callback.callFunction.prototype.call のオリジナルの値として評価されます。

// Production steps of ECMA-262, Edition 5, 15.4.4.19
// Reference: http://es5.github.com/#x15.4.4.19
if (!Array.prototype.map) {
  Array.prototype.map = function(callback, thisArg) {

    var T, A, k;

    if (this == null) {
      throw new TypeError(" this is null or not defined");
    }

    // 1. Let O be the result of calling ToObject passing the |this| value as the argument.
    var O = Object(this);

    // 2. Let lenValue be the result of calling the Get internal method of O with the argument "length".
    // 3. Let len be ToUint32(lenValue).
    var len = O.length >>> 0;

    // 4. If IsCallable(callback) is false, throw a TypeError exception.
    // See: http://es5.github.com/#x9.11
    if ({}.toString.call(callback) != "[object Function]") {
      throw new TypeError(callback + " is not a function");
    }

    // 5. If thisArg was supplied, let T be thisArg; else let T be undefined.
    if (thisArg) {
      T = thisArg;
    }

    // 6. Let A be a new array created as if by the expression new Array(len) where Array is
    // the standard built-in constructor with that name and len is the value of len.
    A = new Array(len);

    // 7. Let k be 0
    k = 0;

    // 8. Repeat, while k < len
    while(k < len) {

      var kValue, mappedValue;

      // a. Let Pk be ToString(k).
      //   This is implicit for LHS operands of the in operator
      // b. Let kPresent be the result of calling the HasProperty internal method of O with argument Pk.
      //   This step can be combined with c
      // c. If kPresent is true, then
      if (k in O) {

        // i. Let kValue be the result of calling the Get internal method of O with argument Pk.
        kValue = O[ k ];

        // ii. Let mappedValue be the result of calling the Call internal method of callback
        // with T as the this value and argument list containing kValue, k, and O.
        mappedValue = callback.call(T, kValue, k, O);

        // iii. Call the DefineOwnProperty internal method of A with arguments
        // Pk, Property Descriptor {Value: mappedValue, Writable: true, Enumerable: true, Configurable: true},
        // and false.

        // In browsers that support Object.defineProperty, use the following:
        // Object.defineProperty(A, Pk, { value: mappedValue, writable: true, enumerable: true, configurable: true });

        // For best browser support, use the following:
        A[ k ] = mappedValue;
      }
      // d. Increase k by 1.
      k++;
    }

    // 9. return A
    return A;
  };      
}

例: 配列内の単語 (文字列) を複数形にする

次のコードは、名詞の単数形からなる配列を元にして、それらの名詞の「複数形」からなる配列を生成してコンソールに表示します。

function fuzzyPlural(single) {
  var result = single.replace(/o/g, 'e');  
  if( single === 'kangaroo'){
    result += 'se';
  }
  return result; 
}

var words = ["foot", "goose", "moose", "kangaroo"];
console.log(words.map(fuzzyPlural));

// 変換前 : ["foot", "goose", "moose", "kangaroo"]
// 変換後 : ["feet", "geese", "meese", "kangareese"]

例: 数値の配列を平方根の配列にマッピングする

次のコードは、数値からなる配列を取り、それらの数値の平方根からなる新しい配列を生成します。

var numbers = [1, 4, 9];
var roots = numbers.map(Math.sqrt);
// roots   の内容は [1, 2, 3] となる
// numbers の内容は [1, 4, 9] のまま

例: 汎用的な map の使用

以下の例は、各文字を表す ASCII エンコードのバイトの配列を得るために 文字列 に map を使う方法を示しています。:

var map = Array.prototype.map
var a = map.call("Hello World", function(x) { return x.charCodeAt(0); })
// a の内容は [72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100] となる

ブラウザ実装状況

機能 Firefox (Gecko) Chrome Internet Explorer Opera Safari
基本サポート (有) (有) 9 (有) (有)
機能 Firefox Mobile (Gecko) Android IE Mobile Opera Mobile Safari Mobile
基本サポート ? ? ? ? ?

Kangax's compat tables に基づく。

ドキュメントのタグと貢献者

Contributors to this page: teoli, tatsuyaoiw, ethertank, Potappo, Shoot
最終更新者: teoli,
サイドバーを隠す