簡體   English   中英

JavaScript 算法問題:如何使用遞歸來解決這樣的組合問題?

[英]JavaScript Algorithms question: how do I use recursion to solve such a combination problem?

我們有一個看起來像這樣的數字字母 map

const digitsLetters = new Map([
    ["2", ['a', 'b', 'c']],
    ["3", ['d', 'e', 'f']],
    ["4", ['g', 'h', 'i']],
    ["5", ['j', 'k', 'l']],
    ["6", ['m', 'n', 'o']],
    ["7", ['p', 'q', 'r', 's']],
    ["8", ['t', 'u', 'v']],
    ["9", ['w', 'x', 'y', 'z']],
  ]);

問題要求我們返回數字可以代表的所有可能的字母組合。 例如,如果我們有"23" ,那么第一個數字2映射到['a', 'b', 'c']和第二個數字映射到['d', 'e', 'f']我們最終得到["ad","ae","af","bd","be","bf","cd","ce","cf"]

我找到了一種在兩個 arrays 之間產生這種組合的方法。

// this will output ["ad","ae","af","bd","be","bf","cd","ce","cf"]
['a', 'b', 'c'].map(char1 => ['d', 'e', 'f'].map(char2 => char1 + char2)).flat(2)

所以我想我可以遞歸地將這個算法應用於這樣的數字,直到我打到最后一個。 我認為這是可行的。 但是,我很難實施該解決方案。 有人可以幫幫我嗎?

您基本上可以使用map方法從您的Map數據中獲取基於字符串參數的數組,並實現笛卡爾積算法。

 const data = new Map([ ["2", ['a', 'b', 'c']], ["3", ['d', 'e', 'f']], ["4", ['g', 'h', 'i']], ["5", ['j', 'k', 'l']], ["6", ['m', 'n', 'o']], ["7", ['p', 'q', 'r', 's']], ["8", ['t', 'u', 'v']], ["9", ['w', 'x', 'y', 'z']], ]); function f(str, map) { const result = []; const arr = str.split('').map(c => map.get(c)) function r(data, n = 0, prev = []) { if (n === data.length) { return result.push(prev.slice()) } for (let i = 0; i < data[n].length; i++) { prev[n] = data[n][i] r(data, n + 1, prev.slice()) } } r(arr) return result; } console.log(f('23', data)) console.log(f('358', data))

像這樣的東西

 const digitsLetters = new Map([ ["2", ['a', 'b', 'c']], ["3", ['d', 'e', 'f']], ["4", ['g', 'h', 'i']], ["5", ['j', 'k', 'l']], ["6", ['m', 'n', 'o']], ["7", ['p', 'q', 'r', 's']], ["8", ['t', 'u', 'v']], ["9", ['w', 'x', 'y', 'z']], ]); const foo = (arr, result = []) => { if (arr.length === 0) return result; const value = arr.shift(); if (result.length === 0) return foo(arr, value); const newResult = []; result.forEach((el) => { value.forEach((el2) => { newResult.push(el + el2); }); }); return foo(arr, newResult); }; const boo = (str) => foo(str.split('').map((symbol) => (digitsLetters.get(symbol)))); console.log(boo('')); console.log(boo('2')); console.log(boo('23')); console.log(boo('232'));

讓我們用一個例子來考慮笛卡爾積f(E, F)

假設E就像['12', '13']

然后你得到候選人ab ,我將其命名為F = ['a', 'b']

f(E, F) = E x F將給出['12a', '13a', '12b', '13b']

(注意ExF是相同類型的E ,一個字符串數組)

現在你可以遞歸給定的數字

g([digit, ...otherDigits], E) => {
  candidates = m.get(digit)
  EF = cartesianProduct(E, candidates)
  return g(otherDigits, EF)
}

請注意, E上的初始化不應是空數組,而是長度為 1 的數組,其唯一元素是“中性”元素(字符串為空字符串)

 const data = new Map([ ["2", ['a', 'b', 'c']], ["3", ['d', 'e', 'f']], ["4", ['g', 'h', 'i']], ["5", ['j', 'k', 'l']], ["6", ['m', 'n', 'o']], ["7", ['p', 'q', 'r', 's']], ["8", ['t', 'u', 'v']], ["9", ['w', 'x', 'y', 'z']], ]); const f = (E, F) => E.flatMap(e => F.map(f => e + f)) const g = ([digit, ...otherDigits], E=['']) => digit? g(otherDigits, f(E, data.get(digit))): E console.log(g('23'.split(''))) console.log(g('234'.split('')))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM