user4490801
user4490801

Reputation:

most elegant way to get benefits of map and filter in javascript for reducing array and changing variables within it

I've found a couple of ways to remove a set of values from an array, and then change the values within the array (or in reverse order). For example:

original_array= ["unwanted variable 1","Score: Question 1","Score: Question 2","Score: Question 3","unwanted variable 2"];
// i want to end with just the "Score:" variables.
// method 1 
scales = original_array.filter(function(element){
       if(element.indexOf("Score:") !== -1){
           return element.replace("Score: ","");
       } 
    });

I was hoping that this would both reduce the array down to the relevant variables, and replace the "Score: " with nothing. It reduces the array, but doesn't change the value of the variables.

I've also tried using .map instead of .filter.

  //method 2
  scales = original_array.map(function(element){
       if(element.indexOf("Score:") !== -1){
           return element.replace("Score: ","");
       } 
    });

Which replaces all the invalid variables with "undefined", but does change the value of the valid variables (e.g. "Question 1" rather than "Score: Question 1".

Is there an elegant way to make use of either of these functions to both filter and then rename the variables? Or do I have to this in two steps?

Upvotes: 0

Views: 46

Answers (4)

Nina Scholz
Nina Scholz

Reputation: 386868

While you have an answer of yourself, you might get the right way for filtering an array, because you return an element, but Array#filter need a truthy value, which can be the result of checking itself.

scales = original_array.filter(function(element) {
    return element.indexOf("Score:") !== -1;      // just return the result of checking
}).map(function(element) { 
    return element.replace("Score: ", "");
});

Upvotes: 0

Rajesh
Rajesh

Reputation: 24955

It reduces the array, but doesn't change the value of the variables

Array.filter as name implies, filters the array. It expects a callback that should return boolean value. If true, value will be returned. If false, value will be ignored.

Which replaces all the invalid variables with "undefined", but does change the value of the valid variables (e.g. "Question 1" rather than "Score: Question 1".

Array.map as name implies, maps some value to existing values in array. That means, it will create a temp array and put return value of callback on the current index position. If you do not return anything, by default, it will set that index to undefined.


If you wish to do both, you have methods like Array.forEach and Array.reduce.

The use of Array.reduce is depicted in @Titus's answer.

Following is the implementation on Array.forEach.

var original_array = ["unwanted variable 1", "Score: Question 1", "Score: Question 2", "Score: Question 3", "unwanted variable 2"];
var scales = [];
original_array.forEach(function(element) {
  if (element.indexOf("Score:") !== -1) {
    scales.push(element.replace("Score: ", ""));
  }
});

console.log(scales)

Upvotes: 0

Titus
Titus

Reputation: 22484

Instead of filter and map you can use reduce, here is an example:

var original_array= ["unwanted variable 1","Score: Question 1","Score: Question 2","Score: Question 3","unwanted variable 2"];
var scales = original_array.reduce(function(acc, element){
       if(element.indexOf("Score:") !== -1){
           acc.push(element.replace("Score: ",""));
       } 
       return acc;
    }, []);

console.log(scales)

What this does is to check if the element meets the criteria element.indexOf("Score:") !== -1 and adds the modified element to the returned array (acc.push(....)).

Upvotes: 0

user4490801
user4490801

Reputation:

Whilst writing the question I found that you can combine .map and .filter:

scales = original_array.filter(function(element){
     if(element.indexOf("Score:") !== -1){
         return element;
     } 
}).map(function(element){ 
     return element.replace("Score: ","");
});

However - I'm hoping there's an easier or more elegant solution than this.

Upvotes: 1

Related Questions