読者です 読者をやめる 読者になる 読者になる

CODEPREPからのお知らせ

CODEPREP運営事務局の公式ブログです。

エクササイズ解説 - JavaScriptの配列操作を理解する

CODEPREP エンジニアの小西です。

水曜日にリリースした配列Book、みなさん楽しんでいただけているでしょうか?

新機能、「エクササイズ」を投入したこのBook、事前に予想はしていたんですが実にコンプ率が低いです。

実に30%以上の人がエクササイズで離脱中。コンプ者は社内で勇者として讃えられています。(^^;

このエントリでは配列Bookのエクササイズ3問について、模範回答と解説を提示します。自力で解きたい人はこの先は立ち入り禁止です。

問1. 値の変換

配列内の各要素(数値)を2倍した配列を返す。という問題です。

この問題についてはHINTに解答を書いてあります。

function toDouble(array) {
  return array.map(v => v * 2);
}

mapを使って、個別の値を2倍したものを返すようにすればOKです。

ちなみにmapを使わず古典的なforを使った書き方をした場合は以下のようになります。

function toDouble(array) {
  for (var i=0; i<array.length; i++) {
    array[i] = array[i] * 2;
  }
  return array;
}

ただし、このやり方では元の配列の内容が書き換わってしまうので、さらに改良して以下のようにした方が良いでしょう。

function toDouble(array) {
  var ret = [];  
  for (var i=0; i<array.length; i++) {
    ret.push(array[i] * 2);
  }
  return ret;
}

先の例との違いは、新しく空の配列retを宣言して、そこに各要素を2倍した値を追加していっていることです。

この例は最初のmapを使った例と処理内容は同じですが、mapを使った方が圧倒的に記述量が少ないことがわかると思います。

慣れないうちはfor文の方が分かりやすく感じますが、経験を積んでくるとだいたい皆forと書くのが嫌になります。(^^;

問2 ソート

6-8で同じことをやっているので、そんなに難しくないかと思いましたが、ここで離脱した人も多いようです。 解答は以下のようになります。

function sort(array) {
  array.sort((a, b) => a.length > b.length ? -1 : 1);  
  return array;
}

sortメソッド内の関数で各要素の長さを比較して、長い方が先に来るようにしています。

厳密に言えば、a.length === b.lengthの場合は0を返した方が良いですが、結果は同じなのでここでは省略しています。

sortメソッドは返り値を返さないのでsortした後に別途arrayをreturnしなければならない点に注意が必要です。

上の例では元の配列自体がソートされますが、もしも最初の配列の内容を変更してはならないという要件があるならば以下のように配列をコピーしてからソートします。

function sort(array) {
  var ret = [].concat(array);
  ret.sort((a, b) => a.length > b.length ? -1 : 1);  
  return ret;
}

配列をコピーする場合はconcatメソッドが元の配列を変更せずに新しい配列を生成する性質を利用して、空の配列にconcatすることで実現できます。

問3 最大値の取得

まずはreduceを使った例から。

function max(array) {
  return array.reduce((a, b) => a > b ? a : b);
}

配列内の各要素を比較して値の大きい方を返しています。 これを配列の先頭から最後まで繰り返すことで最大値を得ることができます。

非常に簡潔ですが、おそらくこの処理は初学者には少し難しいと思います。(reduceが自由自在に使いこなせるようになれば、もはやこのBookには用は無いです。)

なので、慣れないうちはforを使って以下のように書いても構いません。

function max(array) {
  var ret = 0;
  for (var i=0; i<array.length; i++) {
    if (array[i] > ret) {
      ret = array[i];
    }
  }
  return ret;
}

最初に0を最大値として置いておいて、配列内の値がそれよりも大きければそれを置き換えていく処理になります。

タイプ量は多くなりますが、これはこれで分かりやすいので特に問題はありません。


以上、エクササイズ解説でした。

エクササイズについては難易度の調整など、まだ手探りな部分もありますが、これからも面白い問題を提供していく予定なので、是非コンプ目指してトライしてみてください。