2010-09-22 8 views
0

j'ai le code comme celui-ciParsing une classe de type en C#

public class People 
{ 
    public string name { get; set; } 
} 

public class Animal 
{ 
    public string age { get; set; } 
} 

class Test 
{ 
    public void DataPeopleList() 
    { 
     string sql = "SELECT * FROM People"; 
     SqlCommand cmd = new SqlCommand(sql, conn); 
     SqlDataReader rdr = cmd.ExecuteReader(); 
     List<People> list = new List<People>(); 
     while (rdr.Read()) { 
      People p = new People(); 
      p.name = rdr["name"].ToString(); 
      list.Add(p); 
     } 
     rdr.Close();    
    } 

    public void DataAnimalList() 
    { 
     string sql = "SELECT * FROM Animal"; 
     SqlCommand cmd = new SqlCommand(sql, conn); 
     SqlDataReader rdr = cmd.ExecuteReader(); 
     List<People> list = new List<People>(); 
     while (rdr.Read()) 
     { 
      People p = new People(); 
      p.name = rdr["age"].ToString(); 
      list.Add(p); 
     } 
     rdr.Close(); 
    } 
} 

je pense est pas bon pour moi. puis-je écrire donner la classe en tant que paramètre donc quand je veux charger les données que je viens de donner requête et classe comme parameter..example le code que je veux comme:

public void LoadData(string query, Type ClassName) 
    { 
     SqlCommand cmd = new SqlCommand(sql, conn); 
     SqlDataReader rdr = cmd.ExecuteReader(); 
     List<ClassName> list = new List<ClassName>(); 
     while (rdr.Read()) 
     { 
      ClassName p = new ClassName(); 
      //p.name = rdr["age"].ToString(); i dont have idea in this part 
      list.Add(p); 
     } 
     rdr.Close(); 
    } 

donc assez I`m appeler la méthode comme

public void DataAnimalList() 
    { 
     string sql = "SELECT * FROM Animal"; 
     LoadData(sql,class Animal); 
    } 

pouvez-vous me donner une réponse ou soupçon .. Merci à l'avance

+1

Avez-vous envisagé de tirer parti d'un ORM à la place? –

Répondre

0

Je me sens, ce que vous pensez peut-être pas très élégant Solution. Parce que

1) Vous pouvez utiliser la réflexion mais qui peut entraîner des performances médiocres. Donc, mieux vaut ne pas aller jusqu'au bout, c'est vraiment nécessaire.

2) Aussi, demain, si les colonnes à traiter dans le jeu de résultats change, alors vous devez aller modifier le code sinon votre code pourrait échouer. Donc, mieux peut-être que vous pouvez aller pour un cadre ORM comme suggéré par Ani.

+0

ouais, je vais essayer d'utiliser NHibernate .. merci pour des conseils .. :) –

6

Il y a plusieurs façons que vous pouvez accomplir quelque chose comme ça avec la réflexion, mais je fortement vous recommandons de passer à l'aide d'un framewor ORM k comme ADO.NET Entity Framework, Linq to SQL ou NHibernate à la place.

Vous pouvez lire:

+2

+1. Pourquoi écrire ce genre de code quand tout a été fait une centaine de fois, et que les développeurs peuvent réellement écrire du code de valeur commerciale? –

+0

D'accord - investissez 10% du temps dans l'apprentissage de l'ORM de votre choix, comme NHibernate, EF, ActiveRecord, etc., et concentrez-vous sur la création de valeur. Jetez un oeil à http://ayende.com/Blog/archive/2008/11/21/stealing-from-your-client.aspx –

0

Si je suis votre question tout de suite ce que vous cherchez est Polymorphisme. Essayez ceci:

void DataList(IType var) 
{ 
    if(IType is Animal) 
    { 
    //Do something for Animal 
    } 

    if(IType is People) 
    { 
    //Do something for People 
    } 
} 

La classe Animal et People implémenterait l'interface IType, qui peut être une interface vide. Une meilleure conception consisterait à modifier votre structure de code et à déplacer la méthode DataList vers IType et à l'implémenter en conséquence dans votre classe People et Animal. Plus d'une façon de peau le chat, vous voyez :)

+0

Toujours pas trop aider - les propriétés qu'il veut définir à la suite de la requête sont des membres des sous-classes, pas la classe de base. Créer une méthode réutilisable qui peut définir les propriétés sur un objet à partir des résultats dans un ensemble de données, sans connaître le type de l'objet est compliqué. –

+0

Si le type est connu (ce que nous savons dans ce cas) alors je ne vois aucun problème ici. –

+0

merci pour les conseils :) –

1

Vous pouvez utiliser des génériques. Je pense que cela peut être fait comme ceci:

public List<T> LoadData<T> (String query) { 
    SqlCommand cmd = new SqlCommand(query, conn); 
    SqlDataReader rdr = cmd.ExecuteReader(); 
    List<T> list = new List<T>(); 
    while (rdr.Read()) 
    { 
     T p = new T(rdr[0]); 
     list.Add(p); 
    } 
    rdr.Close(); 

    return list; 
} 

Si vous devez créer un constructeur pour chaque classe qui accepte les données en tant que paramètre. Vous pouvez modifier un peu le code et utiliser un DataAdapter pour remplir un DataTable, puis créer un constructeur qui accepte DataRow comme argument afin de pouvoir instancier des classes avec un nombre différent d'éléments.

Mais si vous obtenez un plus compliqué avec cela, je suggère d'utiliser un certain cadre ORM comme LINQ to SQL, Entity Framework, NHibernate ...

0

Vous pourriez avoir quelque chose comme celui-ci où un délégué est utilisé pour remplir l'objet du lecteur de données:

public List<T> LoadData<T>(string sql, Action<IDataReader, T> fill) where T : new() 
{ 
    using(SqlCommand cmd = new SqlCommand(sql, conn)) 
    using(SqlDataReader reader = cmd.ExecuteReader()) 
    { 
    List<T> items = new List<T>(); 
    while(reader.Read()) 
    { 
     T item = new T(); 
     fill(reader, item); 
     items.Add(item); 
    } 
    return items; 
    } 
} 

utiliser ensuite comme ceci:

public List<Person> LoadPeople() 
{ 
    return LoadData<Person>("SELECT * FROM Person", (r, p) => 
    { 
     p.Name = r["Name"].ToString(); 
    }); 
} 

Mais vraiment vous devriez utiliser un ORM.