I'm creating a function to filter my javascript objects.
function filter(array,filterName,filterCondition,filterParameter){
for(var i=0; i< array.length;i++){
if(array[i][filterName] -<convert FilterCondition here>- filterParameter){
}
}
}
and ideally I would like to use it like this:
filter(anArray,"age",">",10)
Is it possible to convert a string parison operator into a real operator in my if statement?
I'm creating a function to filter my javascript objects.
function filter(array,filterName,filterCondition,filterParameter){
for(var i=0; i< array.length;i++){
if(array[i][filterName] -<convert FilterCondition here>- filterParameter){
}
}
}
and ideally I would like to use it like this:
filter(anArray,"age",">",10)
Is it possible to convert a string parison operator into a real operator in my if statement?
Share Improve this question asked Jun 26, 2015 at 21:12 Terence ChowTerence Chow 11.2k24 gold badges81 silver badges148 bronze badges 3- @blex why is it evil? Is it slow? – Terence Chow Commented Jun 26, 2015 at 21:13
- 1 @blex thanks this works! If you want to provide answer I will accept – Terence Chow Commented Jun 26, 2015 at 21:16
-
Thanks Chowza. If you want to avoid using
eval
or a bigswitch
statement, I've found an alternative way, check my edited answer. – blex Commented Jun 26, 2015 at 22:00
2 Answers
Reset to default 8For example, you can use hash like this:
function filter(array,filterName,filterCondition,filterParameter){
var parisonOperatorsHash = {
'<': function(a, b) { return a < b; },
'>': function(a, b) { return a > b; },
'>=': function(a, b) { return a >= b; },
'<=': function(a, b) { return a <= b; },
'==': function(a, b) { return a == b; },
'===': function(a, b) { return a === b; },
};
var parisonOperator = parisonOperatorsHash[filterCondition];
if (parisonOperator === undefined) {
// throw error here
}
for(var i=0; i< array.length;i++){
if(parisonOperator(array[i][filterName], filterParameter)) {
}
}
}
eval
is evil, but can do anything. It's considered evil if arbitrary input can be passed to it, like user input. But if you control what's in there, it should be safe. More info here.
So you could do:
function filter(array,filterName,filterCondition,filterParameter){
var results = [];
for(var i=0; i< array.length;i++){
if(eval(array[i][filterName] + filterCondition + filterParameter)){
results.push(array[i]['name'])
}
}
document.body.innerHTML = 'These guys are older than 10: ' + results.join(', ');
}
var anArray = [
{'name': 'Patrick', 'age': 8 },
{'name': 'John', 'age': 12 },
{'name': 'Debora', 'age': 26 },
{'name': 'Jenna', 'age': 3 },
{'name': 'Brandon', 'age': 14 },
];
filter(anArray,"age",">",10);
Edit
I've thought of another way without the eval
, or an endless switch
statement. The trick here is to create a temporary script
tag, that will hold a function to check conditions. This will avoid repiling your function on every iteration of the loop, as it would with eval
.
var conditionScript = document.createElement('script');
function filter(array,filterName,filterCondition,filterParameter){
var results = [];
prepareCondition(filterCondition,filterParameter);
for(var i=0; i< array.length;i++){
if( evalCondition(array[i][filterName]) ){
results.push(array[i]['name']);
}
}
document.body.innerHTML = 'These guys are older than 10: ' + results.join(', ');
}
function prepareCondition(filterCondition,filterParameter){
if(conditionScript.parentNode) document.body.removeChild(conditionScript);
conditionScript.innerText = 'function evalCondition(value){'
+ ' return value ' + filterCondition + filterParameter
+ '}';
document.body.appendChild(conditionScript);
}
var anArray=[
{'name': 'Patrick', 'age': 8 },
{'name': 'John', 'age': 12 },
{'name': 'Debora', 'age': 26 },
{'name': 'Jenna', 'age': 3 },
{'name': 'Brandon', 'age': 14 },
];
filter(anArray,"age",">",10);