配列を総当りの配列に変換する機会があったので、備忘録として残します。
やりたいこと
例えば以下のようなイメージです。
元の配列から全てのパターンの配列を作ります。
// 元の配列
const originalList = [
['柴犬', 'チワワ', 'コーギー'],
['茶', '白', '黒'],
['3', '5', '9'],
]
// 総当りに変換後の配列
const formattedList = [
['柴犬', '茶', '3'],
['柴犬', '茶', '5'],
['柴犬', '茶', '9'],
['柴犬', '白', '3'],
['柴犬', '白', '5'],
['柴犬', '白', '9'],
['柴犬', '黒', '3'],
['柴犬', '黒', '5'],
['柴犬', '黒', '9'],
['チワワ', '茶', '3'],
['チワワ', '茶', '5'],
['チワワ', '茶', '9'],
['チワワ', '白', '3'],
['チワワ', '白', '5'],
['チワワ', '白', '9'],
['チワワ', '黒', '3'],
['チワワ', '黒', '5'],
['チワワ', '黒', '9'],
['コーギー', '茶', '3'],
['コーギー', '茶', '5'],
['コーギー', '茶', '9'],
['コーギー', '白', '3'],
['コーギー', '白', '5'],
['コーギー', '白', '9'],
['コーギー', '黒', '3'],
['コーギー', '黒', '5'],
['コーギー', '黒', '9'],
]
コード
const originalList = [
['柴犬', 'チワワ', 'コーギー'],
['茶', '白', '黒'],
['3', '5', '9'],
]
// 全パターンの数を計算し、空の配列を作成
const arrayLength = originalList.map(x => x.length).reduce((a, b) => a * b, 1)
let formattedList = [... new Array(arrayLength)].map(() => [])
originalList.forEach((item, index) => {
// 対象の配列を追加する時の数を計算
const restList = originalList.slice(index + 1) // 対象の配列より後ろの配列
const addNumber = restList.map(item => item.length).reduce((a, b) => a * b, 1)
// addNumberずつ配列に追加していく
formattedList = formattedList.map((formattedItem, formattedIndex) => {
const addItemIndex = Math.floor(formattedIndex / addNumber) % item.length
// 追加するアイテム
const addItem = item[addItemIndex]
return [...formattedItem, addItem]
})
})
処理のイメージ図
originalList.forEach((item, index) => {
以降のループ部分のイメージ図です。
①->②->③の順番で追加していきます。
まとめ
処理が少しややこしいですが、全てのパターンの配列が作れました。
もっと良い方法があれば教えて下さい。
最後に
GoQSystemでは一緒に働いてくれる仲間を募集中です!
ご興味がある方は以下リンクよりご確認ください。