2009-04-10 17 views
5

昨日、特定の条件を満たすフォームですべてのコントロールを削除するコードを書きました。それを素朴に書いて、これが私が思いつくものです。ループ内のコントロールを削除する

for (int i = 0; i < this.Controls.Count; ++i) 
{ 
    if (this.Controls[i].Name.Length == 2) 
    { 
     this.Controls.Remove(this.Controls[i); 
    } 
} 

しかし、コードが間違っていることが起こります。私はそれからそれを次のように変更します:

foreach (Control ctr in this.pbBoardImage.Controls) 
{ 
    if (ctr.Length == 2) 
    { 
     this.Controls.Remove(ctr); 
    } 
} 

しかし、それでも正しいわけではありません。 私は正しい方法であろうことを知っている:

for (int i = this.Controls.Count - 1; i >= 0; i--) 
{ 
    if (this.Controls[i].Name.Length == 2) 
    { 
     this.Controls.Remove(this.Controls[i]); 
    } 
} 

しかし、それはまだエレガントな感じがしません。 this.ControlsはListではなかったので、List.RemoveAllは使用できませんでした。だから、私はよりエレガントな方法を、好ましくはループを使用せずに求めることができますか?

答えて

13

なぜこの回答が嫌いかわかりません...重要な点を強調しましたRemoveAt;しかし、.NET 3.5/C#3.0での代替として:LINQ:

 var qry = from Control control in Controls 
        where control.Name.Length == 2 
        select control; 

     foreach(var control in qry.ToList()) { 
      Controls.Remove(control); 
     } 

(オリジナル)foreach

あなたがすることができませんRemove - それはイテレータを破ります。ここでの一般的なアプローチは後方を反復することである。

for (int i = this.Controls.Count - 1; i >= 0; i--) { 
    if (this.Controls[i].Name.Length == 2) { 
     this.Controls.RemoveAt(i); // <=========== *** RemoveAt 
    } 
} 

これは「オフ一つ」問題回避など

+0

が私には良い答えのように思えます。私はそれを上回った。 –

+0

それは私ではありませんでしたが、正解です。だから+1! –

関連する問題