JavaScript排列问题

JavaScript排列问题,javascript,Javascript,我正在使用递归处理置换str,但它不能跳出for循环。 有人能帮我写这段代码吗? 先谢谢你 var置换=[]; var-words=[]; 函数getPerms(str){ 如果(str.length==0){ 排列。推送(“”); 返回置换; } var first=str.charAt(0);//获取第一个字符 var rementer=str.slice(1);//删除第一个字符 words=getPerms(提醒); for(var i=0;i

我正在使用递归处理置换str,但它不能跳出for循环。 有人能帮我写这段代码吗? 先谢谢你

var置换=[];
var-words=[];
函数getPerms(str){
如果(str.length==0){
排列。推送(“”);
返回置换;
}
var first=str.charAt(0);//获取第一个字符
var rementer=str.slice(1);//删除第一个字符
words=getPerms(提醒);
for(var i=0;i对于(var j=0;j问题可能是在最后一次调用时,您返回排列,然后将其分配给单词(您在这里所做的类似于单词=排列),但这不是通过复制进行分配,而是通过引用进行分配(因为
单词
排列
属于同一范围+它们是数组),因此从上一次调用开始,它们是相同的对象(当代码取消堆栈上一次调用时,它们现在是相同的对象)。为了进行说明,请执行以下代码。您将看到,当您修改
单词时,您就修改了
排列

var permutations = [];
var words = [];
function getPerms(str) {

    if(str.length == 0) {
        permutations.push("");
        return permutations;
    }
    var first = str.charAt(0);//get the first char
    var reminder = str.slice(1);//remove the first char
    words = getPerms(reminder);
    words.push("foo");
    console.log( permutations);
    return permutations;
}
function insertCharAt(word, c, i) {
    var start = word.slice(0, i);
    var end = word.slice(i);
    var result = start + c + end;
    return result;
}
console.log(getPerms("abc"));
在你的代码中,你循环单词并同时修改排列(因此,根据前面的解释,这就像同时修改
单词
和循环
单词
),正是这些东西创造了无限循环。 我没有检查你的算法是否有效,我只是指出代码的问题。 所以我想你想要的是:

     function getPerms(str) {

        var permutations = [];
        var words = [];
        if(str.length == 0) {
            permutations.push("");
            return permutations;
        }
        var first = str.charAt(0);//get the first char
        var reminder = str.slice(1);//remove the first char
        words = getPerms(reminder);
        for(var i = 0; i < words.length; i++) {
            for(var j = 0; j <= words[i].length; j++) {
                var s = insertCharAt(words[i], first, j);
                permutations.push(s);
            }
        }
        return permutations;
    }
    function insertCharAt(word, c, i) {
        var start = word.slice(0, i);
        var end = word.slice(i);
        var result = start + c + end;
        return result;
    }
    console.log(getPerms("abc"));
函数getPerms(str){ var置换=[]; var-words=[]; 如果(str.length==0){ 排列。推送(“”); 返回置换; } var first=str.charAt(0);//获取第一个字符 var rementer=str.slice(1);//删除第一个字符 words=getPerms(提醒); for(var i=0;i对于(var j=0;j您的代码很好,除了一个问题:

变量
permutations
不应该是全局变量。通过查看
permutations.push(“”),可以清楚地看出这是错误的
。这是最深层递归中的一个临时结果,但显然这不应该出现在最终结果中。然而,由于
置换
是全局的,您永远不会从中删除任何内容,
置换
将保留此

问题变得更糟,因为
单词
从递归调用中获取
排列
引用,因此它们指向非常相同的数组!因此,不仅重复所有以前的结果,而且在添加额外字符后,它们会再次被推入相同的
排列
数组as
words
给了你一个无止境的循环:你添加到你正在迭代的数组中,因此永远不会结束

解决方案很简单:

使
permutations
成为
getPerms
函数的局部变量。当您使用
words
时,为什么不对其执行相同的操作呢

函数getPerms(str,depth=0){ var-words=[]; var置换=[]; 如果(str.length==0){ 排列。推送(“”); 返回置换; } var first=str.charAt(0);//获取第一个字符 var rementer=str.slice(1);//删除第一个字符 words=getPerms(提醒,深度+1); for(var i=0;i对于(var j=0;j)您能描述一下您想要实现什么以及它是如何出错的吗?“使用递归的置换str”不是描述性的。我们可以假设,对于“abc”,您想要“cba”?
[“abc”、“acb”、“bac”、“bca”、“cab”、“cba”]