2016-06-24 9 views
0

別の値の配列を使用してオブジェクトの配列をフィルタリングしようとしていますが、空のリストがあります。以下は私のコードがある値の別の配列に基づいてオブジェクトの配列をフィルタリングし、空のリストを返す

[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}].filter(function(val){ 
     [1,2,3].forEach(function(id){ 
      if(id == val.id){ 
       return true; 
      } 
     }); 
    }); 

私の疑問は、これは、フィルタの親コールバック関数にブール値を返しますdoesntの内部のforEachのコールバック関数のように思える)

1です。これを達成する方法はありますか?

+0

@squint。私の間違いを今すぐ見つけた – MeanMan

+0

これはよくある間違いですが、それはありません。そうした場合、呼び出しスタック内のすべての関数を停止するという副作用がありますが、通常は望ましくありません。 –

答えて

0

フィルタ機能が何も返さないため、undefinedは実質的にfalseです。つまり、リストから除外されます。 return文は、forEachコールバックからのみ返されます。

.forEach()の代わりに.some()を使用し、その前にreturnステートメントを入れてください。コールバックの少なくとも1つの呼び出しがtruthy値を返す場合

[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}].filter(function(val){ 
    return [1,2,3].some(function(id){ 
     if(id == val.id){ 
      return true; 
     } 
    }); 
}); 

.some()方法はtrueを返します。真理値が返されると直ちに反復を停止します。


FYI、あなたはifステートメントをドロップすることによって、それを少し短くすることができます。

[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}].filter(function(val){ 
    return [1,2,3].some(function(id){ 
     return id == val.id 
    }); 
}); 

またはそれ以上の新しい矢印関数の構文を使用します。

[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}] 
    .filter((val) => [1,2,3].some((id) => id == val.id)); 

それとも、比較を行うために、任意の複雑なロジックを必要としないので、あなたは、厳密な等価比較に基づいてブール結果を返すES7 .includes()方法を、使用することができます。

[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}] 
    .filter(function(val) { return [1,2,3].includes(val.id) }); 

または

[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}] 
    .filter((val) => [1,2,3].includes(val.id)); 

まだ.indcludes()を持っていない古い実装をアップパッチを適用するためにリンクされドキュメント内ポリフィルがあります。

0
[{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}].filter(function(val){ 
     var returnValue = false; 
     [1,2,3].forEach(function(id){ 
      if(id == val.id){ 
       returnValue = true; 
      } 
     }); 
     return returnValue; 
    }); 
0

Array.filterArray.indexOf機能を使用して非常に簡単な方法があります:

var arr = [{'id':1,name:'x1'},{'id':2,name:'x2'},{'id':3,name:'x3'}]; 

arr = arr.filter(function(val){ 
    return [1,2,3].indexOf(val.id) !== -1; 
}); 

console.log(JSON.stringify(arr, 0, 4)); 

出力:私はforEachののリターンは、フィルタのリターンまで気泡が考え

[ 
    { 
     "id": 1, 
     "name": "x1" 
    }, 
    { 
     "id": 2, 
     "name": "x2" 
    }, 
    { 
     "id": 3, 
     "name": "x3" 
    } 
] 
+0

はこれが最も簡単でシンプルなオプションだと私は疑念を抱いていましたが、forEachコールバックの戻り値がフィルタコールバックに到達したかどうか、@ squintのコメントとmohitの答えが私の疑問を解決しました。 – MeanMan

関連する問題