我试图理解下面的递归函数,以自学递归。我试图解释它的过程低于预期的输出和函数本身。我想念什么?我没有看到从“abc”到“acb”的过程。我的理解使我从'abc'变成了'bac'。
example usage:
var anagrams = allAnagrams('abc');
console.log(anagrams); // [ 'abc', 'acb', 'bac', 'bca', 'cab', 'cba' ]
var allAnagrams = function(string) {
var uniqueOutput = {};
(function anagram(ana, str) {
// could have also written this as: if(!str)....
if (str === '') {
uniqueOutput[ana] = 1;
}
//recursive call for the length of the anagram.
for (var i = 0; i < str.length; i++) {
anagram(ana + str[i], str.slice(0, i) + str.slice(i + 1));
console.log(ana);
}
})('', string);
console.log(uniqueOutput)
return Object.keys(uniqueOutput);
};
// you are calling the recursive function like this: anagram([anagram=]'', [string=]'abc')
// so the base case is not met on the first iteration since the string isn't empty
// first iteration: i = 0
// anagram('' + 'a' + 'bc' [from str.slice(0 +1)]) ---> resolves to "abc") ---> anagram("abc")
//second iteration: i = 1. we are still in the original call from line 37.
// here below, does "ana" stay as '' since we are still inside the initial recursion call?
//anagram('' + b + a + c) ---- resolves to "bac" ---> anagram("bac")
//third and last iteration iteration: i = 2
//anagram(" " + c + c) ----> anagram("cc") ? not a valid result.
我的新的,正确的(我认为)解释是:
//initial input: anagram("", "abc")
//STEP 1: enter the function --> i = 0 for original string "abc"
//anagram("" + "a", "bc") ----> anagram("a", "bc")
//STEP 2: loop through the new, modified string, which is now "bc"
//var i = 0;
//anagram("a" + "b", "c")---> anagram("ab", "c")
//anagram("ab" + "c", [nothing here])
//base case hit, so uniqueOutput["abc"] = 1;
//var i = 1; --> this applies to the string "bc". the loop gets reset to i = 0 once you have a new string to worth with (like below, with "b")
//anagram("a" + "c", "b")
//anagram("ac", "b")
//anagram("ac" + "b", "" )
//base case hit, so uniqueOutput["acb"] = 1;
//STEP 3: increment up on the original string input ("abc") --> so now you are dealing with str[i] === b
//var i = 1;
//anagram("" + "b", "a" + "c")
//anagram("b", "ac") ---> now we need to loop through "ac"!
//anagram("b" + "a", "c")
//anagram("ba", "c")
//anagram("bac", "")---> base case hit, uniqueOutput["bac"] = 1;
//anagram("b", "ac")
//anagram("b" + "c", "a") ---> anagram("bc", "a")
//anagram("bca", "") ---> base case hit, uniqueOutput["bca"] = 1;
//STEP 4: increment up on the original string input ("abc") ---> str[i] === c
//var i = 2;
//anagram ("" + "c", "ab")---> anagram("c", "ab")
//now we need to loop through "ab!" c's index stays the same.
//anagram("c" + "a", "b") ---> anagram("ca", "b")
//anagram("cab", '')---> uniqueOuput["cab"] = 1;
//anagram("c" + "b", "a") ---> anagram("cb", "a")
//anagram("cba", "")----> uniqueOutput["cba"] = 1
最佳答案
根据您上面的评论:
// first iteration: i = 0
// anagram('' + 'a' + 'bc' [from str.slice(0 +1)]) ---> resolves to "abc") --->
实际上在
i = 0
上,传递给anagram
的参数是:anagram('' + 'a', '' + 'bc');
结果为:
anagram('a', 'bc');
然后,在对
anagram
的调用中,我们再次遍历str
,现在它只是“bc”。这将导致对anagram
的2次调用,这将是anagram('a' + 'b', '' + 'c'); // i = 0
anagram('a' + 'c', 'b' + ''); // i = 1
评估结果为:
anagram('ab', 'c');
anagram('ac', 'b');
这些调用中的第二个将导致使用以下参数再次调用
anagram
:anagram('acb', '');
由于
uniqueOutput
现在为空,因此已添加到str
中。只有执行完所有代码后,代码才会返回到
anagram
和i
的最外层调用,具体取决于您的注释://second iteration: i = 1. we are still in the original call from line 37.