【发布时间】:2021-06-05 19:39:52
【问题描述】:
在尝试解决以下问题:
Generate all combinations of an array of string.
Ex: Input: ['A', 'T', 'C', 'K']
Output: [
'ATCK', 'ATC', 'ATK',
'AT', 'ACK', 'AC',
'AK', 'A', 'TCK',
'TC', 'TK', 'T',
'CK', 'C', 'K',
''
]
我有以下代码:
function getSpellableWords(arr) {
const res = [];
// helper(arr, res, 0, '');
helper(arr, res, 0, []);
return res;
}
function helper(arr, res, i, slate) {
const char = arr[i];
console.log(i, 'i')
if(i === arr.length) {
res.push(slate.join(''));
return;
}
// slate = slate + char;
slate.push(char)
console.log(slate, 'slate')
helper(arr, res, i+1, slate);
slate.pop()
helper(arr, res, i+1, slate);
}
getSpellableWords(['A', 'T', 'C', 'K']);
我的问题是:
如果我在代码中删除以下行:
helper(arr, res, i+1, slate);
一旦i 等于5(即array.length),代码将在将slate 推入res 后停止。但是,如果我保留该行,则会设置一个调用堆栈,因此i 将从 1->5 上升,然后逐渐弹出到 4 然后 3 然后回到 4 等等.为什么会这样?
澄清:所以我知道对于每个递归调用,都会生成另一个i 变量。然而,我期待第二次递归调用也再次从 1->4 生成i,但这一次不是线性递增,而是回溯。为什么第一次调用没有回溯,为什么第一次调用只生成第一个结果时,第二次调用会生成其余结果?
【问题讨论】:
-
因为
i是一个局部变量,helper的每次新执行都会有自己的i版本,它可以有不同的值。当递归调用返回并且调用代码继续时,它自己的i是相关的(再次)。 -
所以我知道对于每个递归调用,都会生成另一个
i变量。然而,我期待第二次递归调用也能再次从 1->4 生成i,但这一次不是线性递增,而是回溯。为什么第一次调用没有回溯,为什么第一次调用只生成第一个结果时第二次调用生成其余结果? -
你为什么期望递归调用改变
i?它永远不会。如果您查看代码,您会发现helper中没有对i的赋值。唯一发生的事情是i+1被传递给递归调用,在那里它将成为仅存在于该递归执行上下文中的局部变量i的初始值和唯一值。当该执行终止时,我们回到调用者那里,那里仍然存在未更改的i。 -
你能举个例子吗?所以在这种情况下,在第一个函数调用返回后,
i在 5 处停止。那么接下来会发生什么?现在将1添加到i以使其成为6? -
发表了答案。
标签: javascript arrays recursion backtracking callstack