I'm confused on why one is returning me the sum while the other one is just returning the list.
This correctly returns the output 10
function sum(){
var arrays = [1,2,3,4].reduce(function (total, num) {
return total + num;
})
console.log(arrays);
}
This however, returns [1, 2, 3, 4] and not 10.
function sum(){
var arrays = [1,2,3,4];
arrays.reduce(function (total, num) {
return total + num;
})
console.log(arrays);
}
At first I thought it's where I was declaring the var arrays so I tried moving it out of the function and also tried not declaring it var. However for this one I'm still not getting 10.
What's the difference between the two that I'm not getting the correct output?
Thanks.
You are missing the assignment, which is returned by the reduce:
function sum() {
var arrays = [1, 2, 3, 4];
arrays = arrays.reduce(function(total, num) {
//-----^
return total + num;
})
console.log(arrays);
}
In the second function you are ignoring the return value from the reduce method. It will correctly calculate the sum, but you don't use it.
Assign the result to the variable as in the first function:
array = arrays.reduce(function (total, num) {
return total + num;
});
However, having the result in the same variable as where the array was makes the code somewhat confusing. You should avoid having a variable change meaning in the middle of the code, so you can use a different variable for the result:
function sum(){
var arrays = [1,2,3,4];
var result = arrays.reduce(function (total, num) {
return total + num;
});
console.log(result);
}
Side note: The term functional programming is used for languages that are based on functional expressions instead of variable state. Just using a function doesn't mean that you are using functional programming.
In first,
when the function return the value i.e. 10 it is getting stored in var arrays and you are printing it.
whereas,
In second,
You declared the var arrays and give it the value [1,2,3,4] then funtion is called, the returned value is not getting stored anywhere and at last you are simply printing the var arrays which is [1,2,3,4]
Related
I have only been learning javascript for 2 weeks, so apologies if my question seems weird/doesn't make sense. I'm learning the basics of arrays, and to help me learn I like to practise and play around with the code but I can't seem to figure this one out.
I've created a simple function, and wanting to call upon the function to calculate the sum of variables in an array. Here is my code below:
//functions
function simpleCalc (a,b) {
var result = a + b;
return result;
}
//array
var myArray = [12,567];
//final calculation
var total = simpleCalc([0],[1]);
alert("The total is " + total);
Can anyone please shed any light as to how I input the numbers "12" and "567" into the function parameters? The result here as it stands outputs to "01"
Thanks
You have two options:
Your option but, it is very limited to only two values.
You need to pass reference to your array elements like so (myArray[0], myArray[1])
Create new function - let's call it sumValuesInArray(), pass an array and calculate all values inside an array using for loop.
See working example here:
//functions
function simpleCalc (a,b) {
var result = a + b;
return result;
}
//array
var myArray = [12,567];
//final calculation
var total = simpleCalc(myArray[0],myArray[1]);
//alert("The total is " + total);
// OR
function sumValuesInArray(array) {
var total = 0;
for(i = 0; i < array.length; i++) {
var element = array[i];
total += element;
}
return total;
}
console.log(sumValuesInArray(myArray));
You don't specify the array but only indexes :
var total = simpleCalc([0],[1]);
So, it passes two array objects : [0] and [1].
The concatenation of them here :
var result = a + b;
has as result the 01 String.
To pass the two first elements of myArray, try it :
var total = simpleCalc(myArray[0],myArray[1]);
You need to access the array values by index. You do this using the brackets WITH the name of the array. If you pass the brackets with numbers inside, you're creating new arrays.
It should be:
var total = simpleCalc(myArray[0],myArray[1]);
I am learning map & reduce, but am having a hard time understanding how to utilize these methods to tackle problems.
For example,
Create a function that takes a number and returns an array of strings containing the number cut off at each digit.
420 should return ["4", "42", "420"]
My old Approach:
function createArrayOfTiers(num) {
var numArr = num.toString().split('');
var output = [];
for(var i = numArr.length-1; i>=0; i--) {
output.unshift(numArr.join('');
numArr.pop();
}
return output;
}
Attempt to use map-reduce combination:
function createArrayOfTiers(num) {
var numArr = num.toString().split('');
return numArr.map(function(element) {
var newElement = numArr.reduce(function(acc, val) {
return acc + val;
});
numArr.splice(element, 1);
return newElement;
});
}
You have used two loops, but apparently it can be done just with one.
function n(num) {
let res = (""+num).split('').map((_,i) => (""+num).slice(0, i+1));
return res;
}
console.log(n(420));
console.log(n(13579));
One-liner.
const n = num => (""+num).split('').map((_,i) => (""+num).slice(0, i+1));
console.log(n(420));
console.log(n(13579));
As others noted, that this problem doesn't seem to be the best use case of the map and reduce functions.
map function provides the element, index and array information in the parameters. Making use of these you can iterate on the elements you need to apply the reduce function.
Statement var arrayToIterate = arr.slice(0,i+1); helps to achieve the above mentioned array to iterate.
Complete Code:
function createArrayOfTiers(num) {
var numArr = num.toString().split('');
return numArr.map(function(element, i, arr) {
var arrayToIterate = arr.slice(0,i+1);
var newElement = arrayToIterate.reduce(function(acc, val) {
return acc + val;
},"");
return newElement;
});
}
var result = createArrayOfTiers(420);
console.log(result);
I don't think these are good uses-cases of map or reduce, but here goes :
var numArr = [4,2,0];
var result = numArr.map(e => numArr.join('')) // now ["420", "420", "420"]
.map((arr, i) => arr.substring(0, i+1)) // now ["4", "42", "420"]
console.log(result);
We first replace every element of the array by the whole (unmodified) array joined into a string, then substring each of these strings based on their position in the outer array.
There's a reduction hidden in there, although not using reduce : join reduces [4, 2, 0] to "420".
I am learning map & reduce, but am having a hard time understanding how to utilize these methods to tackle problems.
Mapping associates to each value of the source array a new value provided by a mapping function : if you have an [x, y, z] array, a mapping function f(x)=x+1, the result of mapping the array with the function will be [x+1, y+1, z+1].
I believe reduction was meant to "reduce" an array to a primitive type, although I might be mistaken. If you have an [x, y, z] array and reduce it with the addition operation, the result will be x+y+z.
Can someone explain why these array methods in Javascript have functions as parameters? An example would be:
newArray = oldArray.map(
function(val){
return val + 3;
});
also this,
array.sort(function(a, b) {
return b - a;
});
I am having trouble understanding how these functions and their parameters play a roll in the actual Array methods.
First you need to understand, all JavaScript functions are first class which mean:
A function is an instance of the Object type
A function can have properties and has a link back to its constructor method
You can store the function in a variable
You can pass the function as a parameter to another function
You can return the function from a function
reduce(), sort(), map() and filter() are method of Array object that accept a callback function as its parameter.
For instance:
reduce()
var total = [0, 1, 2, 3].reduce(function(a, b) {
return a + b;
});
sort():
var items = ['réservé', 'premier', 'cliché', 'communiqué', 'café', 'adieu'];
items.sort(function (a, b) {
return a.localeCompare(b);
});
map():
var numbers = [1, 4, 9];
var doubles = numbers.map(function(num) {
return num * 2;
});
filter():
function isBigEnough(value) {
return value >= 10;
}
var filtered = [12, 5, 8, 130, 44].filter(isBigEnough);
Reference:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/filter
This callback functions are used to define behaviour. Like in sort it will sort array in order descending order. That's the definition how you want to sort array or filter array. You can play around it to understand it better or MDN has good examples.
var arr = [12,23,1,56,4,32];
alert(arr.sort());
alert(arr.sort(function(a,b) {
return b - a;
}
));
Here in case of first example sort method will sort by comparing first digit. In order to achieve correct sorting we need to pass our own logic.
You can use sort for various different sorting by changing logic in callback function.
Similar is true for other array methods you mentioned.
In above example of you want to do ascending order you need to
return a - b;
It is functional programming style
To (over) simplify concept is, these function will loop through all members of that array for you. It will just plug that function you pass in at the place it need
Let make an example with map
If you don't use map, the whole thing you need to write is
var oldArray;
var newArray;
for(var i in oldArray){
if(oldArray[i])
newArray.push(oldArray[i] + 3);
}
You could see that everytimes we do something like this. The thing that will change is the line in for block. So they just make a function for it
function map(oldArray,ConvertToSomething){
var newArray;
for(var i in oldArray)
newArray.push(ConvertToSomething(oldArray[i]));
return newArray;
}
var array;
//// The function you pass in here will became that ConvertToSomething above
var newArray = map(array,function(val){ if(val) return val + 3; })
Easy as that. Same go for sort and filter. sort will pick a pair of them for you. filter is like map but it will make an array that exclude thing you don't want by just return false or true
I am playing with reduce method provided by mozilla. Underscore provides its own version which seems very similar. Reducing an array is very simple.
ArrayName.reduce(function(a,b) {
return a +b;
});
I use a very similar approach when sorting arrays as well. However, what I do not understand is how to return a list of calls. https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/Reduce Provides a really cool table that shows how their method works. I set my array pretty much the same
var array = [1,2,3,100,55,88,2];
var sortArray= function(a,b) {
return a -b;
}
var sorted = array.sort(sortArray);
var reduced = sorted.reduce(function(previousValue,currentValue, index,array){
return previousValue + currentValue;
});
What I wanted to set up though was each call that was made. I figured that I could simply reference the index in the return value with a , at the end.
return previousValue + currentValue, index;
However, that only returns the index. I am trying to figure a way to get the value of each call. Does this approach allow you to get each call?
You don't need to use reduce for what you are doing. Try
function running_total(array) {
var sum = 0;
return array.map(function(elt) {
return sum += elt;
};
}
Reduce is about "boiling down" an array to a "single thing". In contrast, map is about "transforming" elements of the array. Your problem (as I understand it) is to transform each element of the array into the sum of itself and all the preceding elements. Therefore, conceptually, it's a map, not a reduce.
Using the , in the return statement will only return index due to the comma operator rule
[0, 1, 2, 3, 4].reduce(function(previousValue, currentValue, index, array) {
console.log(previousValue+"--"+currentValue)
return previousValue + currentValue;
});
this will do want you want
You can create another array and store its value for each progress.
var array = [1,2,3,100,55,88,2];
var sortArray= function(a,b) {
return a -b;
}
var sorted = array.sort(sortArray);
var progress = [];
var reduced = sorted.reduce(function(previousValue,currentValue, index,array){
progress[index] = previousValue + currentValue;
return progress[index];
}, 0);
// ^^^^^
// give it a init value so it starts at first element.
console.log(progress);
However, as torazaburo says, as you expect to get an array, you should use .map which returns an array instead of .reduce.
I'm trying to get the function below to return the average of all elements in array1, but I keep getting null as the result. I can't seem to figure out why.
var array1 = [46,73,-18,0,-442,779,5,1400];
var arrayAverage = function(arrayavg) {
for (var average = 0,answer=0, arrayavg = arrayavg.length;array1 > answer;answer++)
average +=parseInt(arrayavg[answer]);
var calc = average/arrayavg.length;
return calc
};
There are a number of errors, I don't have time to point them all out, hopefully the following is sufficient:
var array1 = [46,73,-18,0,-442,779,5,1400];
var arrayAverage = function(arrayavg) {
I don't know why you using a function expression rather than a function declaration. It doesn't affect the issue, but is more code to write. It's also good to give variables names that express what they are for, so given that the function expects an array:
function arrayAverage(array) {
then:
for (var average = 0,answer=0, arrayavg = arrayavg.length;array1 > answer;answer++)
It's not a good idea to pile all those variable declarations into the for condition, far better to separate concerns and only create variables that you need:
var total = 0;
Now iterate over the array to get the total value. The '{' brackets can be omitted, but it's clearer to include them:
for (var i=0, iLen=array.length; i<iLen; i++) {
total += array[i];
}
Now calculate the average and return it in one statement:
return total/iLen;
}
console.log(arrayAverage(array1)); // 230.375
You need to put brackets after your for loop
I was too fast to answer.
You are re-assigning the passed array to the length of the passed array.
arrayavg = arrayavg.length
this breaks everything.
in the for loop you have assigned arrayavg=arrayavg.length and in the body ,you are accessing average+=arrayavg[answer]. arrayavg is now a primitive type . it will return undefined.
And your loop condition is array1 > answer array1 is an array .you cant compare it like that.it will return false.
modified code.
var array1 = [46,73,-18,0,-442,779,5,1400];
var arrayAverage = function(arrayavg) {
var sum=0;
for (var i=0;i<arrayavg.length;i++)
sum +=parseInt(arrayavg[i]);
return sum/arrayavg.length;
};
You are comparing a number to your array in your for loop. You want to stop the for when answer is the same as array1 length.
Also, don't change your parameter array to its length if you want to get its values in the loop.
var array1 = [46,73,-18,0,-442,779,5,1400];
var arrayAverage = function(arrayavg) {
for (var average = 0,answer=0, len = arrayavg.length;len > answer;answer++)
average +=parseInt(arrayavg[answer]);
var calc = average/len;
return calc
};
And to call it:
arrayAverage(array1);
Your code has two problems in the for loop.
for (var average = 0,answer=0, arrayavg = arrayavg.length;array1 > answer;answer++)
^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^
First thing is you set arrayavg to arrayavg's length BUT in the next line you try to read the index of the array. Well you overwrote the array with a number! Not going to happen.
Second issue you are comparing an array 'array1' to a number 'answer' . What does that check do? Not what you think it is going. You want to be checking the length, but wouldn't you want to be checking the passed in array, not the hardcoded one?
I think the other answers (particularly RobG) have covered most of it. It might help to follow a couple of standard rules (that I use) for your loops:
1) Always have the index as the first declared element, the length of the array (for caching purposes) as the second, and any other variables after them.
2) Always use brackets to separate your loop code from the code in the rest of the function. That way you know when to return your averaged product (ie after the }).
So this is my slightly rewritten code of your problem:
for (var index = 0, len = arrayavg.length, avg = 0; index < len; index++) {
avg += parseInt(arrayavg[index], 10) / len;
}
return avg;
Note also that parseInt should contain a radix (in this case 10). You can leave it out but it's good practice to always include it.
By the way, here's an alternative to your function you might find useful that uses a functional approach using reduce:
var arrayAverage = function (arr) {
return arr.reduce(function (a, b) { return a + b; }) / arr.length;
}