提问者:小点点

数组中大小N的组合


我正在尝试构建一个javascript函数来从数组中获取大小N的所有组合。假设我得到了:

const Xarray = ["19", "21","42","23",  "25", "28"];
const n = 4;

combinationsOfN(Xarray, n) =>

[ ["19", "21", "42", "23"],
  ["19", "21", "42", "25"],
  ["19", "21", "42", "28"],
  ["19", "21", "23", "25"],
  ["19", "21", "23", "28"],
  ["19", "21", "25", "28"],
…. ]

共3个答案

匿名用户

自己做这件事可能相当困难,因为我已经尝试过了。已经有一个js工具可以为您做到这一点,组合. js

/**
 * Copyright 2012 Akseli Palén.
 * Created 2012-07-15.
 * Licensed under the MIT license.
 */
function k_combinations(set, k) {
    var i, j, combs, head, tailcombs;
    if (k > set.length || k <= 0) {
        return [];
    }
    if (k == set.length) {
        return [set];
    }
    if (k == 1) {
        combs = [];
        for (i = 0; i < set.length; i++) {
            combs.push([set[i]]);
        }
        return combs;
    }
    combs = [];
    for (i = 0; i < set.length - k + 1; i++) {
        head = set.slice(i, i+1);
        tailcombs = k_combinations(set.slice(i + 1), k - 1);
        for (j = 0; j < tailcombs.length; j++) {
            combs.push(head.concat(tailcombs[j]));
        }
    }
    return combs;
}
function combinations(set) {
    var k, i, combs, k_combs;
    combs = [];
    for (k = 1; k <= set.length; k++) {
        k_combs = k_combinations(set, k);
        for (i = 0; i < k_combs.length; i++) {
            combs.push(k_combs[i]);
        }
    }
    return combs;
}
	
var array = ["19", "21","42","23", "25", "28"];

document.body.innerHTML += "<pre>" + JSON.stringify(k_combinations(array, 4), false, "\t") + "</pre>";

匿名用户

嗯,我不得不说我有时讨厌JS。我肯定讨厌push()。当你做功能时,你需要越来越多的对变异对象的引用。改变它调用的对象的方法应该返回对该对象的引用。

无论如何,代码看起来可能会简单得多,但是唉……这是它所能得到的。这只不过是一个简单的递归运行。看起来复杂的部分实际上是愚蠢的部分,例如;

a.slice(0,i).concat(a.slice(i+1))

实际上意味着删除索引位置i的元素并返回结果数组。当您需要将此功能用作单个指令或可链接指令作为函数的参数时,这似乎是唯一的方法。就像

(t.push(c),t)

指令。这意味着将c推送到t数组并返回t数组。愚蠢的push(c)会返回长度……我讨厌它。你给我参考人,如果需要,我可以从中获得长度。所以剩下的很容易理解。

所以我有两个解决方案,一个是排列,一个是组合。

var xarray = ["19", "21", "42", "23", "25", "28"],
         n = 4;

function getPermutations(a,n,s=[],t=[]){
  return a.reduce((p,c,i,a) => { n > 1 ? getPermutations(a.slice(0,i).concat(a.slice(i+1)), n-1, p, (t.push(c),t))
                                       : p.push((t.push(c),t).slice(0));
                                 t.pop();
                                 return p},s)
}
document.write("<pre>" + JSON.stringify(getPermutations(xarray,n),null,2) + "</pre>");

匿名用户

我提供了两种解决方案,第一种解决方案的结果包括任何地方的项目。

function combine(array, length) {
    function c(l, r) {
        var i, ll;
        if (r.length === length) {
            result.push(r);
            return;
        }
        for (i = 0; i < l.length; i++) {
            ll = l.slice();
            c(ll, r.concat(ll.splice(i, 1)));
        }
    }
    var result = [];
    c(array, []);
    return result;
}

document.write('<pre>' + JSON.stringify(combine(["19", "21", "42", "23", "25", "28"], 4), 0, 4) + '</pre>');