I want to count the average value of the odd numbers from a list of numbers. I have a starting code to count the average, but I don't know how can I choose only the odd numbers from the list?
Here is my code:
var numberArray = [1,2,3,4,5,6], thisTotal=0,thisAverage=0;
for (var i=0; i<numberArray.length; i++) {
thisTotal += numberArray[i];
}
thisAverage = (thisTotal/numberArray.length);
alert(thisAverage)
You can use a filter function to return only the odd numbers:
var oddArray = numberArray.filter(function(val) {
return val % 2 !== 0;
});
Full example:
var numberArray = [1, 2, 3, 4, 5, 6];
var thisTotal = 0;
var thisAverage = 0;
var oddArray = numberArray.filter(function(val) {
return val % 2 !== 0;
});
console.log(oddArray); // [1, 3, 5]
var thisTotal = oddArray.reduce(function(accumulator, currentValue) { return accumulator + currentValue;
});
console.log(thisTotal); // 1 + 3 + 5 => 9
var thisAverage = thisTotal / oddArray.length;
console.log(thisAverage); // 9 / 3 => 3
var numberArray=[1,2,3,4,5,6], thisAverage=0,oddlength=0;
for(var i=0;i<numberArray.length;i++)
{
if(numberArray[i]%2!==0){
thisAverage+=numberArray[i];
oddlength++;
}
}
thisAverage=(thisAverage/oddlength);
alert(thisAverage)
Well, you can get what you want by this.
var numberArray=[1,2,3,4,5,6], thisTotal=0,thisAverage=0;
for(var i=0; i < 3; i++) {
thisTotal += numberArray[i * 2];
thisAverage= (thisTotal/numberArray.length);
}
console.log(thisAverage);
or if you want general solution, use this.
var numberArray=[1,2,3,4,5,6,7,8,...on and on], thisTotal=0,thisAverage=0;
for(var i=0; i < Math.ceil(numberArray.length() / 2); i++) {
thisTotal += numberArray[i * 2];
thisAverage= (thisTotal/numberArray.length);
}
console.log(thisAverage);
hope my code be helpful :)
You can use the function reduce to add and count.
var numberArray = [1, 2, 3, 4, 5, 6],
result = numberArray.reduce((a, n) => {
if (n % 2 !== 0) {
a.sum += n;
a.count++;
}
return a;
}, {sum: 0, count: 0}),
average = result.sum / result.count;
console.log(average);
Assuming the numbers are in an array, you can do this:
var numbers = [1, 2, 3, 4, 5, 6];
var info = numbers.filter(function(n) { return n % 2 !== 0})
.reduce(function(acc, item) {
return {sum: acc.sum + item, count: acc.count + 1}
}, {sum: 0, count: 0});
var avg = info.sum / info.count;
This example uses filter and reduce methods, which are declarative and more clear.
filter returns a new array with the items for which the function returns true, and then reduce, for each item, updates an 'accumulator'. The accumulator can be anything, and in this case is an object with the sum of the numbers and their count. For each item, we add add the current number to the sum property and add 1 to count. Finally, we just devide sum by count and done.
var acc = 0, oddCount = 0;
for(var i = 0; i < numberArray.length; i++) {
if(numberArray[i] % 2 !== 0) {
acc += numberArray[i];
oddCount++;
}
}
return acc / oddCount;
You can create a new array and store odd values in that array and after that you can apply your logic to that array.
var a=[1,2,3,4,5,6,10,11];
var ar=[];
for (var i = 0; i < a.length; i++) {
if(a[i] % 2 !== 0) {
ar.push(a[i]);
}
}
console.log(ar);
var numberArray=[1,2,3,4,5,6,7,8];
var count = 0;
var result = 0;
for (let i = 0; i <= (numberArray.length-1); i++)
{
if (numberArray[i] % 2 != 0)
{
result += numberArray[i];
count++;
}
}
alert(result / count);
Related
Input Arr=[1,2,3,4,5,6,7,8,9,10]
Expected output:-
Arr1 = [1,2,3,4,5,6,7] = 28
Arr2 = [8,9,10] = 27
The sum of arrays should be almost the same..
It can also be 3 or more parts
How to achieve this via custom function?
let Arr = [1,2,3,4,5,6,7,8,9,10]
const numberOfParts = 2
function SplitArr(Array, Parts){
/* ... */
}
let result = SplitArr(Arr,numberOfParts)
/* result should be [[1,2,3,4,5,6,7],[8,9,10]] */
/* output can be in any format as long as it can get the parts */
I think you can't do that directly by JS functions.
You have to create a custom function to achieve this.
I have considered dividing the array into 2 equal parts.
You can't always split the array equally. Here in this array, you can't partition array into more than 2 subparts, otherwise it will give more than 3 parts as some of the elements are present there having sum more than the partitioned Sum.
Note: I treated the array to be sorted, otherwise it depends on the usecase.
Note: I have updated the old implementation based on the updated question requirement
let arr=[1,2,3,4,5,6,7,8,9,10]
function splitArrayEqually(arr, parts=2){
//get the total sum of the array
let sum = arr.reduce((currentSum, value) => currentSum+value ,0);
//get the half sum of the array
let partitionedSum = Math.ceil(sum/parts);
let start=0, end=0, currentSum=0;
let splittedArray=[];
//get the index till which the sum is less then equal partitioned sum
while(end < arr.length){
if(currentSum+arr[end] > partitionedSum){
splittedArray.push(arr.slice(start,end));
start = end; //start new window from current index
currentSum = 0; //make sum =0
}
//add current end index to sum
currentSum += arr[end];
end++;
}
splittedArray.push(arr.slice(start));
return splittedArray;
}
splitted = splitArrayEqually(arr,3);
console.log(splitted)
let Arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
const numberOfParts = 3
function sumOfArray(arr) {
if (arr) {
if (arr.length > 0) {
let sum = 0
for (let i = 0; i < arr.length; i++) sum += arr[i]
return sum
} else {
return 0
}
} else {
return 0
}
}
function SplitArr(Array, Parts) {
let lastIndex = 0
let result = []
function getReamingSum(arr) {
let psum = sumOfArray(Array.slice(lastIndex)) / Parts
console.log('psum ' + psum)
return psum + Parts
}
let psum = getReamingSum(Array)
for (let j = 0; j < Parts; j++) {
let total = 0
for (let i = 0; i < Array.length; i++) {
if (i >= lastIndex) {
total += Array[i]
if (total < psum || j === Parts - 1) {
if (result[j]?.length > 0) {
result[j].push(Array[i])
} else {
let arr = []
arr.push(Array[i])
result[j] = arr
}
lastIndex = i + 1
}
}
}
}
return result
}
let result = SplitArr(Arr, numberOfParts)
console.log(result)
Assuming the array isn't sorted,using a 2D array, with each sub array with sum almost equal to (sum of array / n).
let arr = [9,2,10,4,5,6,7,8,1,3]
arr.sort(function(a, b) { return a - b; });
const sum = arr.reduce((a, b) => a + b, 0);
const n = 2;
const result = [];
let s = 0;
let j = 0;
result[j] = [];
for(let i=0; i<arr.length; i++){
if(s <= Math.floor(sum/n)){
result[j].push(arr[i]);
s +=arr[i];
}
else{
s = 0;
j = j + 1;
result[j] = [];
result[j].push(arr[i]);
}
}
console.log(result)
O/P:
[ [1, 2, 3, 4,5, 6, 7], [ 8, 9, 10 ] ]
const arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
const splitArray = (arr,parts) => {
const totalSum = arr.reduce((acc, item) => {
acc += item;
return acc;
}, 0)
const splitSum = Math.floor(totalSum / parts);
const arrObj = arr.reduce((acc, item,index) => {
acc.sum = acc.sum || 0;
acc.split = acc.split || {};
const pointer = Math.floor(acc.sum / splitSum);
//console.log(item,acc.sum, splitSum, pointer);
acc.split[pointer] = acc.split[pointer] || [];
acc.split[pointer].push(item);
acc.splitSum = splitSum;
acc.sum += item;
return acc;
}, {})
return arrObj;
}
console.log(splitArray(arr,2).split)
You're better off making a custom function:
let currentTotal = 0
let tempList = []
Arr.forEach(val => {
if (val >= 27) {
// push tempList to a new array
tempList = [];
currentTotal = val;
} else {
tempList.push(val);
currentTotal += val;
}
})
You are given an array with N length. Please develop the function reverseArray to reverse the array
E.g.
Input: [1, 2, 3, 4, 5]
Output:
5
4
3
2
1
My attempt is as follows:
function printArray (inputArray){
for(let i = 0; i < inputArray.length; i++){
console.log(inputArray[i]);
}
}
function reverseArray (inputArray){
for (var i = inputArray.length - 1; i >= 0; i--){
inputArray.push(inputArray[i]);
}
printArray(inputArray);
}
reverseArray([1, 2, 3, 4, 5]);
But it turns out to be as follows:
1 2 3 4 5 5 4 3 2 1
Can anyone teach me how to solve, i have been struggling with this question for 2 days
Check
this link
function reverseArr(input) {
var ret = new Array;
for(var i = input.length-1; i >= 0; i--) {
ret.push(input[i]);
}
return ret;
}
var a = [3,5,7,8]
var b = reverseArr(a);
You can use reverse() and join()
var arr = [1, 2, 3, 4, 5];
arr.reverse();
console.log(arr.join(' '));
Use for loop:
function printArray (inputArray){
for(let i = 0; i < inputArray.length; i++){
console.log(inputArray[i]);
}
}
function reverseArray (inputArray){
var results = [];
for (var i = inputArray.length - 1; i >= 0; i--){
results.push(inputArray[i]);
}
printArray(results);
}
reverseArray([1, 2, 3, 4, 5]);
User array's reverse method:
function printArray (inputArray){
for(let i = 0; i < inputArray.length; i++){
console.log(inputArray[i]);
}
}
function reverseArray (inputArray){
var results = [];
results = inputArray.reverse();
printArray(results);
}
reverseArray([1, 2, 3, 4, 5]);
A bit change on your base code. It could be simpler, but I think what you need is a inplace reverse.
function printArray(inputArray) {
for (let i = 0; i < inputArray.length; i++) {
console.log(inputArray[i]);
}
}
function reverseArray(inputArray) {
const tempArr = inputArray.slice();
inputArray.splice(0, inputArray.length);
for (var i = tempArr.length - 1; i >= 0; i--) {
inputArray.push(tempArr[i]);
}
printArray(inputArray);
}
reverseArray([1, 2, 3, 4, 5]);
there are many ways to do this. and there is a reverse method for array too.
function reverseArray(inputArray) {
let start = 0;
let end = inputArray.length -1;
while (start < end) {
const tmp = inputArray[start];
inputArray[start] = inputArray[end];
inputArray[end] = tmp;
start++;
end--;
}
}
arr = [1, 2, 3, 4, 5];
reverseArray(arr);
console.log(arr);
thats very simple you can use javascript method "reversed()"
or you can use this function
function reverse(input) {
var ret = new Array;
for(var i = input.length-1; i >= 0; i--) {
ret.push(input[i]);
}
return ret;
}
var arr = [3,5,7,8]
var b = reverse(arr)
console.log(b)
The easiest method for reserve array is using Array.reverse;
But if you want do it by yourself,you can do it like this:
function reserveArray (input){
for (let i =0;i<input.length;i++){
input.unshift(input.pop())
}
}
It's just an idea, and i do not test if it run as expected.
You could iterate through half the array and swap [i] and [inputArray.length-1-i].
function reverseArray(a) {
for(let i = 0; i < Math.floor(a.length / 2); i++) {
[a[i], a[a.length - 1 - i]] = [a[a.length - 1 - i], a[i]];
}
}
If the output is really a string (opposed to an array) just print the elements start from the end:
function reverseArray(a) {
for(let i = a.length - 1; i >= 0; i--) {
process.stdout.write(a[i].toString() + (i ? " " : ""));
}
}
Here is the idea:
var a = [4, 5, 6];
for (var m = 0; m < a[0]; m++)
for (var n = 0; n < a[1]; n++)
for (var p = 0; p < a[2]; p++)
console.log(`${m} + ${n} + ${p} = ${m+n+p}`);
Live Copy:
// This just tells the Stack Snippets in-snippet console not
// to throw away entries once it reaches a max (the default max
// is just the last 50 logs).
console.config({maxEntries: Infinity});
var a = [4, 5, 6];
for (var m = 0; m < a[0]; m++)
for (var n = 0; n < a[1]; n++)
for (var p = 0; p < a[2]; p++)
console.log(`${m} + ${n} + ${p} = ${m+n+p}`);
/* This just makes the console take up the full output area */
.as-console-wrapper {
max-height: 100% !important;
}
The code would get longer if the array a has more indexes. Could the code be shorten using Array.map or filter or a function?
We can do this without taking up massive amounts of memory, and fairly simply, by using recursion:
const process = (array, n, numbers) => {
if (n < array.length) {
// Not done yet, recurse once for each number at this level
const max = array[n];
for (let i = 0; i < max; ++i) {
process(array, n + 1, [...numbers, i]);
}
} else {
// Done with this level, process the numbers we got
console.log(`${numbers.join(" + ")} = ${numbers.reduce((s, e) => s + e)}`);
}
}
process([4, 5, 6], 0, []);
Live Copy, with cross-checking against your results to ensure the above does the same thing:
// This just tells the Stack Snippets in-snippet console not
// to throw away entries once it reaches a max (the default max
// is just the last 50 logs).
console.config({maxEntries: Infinity});
function thisSolution() {
const results = [];
const process = (array, n, numbers) => {
if (n < array.length) {
// Not done yet, recurse once for each number at this level
const max = array[n];
for (let i = 0; i < max; ++i) {
process(array, n + 1, [...numbers, i]);
}
} else {
// Done with this level, process the numbers we got
const result = numbers.reduce((s, e) => s + e);
results.push(result);
console.log(`${numbers.join(" + ")} = ${result}`);
}
}
process([4, 5, 6], 0, []);
return results;
}
function yourSolution() {
const results = [];
var a = [4, 5, 6];
for (var m = 0; m < a[0]; m++)
for (var n = 0; n < a[1]; n++)
for (var p = 0; p < a[2]; p++)
results.push(m + n + p);
return results;
}
const thisResult = thisSolution();
const yourResult = yourSolution();
if (thisResult.some((entry, index) => entry !== yourResult[index])) {
console.log("WRONG");
} else {
console.log("RIGHT");
}
/* This just makes the console take up the full output area */
.as-console-wrapper {
max-height: 100% !important;
}
This never goes deep into the stack (a.length + 1 stack frames, to be precise, so four in the example case). It builds up a number of temporary arrays (145 in the example case) that max out at a.length entries, releasing them as soon as they aren't needed anymore (a max of four are retained at any given time). Here's the quick and dirty metrics on that:
let maxStack = 0;
let stack = 0;
let totalArrays = 0;
let maxArrays = 0;
let arrays = 0;
// A wrapper for counting stack frames
const process = (...args) => {
if (++stack > maxStack) {
maxStack = stack;
}
const result = process2(...args);
--stack;
return result;
};
const process2 = (array, n, numbers) => {
if (n < array.length) {
// Not done yet, recurse once for each number at this level
const max = array[n];
for (let i = 0; i < max; ++i) {
++totalArrays;
if (++arrays > maxArrays) {
maxArrays = arrays;
}
process(array, n + 1, [...numbers, i]);
--arrays;
}
} else {
// Done with this level, process the numbers we got
//console.log(`${numbers.join(" + ")} = ${numbers.reduce((s, e) => s + e)}`);
}
}
process([4, 5, 6], 0, []);
++maxArrays; // To account for the one in the last argument above
++totalArrays; // "
console.log(`Max stack: ${maxStack}, max arrays: ${maxArrays}, total arrays: ${totalArrays}`);
It's easier if you break it down. First, you need to create a series per every element of your array.
let series = num => Array.from({ length: num + 1 }, (n, i) => i); //creates an array with nums from 0 to num.
That's the first part of your question. Then you need to do a cross product of your series.
Basically for two series [1, 2, 3] and [1, 2, 3, 4] you'll end up with a set of 12 elements:
[2, 3, 4, 5, 3, 4, 5, 6, 4, 5, 6, 7]
And for that you could do:
let crossProduct = (a1, a2) => Array.prototype.concat.call(...a1.map(n1 => a2.map(n2 => n1 + n2)));
Now all you need to do is have a crossProduct for every series.
let final = numbers.map(series).reduce(crossProduct);
And there you have it:
let numbers = [4, 5, 6];
let series = num => Array.from({ length: num + 1 }, (n, i) => i);
let crossProduct = (a1, a2) => Array.prototype.concat.call(...a1.map(n1 => a2.map(n2 => n1 + n2)));
let final = numbers.map(series).reduce(crossProduct);
console.log(final);
Edit: If it's from 0 to the number before (e.g. 4 is [0, 1, 2, 3]) then just take the + 1 in the series function.
2nd Edit: Less objects created for your crossProduct:
let crossProduct = (a1, a2) => {
let resultingSet = [];
for(let i = 0; i < a1.length; i++)
for(let j = 0; j < a2.length; j++)
resultingSet.push(a1[i] + a2[j]);
return resultingSet;
} //only one array is created
And if you want to avoid having the series on memory all the time:
let numbers = [4, 5, 6];
let series = function* (num){
for(let i = 0; i < num; i++){
yield i;
}
}
let crossProduct = (set, num) => {
let resultingSet = [];
for(let i = 0; i < set.length; i++){
for(let j of series(num)){
resultingSet.push(set[i] + j);
}
}
return resultingSet;
}
let final = numbers.reduce(crossProduct, [0]);
console.log(final);
Another solution that doesn't consume alot of memory and fairly efficient is by using an array that represnt the value of the indexes and update it each iteration.
first you create an array that represent in each element the amount of iterations you need to run in order to update the indexes respectively for example for this array [1, 2, 3 ,4 ,5] you will get:
[280, 140, 20, 5, 1] this means that index[0] will be updated each 280 iterations, index[1] will be updated each 140 iterations and so on..
totally you will run arr[n] * arr[n-1] * arr[n-2] * .... * arr[0] iterations as you did with ordinary nested for loop.
var arr = [1, 2, 7, 4, 5];
var indexes = Array.from({length: arr.length}, () => 0);
iterationsPerElement = arr.map((_, i) => arr.slice(i+1).reduce((acc, elem) => acc * elem, 1));
var totalIterations = iterationsPerElement[0] * arr[0];
for(var iteration = 1; iteration <= totalIterations; iteration++) {
// sum those indexes
console.log(`sum = ${indexes.reduce((acc, index) => acc + index, 0)}`);
// update indexes
for(i = 0; i < indexes.length; i++) {
if(iteration % iterationsPerElement[i] == 0) {
indexes[i]++;
// empty the indexes on the right
for(var j=i+1; j <indexes.length; j++) {
indexes[j] = 0;
}
}
}
}
I have an Array which contains numbers. I want to find the pair of the number which sums equal to given value with o(n) complexity.
let data = [5,8,9,6];
var x = {};
function findSum(arr, sum){
data.forEach(function(item){
if(item > sum){
return null
}
var diff = sum - item;
x[item] = diff
})
console.log(x);
}
findSum(data, 7);
Working with O(n2) complexity.
let data = [2, 4, 11, 3, 5, 8, 9, 1, 6, 5]
function findSum(arr, sum) {
let sortArray = arr.sort(function(a, b) {
return a - b
});
let findIndex = arr.indexOf(arr.find(function(item) {
return item >= sum
}))
let iterateValues = sortArray.slice(0, findIndex);
var pairs = [];
console.log(iterateValues)
iterateValues.forEach(function(value, index) {
let getDiff = sum - value;
let findDiff = iterateValues.find(function(diff, index) {
return diff === getDiff
});
if (findDiff) {
let firstPair = value.toString()
let secondPair = findDiff.toString();
let merge = firstPair + ',' + secondPair;
pairs.push(merge)
}
})
console.log(pairs)
}
findSum(data, 7);
Try the following, it takes O(n) time to find the pair whose sum is equal to given value:
let data = [5,8,9,6];
var sum = 17;
var map = {};
var found = false;
for(var i = 0; i < data.length; i++){
map[data[i]] = i;
}
for(var i = 0; i < data.length; i++){
if(map[sum - data[i]] && map[sum - data[i]] != i){
found = true;
console.log(data[map[sum - data[i]]] + " "+data[i]);
break;
}
}
if(!found)
console.log("No pair found");
Using a Set and for of loop
function findSum(arr, sum) {
let set = new Set(),
res = null;
for (let n of arr) {
const diff = sum - n;
if (diff && set.has(diff)) {
res = [diff, n]
break;
}
set.add(n);
}
return res ? res.join(' + ') + ' = ' + sum : 'No Matches for ' + sum
}
let data = [2, 4, 11, 3, 5, 8, 9, 1, 6, 5];
console.log(findSum(data, 6))
console.log(findSum(data, 7))
console.log(findSum(data, 8))
console.log(findSum(data, 22))
I have several numbers in an array
var numArr = [1, 3, 5, 9];
I want to cycle through that array and multiply every unique 3 number combination as follows:
1 * 3 * 5 =
1 * 3 * 9 =
1 * 5 * 9 =
3 * 5 * 9 =
Then return an array of all the calculations
var ansArr = [15,27,45,135];
Anyone have an elegant solution? Thanks in advance.
A general-purpose algorithm for generating combinations is as follows:
function combinations(numArr, choose, callback) {
var n = numArr.length;
var c = [];
var inner = function(start, choose_) {
if (choose_ == 0) {
callback(c);
} else {
for (var i = start; i <= n - choose_; ++i) {
c.push(numArr[i]);
inner(i + 1, choose_ - 1);
c.pop();
}
}
}
inner(0, choose);
}
In your case, you might call it like so:
function product(arr) {
p = 1;
for (var i in arr) {
p *= arr[i];
}
return p;
}
var ansArr = [];
combinations(
[1, 3, 5, 7, 9, 11], 3,
function output(arr) {
ansArr.push(product(arr));
});
document.write(ansArr);
...which, for the given input, yields this:
15,21,27,33,35,45,55,63,77,99,105,135,165,189,231,297,315,385,495,693
I think this should work:
var a = [1, 3, 5, 9];
var l = a.length;
var r = [];
for (var i = 0; i < l; ++i) {
for (var j = i + 1; j < l; ++j) {
for (var k = j + 1; k < l; ++k) {
r.push(a[i] * a[j] * a[k]);
}
}
}
Edit
Just for my own edification, I figured out a generic solution that uses loops instead of recursion. It's obvious downside is that it's longer thus slower to load or to read. On the other hand (at least on Firefox on my machine) it runs about twice as fast as the recursive version. However, I'd only recommend it if you're finding combinations for large sets, or finding combinations many times on the same page. Anyway, in case anybody's interested, here's what I came up with.
function combos(superset, size) {
var result = [];
if (superset.length < size) {return result;}
var done = false;
var current_combo, distance_back, new_last_index;
var indexes = [];
var indexes_last = size - 1;
var superset_last = superset.length - 1;
// initialize indexes to start with leftmost combo
for (var i = 0; i < size; ++i) {
indexes[i] = i;
}
while (!done) {
current_combo = [];
for (i = 0; i < size; ++i) {
current_combo.push(superset[indexes[i]]);
}
result.push(current_combo);
if (indexes[indexes_last] == superset_last) {
done = true;
for (i = indexes_last - 1; i > -1 ; --i) {
distance_back = indexes_last - i;
new_last_index = indexes[indexes_last - distance_back] + distance_back + 1;
if (new_last_index <= superset_last) {
indexes[indexes_last] = new_last_index;
done = false;
break;
}
}
if (!done) {
++indexes[indexes_last - distance_back];
--distance_back;
for (; distance_back; --distance_back) {
indexes[indexes_last - distance_back] = indexes[indexes_last - distance_back - 1] + 1;
}
}
}
else {++indexes[indexes_last]}
}
return result;
}
function products(sets) {
var result = [];
var len = sets.length;
var product;
for (var i = 0; i < len; ++i) {
product = 1;
inner_len = sets[i].length;
for (var j = 0; j < inner_len; ++j) {
product *= sets[i][j];
}
result.push(product);
}
return result;
}
console.log(products(combos([1, 3, 5, 7, 9, 11], 3)));
A recursive function to do this when you need to select k numbers among n numbers. Have not tested. Find if there is any bug and rectify it :-)
var result = [];
foo(arr, 0, 1, k, n); // initial call
function foo(arr, s, mul, k, n) {
if (k == 1) {
result.push(mul);
return;
}
var i;
for (i=s; i<=n-k; i++) {
foo(arr, i+1, mul*arr[i], k-1, n-i-1);
}
}
This is a recursive function.
First parameter is array arr.
Second parameter is integer s. Each call calculates values for part of the array starting from index s. Recursively I am increasing s and so array for each call is recursively becoming smaller.
Third parameter is the value that is being calculated recursively and is being passed in the recursive call. When k becomes 1, it gets added in the result array.
k in the size of combination desired. It decreases recursively and when becomes 1, output appended in result array.
n is size of array arr. Actually n = arr.length
var create3Combi = function(array) {
var result = [];
array.map(function(item1, index1) {
array.map(function(item2, index2) {
for (var i = index2 + 1; i < array.length; i++) {
var item3 = array[i];
if (item1 === item2 || item1 === item3 || item2 === item3 || index2 < index1) {
continue;
}
result.push([item1, item2, item3]);
}
});
});
return result;
};
var multiplyCombi = function(array) {
var multiply = function(a, b){
return a * b;
};
var result = array.map(function(item, index) {
return item.reduce(multiply);
});
return result;
}
var numArr = [1, 3, 5, 9];
// create unique 3 number combination
var combi = create3Combi(numArr); //[[1,3,5],[1,3,9],[1,5,9],[3,5,9]]
// multiply every combination
var multiplyResult = multiplyCombi(combi); //[15,27,45,135];
https://github.com/dankogai/js-combinatorics
Found this library. Tested to be working. Below is from the library document:
var Combinatorics = require('js-combinatorics');
var cmb = Combinatorics.combination(['a','b','c','d'], 2);
while(a = cmb.next()) console.log(a);
// ["a", "b"]
// ["a", "c"]
// ["a", "d"]
// ["b", "c"]
// ["b", "d"]
// ["c", "d"]
Using node, you can do this pretty easily using a library. First install bit-twiddle using npm:
npm install bit-twiddle
Then you can use it in your code like this:
//Assume n is the size of the set and k is the size of the combination
var nextCombination = require("bit-twiddle").nextCombination
for(var x=(1<<(k+1))-1; x<1<<n; x=nextCombination(x)) {
console.log(x.toString(2))
}
The variable x is a bit-vector where bit i is set if the ith element is contained in the combination.