2016-07-05 23 views
0

私はかなり奇妙な問題に直面しています。私はListの型を反復しています。私のループの中では、イテレータ変数を別のローカルオブジェクトに割り当てます。そのローカルオブジェクト内の何かを変更すると、どのループが繰り返し実行されているかのリストが変更されます。コードサンプルでこれをクリアしてみましょう。 繰り返しリストの値に影響を与えるForeachループ内の計算

var balances = DBHelperADO.Select("select * from Orders"); 
// balances is of type List<MyModel> 

foreach (var item in balances) 
{ 
    MyModel model = new MyModel(); 
    model = item; 
    var thisQty = details.Where(x => x.Code == item.Code).Sum(x => x.QTY); 

    // details is another List<MyModel> holding values from the GUI 

    model.BLNC = model.BLNC - thisQty; 
    model.VAL = (model.BLNC == 0) ? 0 : model.VAL - (thisQty * model.RATE); 
    model.TABLE = "Orders"; 
    toUpdate.Add(model); // toUpdate is a List<MyModel>      
} 

は今、私の理解では、(この場合は アイテム)イテレータ変数が読み取り専用であることを、私が書くときです:

モデル=項目;

私は私のアイテム値のコピーを作っています。しかし、モデルオブジェクトの計算を行うと、天びんリストの同じ変更が発生します。

私はなぜそれがバランスリストに反映されているのか分かりません。私はローカルスコープのモデルオブジェクトの計算を行っています。それでは、それらが反復リスト(天びん)に反映されているのはなぜですか?

私が間違っていることを助けてください。

よろしく

答えて

3

残高の要素のタイプがクラスタイプであり、構造体ではないとします。

それではitemmodelに格納されると、そのクラスのインスタンス参照あります。 model = item;を割り当てる場合インスタンスをコピーせず、参照のみをインスタンスにコピーしてください。

model.BLNC = ...でそのインスタンスのプロパティにアクセスすると、元のインスタンスのプロパティが変更されます。 item.BLNC = ...

最初の行MyModel model = new MyModel()は、その新しいインスタンスへの参照を上書きすると、かなり古くなっています。本物のコピーを作成する

あなたは

MyModel model = new MyModel 
{  
    BLNC = item.BLNC, 
    VAL = item.VAL, 
    TABLE = "Orders" 
    // ... copy further properties 
}; 

ような何かを試すことができますまた、完全にこのようなLINQ Select文を使用して、あなたのループを書き換えることができます:

var toUpdate = balances.Select(item => 
    { 
     var thisQty = details.Where(x => x.Code == item.Code).Sum(x => x.QTY); 
     var blnc = item.BLNC - thisQty; 
     return new MyModel 
     { 
      BLNC = blnc, 
      VAL = (blnc == 0) ? 0 : item.VAL - (thisQty * item.RATE), 
      RATE = item.RATE, 
      TABLE = "Orders" 
     }; 
    }).ToList(); 

あなたがする必要がありますあなたのMyModelクラスのプロパティをitemから新しいインスタンスにコピーしてください。ネストされたクエリに問題がある場合は、balances.AsEnumerable()を使用する必要があります。

+0

大変ありがとうございます。そのLINQの選択は本当にエレガントです。 –

3

model = item;参照、ないコピーします。

model.BLNC = model.BLNC - thisQty; updats 参照、つまり元のオブジェクトの値を更新します。

toUpdate.Add(model);参照を元のリストの元のオブジェクトに戻して新しいリストに戻します。

関連する問題