2012-01-25 21 views
0

は、私は次のメソッドを持っている真を返した後に反復を停止しますか?

(より良い質問を記述するタイトルにそれを編集すること自由に感じ、より良いタイトルを考えることができませんでした):

bool CalculateNewState(int adjacent, bool currentState) 
    { 
     if (currentState == true) 
     { 
      foreach (int n in liveRule) 
      { 
       if (adjacent == n) 
       { 
        return true; 
       }    
      } 
      return false; 
     } 
     else 
     { 
      foreach (int n in becomeAliveRule) 
      { 
       if (adjacent == n) 
       { 
        return true; 
       }    
      } 
      return false; 
     } 
    } 

これはgame of lifeクローンのためです。私が実装したいのは、ユーザーが自分のルールを作ることができるということです。

bool currentStateは、細胞が生存しているかどうかをメソッドに伝えます。 int adjacentは、セルにいくつの生きている近隣があるかをメソッドに通知します。

私がこれで達成したいのは、ユーザーが言うとき: 2,3 and 5 neighbors keep the cell aliveです。 2,3 and 5を保持する配列(liveRule)を反復処理します。一致が発生した場合はtrue、それ以外の場合はfalseを返します。

ここで起こるのは、trueを返すと、繰り返し処理を継続し、最終的にliveRuleの要素が一致するかどうかを返します。

一致が発生した後に反復処理を停止するには、何が必要ですか?

私はこの問題に間違ったアプローチをしている可能性があります。私は提案hereから始めました。これはUnity3DでのC#で

は(自分の能力を最大限にそれを記述しようとしたが、それはまだかなり不明確と思われます)。

+1

"ここで何が起きるかは、真を返すと、反復し続けます" - あなたは確信していますか?起こっていますか? – AakashM

+0

私は二重チェックをしますが、私はそれが起こっていることを確信しています。 –

+1

'return'ステートメントに達すると、メソッドのスコープを離れるので、' foreach'が反復処理を続ける方法はありません。これがあなたが経験していると思われるものだとすれば、私はこの方法よりもバグが他の場所にあると考えています... – madd0

答えて

6

あなたが実装したコードでは、「隣同士が2,3、または5のいずれにも等しくない場合は、返されます」と表示されます。明らかに隣接するものはと同じではありません。すべてです!

最初からやり直してください。より明確になるようにメソッドの名前を変更します。ブール値は、真/偽の質問に答えるので、質問して名前を選択する必要があります。

bool IsCellAlive(int adjacentCount, bool isAlive) 
{ 
    if (isAlive) 
     return liveRule.Contains(adjacentCount); 
    else 
     return deadRule.Contains(adjacentCount); 
} 

をforeachループよりも遅いので、これはパフォーマンス上の問題を引き起こす可能性があります「が含ま」。今はそれを心配しないでください。コードも正しくになっていません。 になるようにコードを書いてください。が正しいことを確認してから、プロファイラを使用して速度が遅い場合は遅い場所を見つけてください。

を覚えておいてください。正しいことを確認してから、明確にしてから、速くします。

+0

名前を説明していただきありがとうございます! (これはまだ学校では学ばなかったものです)。私はあなたのソリューションを試しました、そして、それは 'Contains'メソッドが存在しないように見えます。 –

+1

@SimonVerbeke:プログラムの一番上に 'using System.Linq;'を入れてください。 C#3以上を使用してください。 –

+0

それは認識されています:)それは役に立たなかったので、私はデバッグを続け、間違った配列(グリッドの代わりにnewGrid)に戻り値を割り当てていたことに気付きました。再び、愚かな間違い...ありがとう! –

1

returnステートメントはすぐにCalculateNewStateメソッドを終了します。反復が続行されていることがわかった場合、returnステートメント(adjacent == nは決して真ではありません)に当てはまらないか、おそらくCalculateNewStateがコードのどこかから繰り返し呼び出されているかのいずれかです。

あなたはおそらくのようなものをはるかに単純に書き換えることができます:あなたはあなたの方法は、罰金のコードを呼び出すことで、問題のように見える説明されているものを考えると

if (currentState) 
    return liveRule.Contains(adjacent); 
return becomeAliveRule.Contains(adjacent); 
1

、あなたはそれを共有するだろうか? LINQを使用して

はあなたの方法は、単純に、単一の行にリファクタリングすることができます

usign System.Linq; 
bool CalculateNewState(int adjacent, bool currentState) 
{ 
    return (currentState ? liveRule : becomeAliveRule).Any(i => i == n); 
} 
+0

私はあなたのソリューションを試しましたが、 'Any'メソッドも認識していないようです。 (編集:ちょうど私がLINQを最初にインポートする必要があるかもしれないことに気づいた) –

+0

申し訳ありません、それを言いました、ちょうど 'using System.Linq'を追加してください – sll

0

あなたの平等のテストが犯人...あなたの代わりにadjacent != nadjacent == nをテストするべきではありませんているように見えますか?そうすれば、マッチでtrueを返し、一致しない場合にのみfalseを返します。

ループが終了した後もイテレータは続行されません。

+0

私は間違ってコピーしたときに私が間違っていたエラーでした。今は修正されています。 –

0

foreachの代わりにforループを使用して、追加の変数を使用できますか?

bool CalculateNewState(int adjacent, bool currentState) 
{ 
    if (currentState == true) 
    { 
     bool match = false; 
     for(int n = 0; n < liveRule.length && !match; n++) 
     { 
      if (adjacent != n) 
      { 
       match = true; 
      }    
     } 
     return match; 
    } 
    else 
    { 
     bool match = false; 
     for(int n = 0; n < becomeAliveRule.length && !match; n++) 
     { 
      if (adjacent != n) 
      { 
       match = true; 
      }    
     } 
     return match; 
    } 
} 
1

まあ、 "break"ステートメントを使用してループを終了することができます。

bool CalculateNewState(int adjacent, bool currentState) 
{ 
    if(currentState) 
    { 
     return IsStateMatch(adjacent, liveRule); 
    } 
    else 
    { 
     return IsStateMatch(adjacent, becomeAliveRule); 
    } 
} 

bool IsStateMatch(int adjacent, int[] rules) 
{ 
    bool finalState = false; 

    if(rules != null) 
    { 
     for(int i = 0; i < rules.length; i++) 
     { 
      if(adjacent == rules[i]) 
      { 
       finalState = true; 
       break; 
      } 
     } 
    } 

    return finalState; 
} 

私はこの方法をもう少し解読しましたが、これは基本的な考えです。今、私は他のポスターと、何が起こっているのかについて同意します。ブレーク/リターン文の後でループが継続している場合は、メソッドを間違って呼び出すバグのコードがあります。

関連する問題