Я хотел бы создать перестановки над Set (0..n) в Javascript.
Я борюсь с методами Array: некоторые из них, например map
, возвращают новый массив, который может быть дальше модифицированный, другие как forEach
нет. Чтобы кодировать перестановки, я мог сделать это только с улучшением прототипа Array:
Object.defineProperty(Array.prototype, "chain", {
value: function(method, arg) {
this[method].call(this, arg);
return this;
}
});
Object.defineProperty(Array.prototype, "value", {
value: value => value // to value value ;-)
});
Только тогда я смог закодировать перестановки:
let perm = (n) =>
n==0 ? [[0]] :
perm(n-1).reduce((acc, cur) =>
cur.chain("forEach", (_, i) =>
acc.chain("push", [...cur.slice(0,i), n, ...cur.slice(i)])
).value(acc).chain("push", [...cur,n])
,[])
Тест:
console.log(perm(2));
Так возможно ли в ES6 (без добавления в прототип Array) кодировать перестановки над Set (или любым объектом, подобным массиву) чисто функциональным способом?
Я не хочу изнасиловать Javascript (как тогда делал jQuery), чтобы заставить его использовать какую-то ненативную парадигму, но я бы хотел полностью понять ее потенциал в функциональном поле.