2017-02-04 10 views
0

私はよくある問題を抱えており、誰かがそれを解決する良い方法を持っているかどうかを知りたかったのです。もしforループが私が望むものを見つけられないなら何かをしてください

オブジェクトを見つけて更新するために配列をループしたいと思います。オブジェクトが存在しない場合は、配列に追加する必要があります。私は通常、問題をより複雑にするより複雑なオブジェクトを扱っています。

var movies = [ 
    { _id: 1, title:"Movie 1" }, 
    { _id: 2, title: "Another Movie" } 
]; 

var myTheater = { location:"here", current_movies: movies }; 

// A movie to check. The _id may or may not be in movies. 
var aMovie = { _id: 3, title: "Something New" }; 

// boolean flag to let us know if something happened 
var updated = false; 

// look through all movies and my theater and update as needed 
for(var i = 0, len = myTheater.current_movies.length; i<len; i++){ 
    if(myTheater.current_movies[i]._id === aMovie._id){ 
     console.log("Updating movie name."); 
     myTheater.current_movies[i].title = aMovie.title; 
     updated = true; 
     break; 
    } 
} 

// check if anything was updated and add the movie if not 
if(!updated){ 
    myTheater.current_movies.push(aMovie); 
} 

これを行うより良い方法がありますか、フラグを使用するのが最適ですか?ありがとう!

+0

あなたがオブジェクトを検索した後、複数の一致があることができない限り、あなたは、ループを終了するには、 'break'を使用する必要があります。 – Barmar

答えて

1

このようなネイティブArray.prototype.findを使用します。

var movies = [{ _id: 1, title:"Movie 1" }, { _id: 2, title: "Another Movie" }]; 
 
var myTheater = { location:"here", current_movies: movies }; 
 
var aMovie = { _id: 3, title: "Something New" }; 
 

 

 

 
// check if there is a movie with the same id as aMovie 
 
var found = myTheater.current_movies.find(m => m._id == aMovie._id); 
 

 
if(found) // if we found something 
 
    found.title = aMovie.title; // update it's title 
 
else 
 
    /*things to do if nothing was found*/ 
 
    console.log("nothing found!");

アロー機能:

findに渡された関数(コールバック)は、Arrow Functionと呼ばれます。あなたはこのような定期的な機能を使用してfindを呼び出すことができます。

var found = myTheater.current_movies.find(function(m) { 
    return m._id == aMovie._id; 
}); 
+0

私は '=>'にあまり慣れていません。あなたのfind関数は効果的に 'currentMovies.find(function(m){return m._id == aMovie._id}'ですか? – jrose

+0

@jrose私の答えは** Arrow Functions **セクションを参照してください。 Mozillaでも同様です。 –

-1

IDとしてIDまたは別の属性を使用するだけで、最後のエントリが100の場合は101を検索する必要はありません。配列のサイズやループをチェックしてidの値とifそこにそれを挿入することはできません。 javascriptにはすでにこれを行うための機能が用意されています。

+0

提案をする代わりに質問に答えてください。答えが良ければ、代わりにコメントする必要がある代理人が手に入ります – mplungjan

+0

私が書いたものに焦点を当ててコメントしたのではなく、質問に答えていることが分かります。 OPによって実行されるタイトルベースの比較の代わりに、IDベースは適切な結果をもたらすだろう。私がコード全体をコピーして、単なる説明的な行を変更すると思っていない限り、間違っているとは思わない。 –

+0

ようこそ。 a)私は投票しなかったし、b)はい、受け入れられた答えのような '<>'ボタンを使ってコードを[mcve]にコピーすることに注意してください。答えるには[ヘルプ]をご覧ください。私は自分自身に自分のコメントを残して、あなたのコメントが投票された理由を疑問に思っていた。 – mplungjan

0

は、あなたはそれが私が.find()を使用してに同意

var movies = [{ _id: 1, title:"Movie 1" }, 
     { _id: 2, title: "Another Movie" } 
    ]; 
    var myTheater = { location:"here", current_movies: movies }; 
    var aMovie = { _id: 1, title: "Something New" }; 
    var movie = myTheater.current_movies.find(function(x){ 
    if(x._id===aMovie._id){ 
     console.log("Updating movie name."); 
     x.title = aMovie.title; 
     return true; 
    } 
    }); 
    if(!movie){ 
    myTheater.current_movies.push(aMovie); 
    } 
1

をしない場合、それをチェックし、更新映画が存在する場合と更新するArray.findを使用できますが、テスト関数内の任意のデータを変異させるべきではありません。代わりに、それを使ってアイテムを見つけて、それが何を返すか(映画かundefined)ここ.find()について

function createOrUpdate(draftMovie) { 
    var film = movies.find(function(savedMovie){ 
    return savedMovie._id == draftMovie._id; 
    }) 

    if(film){ 
    return film.title = draftMovie.title; 
    } else { 
    return myTheater.currentMovies.push(draftMovie); 
    } 
} 

より:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/find

1

まず映画が、それはあなたが更新含まれている場合はそうでないあなただけのこれまであなたがdynamicaly作成aMovie

を押し、ID
が含まれている場合、あなたは見つけますムービーにidとその位置が含まれているかどうかを簡単に知るためのIDの配列:

var movies = [ 
 
     { id: 1, title:"Movie 1" }, 
 
     { id: 2, title: "Another Movie" } 
 
    ]; 
 
var aMovie = { id: 3, title: "Something New" }; 
 
var index = movies.map(x => x.id).indexOf(aMovie.id); 
 
if (index !== -1) movies[index].title = aMovie.title; 
 
else movies.push(aMovie); 
 
console.log(movies);

関連する問題