2010-01-28 8 views
11

Dopo alcuni tutorial e così sono riuscito a creare una classe di raccolta che eredita la funzionalità necessaria per creare un DataTable che può essere passato a una stored procedure del server SQL come parametro del valore di tabella. Tutto sembra funzionare bene; Posso ottenere tutte le righe aggiunte e sembra bello. Tuttavia, dopo un'osservazione più ravvicinata, noto che quando aggiungo una nuova riga, i dati di tutte le righe precedenti vengono sovrascritti con il valore della nuova riga. Quindi se ho una riga con un valore stringa di "pippo" e aggiungo una seconda riga con il valore "bar", verrà inserita la seconda riga (creando un DataTable con due righe) ma entrambe le righe avranno il valore "bar" ". Qualcuno può capire perché questo sarebbe? Ecco parte del codice, che funziona ma è stato un po 'semplificato (la classe Tag è stata ridotta per facilità di spiegazione).Perché l'aggiunta di un nuovo valore all'elenco <> sovrascrive i valori precedenti nell'elenco <>

Quello che segue è della classe Collection:

using System; 
using System.Collections.Generic; 
using System.Data; 
using System.Linq; 
using System.Web; 
using Microsoft.SqlServer.Server; 

namespace TagTableBuilder 
{ 
public class TagCollection : List<Tag>, IEnumerable<SqlDataRecord> 
{ 
    IEnumerator<SqlDataRecord> IEnumerable<SqlDataRecord>.GetEnumerator() 
    { 
     var sdr = new SqlDataRecord(
      new SqlMetaData("Tag", SqlDbType.NVarChar) 
      ); 

     foreach (Tag t in this) 
     { 
      sdr.SetSqlString(0, t.tagName); 

      yield return sdr; 
     } 
    } 
} 

public class Tag 
{ 
    public string tagName { get; set; } 
} 
} 

Questi sono chiamati come segue:

//Create instance of collection 
TagCollection tags = new TagCollection(); 

//Create instance of object 
Tag _tag = new Tag(); 

foreach (string t in tagList) 
{ 
    //Add value to class propety 
    _tag.tagName = t; 
    //Add class to collection, this is where all previously added rows are overwritten 
    tags.Add(_tag); 
} 
+0

Sì, dovrei risolvere il problema grazie! –

risposta

25

Stai utilizzando la stessa istanza dell'oggetto Tag all'interno del ciclo, in modo che ogni aggiornamento il tagName è allo stesso riferimento. Spostare la dichiarazione all'interno del ciclo per ottenere un oggetto fresca su ogni passaggio del ciclo:

foreach (string t in tagList) 
{ 
    Tag _tag = new Tag(); 

    //Add value to class propety 
    _tag.tagName = t; 
    //Add class to collection, this is where all previously added rows are overwritten 
    tags.Add(_tag); 
} 

Si noti anche che ho aggiornato l'ultima riga per aggiungere _tag invece di mTag come io non vedo questo definito da nessuna parte.

2

Nel ciclo in cui si aggiungono i tag alla raccolta, si sta utilizzando la stessa istanza di oggetto di Tag. In sostanza, stai impostando il nome di un tag sul primo valore in tagList e aggiungendolo alla raccolta, quindi stai cambiando lo stesso nome del tag sul secondo valore in tagList e lo aggiungi nuovamente alla raccolta.

La tua raccolta di Tag contiene diversi riferimenti allo stesso oggetto Tag! Crea un'istanza di _tag all'interno del ciclo for ogni volta prima di impostare il nome del tag e aggiungerlo alla raccolta.

Problemi correlati