2010-11-10 6 views
0

J'ai un objet de collection de hiérarchie dans lequel j'essaie de récupérer la propriété de l'objet de dernier niveau dans Linq. Je ne veux pas écrire une méthode get pour chaque propriété. Je ne sais pas comment y parvenir grâce au sélecteurPropriété générique getter dans Linq

Class Test { 
    public int ID { get; set; } 
    public int PopertyA { get; set; } 
    public string PopertyB { get; set; } 
       ...Many more properties 

} 

public static TResult GetTest(hierarchyObject, int ID, Func<TSource, TResult> selector) 
{ 
    return (from level1 in hierarchyObject.Level1 
      from test in level1.Test 
      where test.ID.Equals(ID) 
      select selector).First(); 
} 

Ce travail de dint. Actuellement, j'ai fait la méthode pour retourner l'objet de test et accéder aux propriétés de la méthode appelante. Mais je voulais savoir si je pouvais implémenter un getter de propriété générique.

Edit:

Class Hierarcy{ 
    public IList<Level1> level1; 
} 

Class Level1 { 
public IList<Test> test; 
} 

Étant donné un objet et test.ID hierachy, je veux récupérer une propriété de test.

+3

Je l'ai lu à travers 5 fois et ne comprends toujours pas ce que vous essayez de faire ... – cjk

+0

Vous ne donnaient pas suffisamment détails. Comment votre "hiérarchie" est-elle organisée? Quel est le type de 'Level1'? S'il y a une sous-propriété nommée 'Level2' ou' Level3', de quel type s'agit-il? Que signifie "dernier niveau"? – Groo

+0

hierarchyObject a une collection de Level1 qui a une collection de Test – anivas

Répondre

1

Cela dépend de ce que vous voulez faire avec votre propriété. Pour éviter de répéter toute requête LINQ pour chaque propriété que vous êtes intéressé, il serait préférable d'obtenir l'objet de test en premier lieu, puis vérifiez ses propriétés individuelles:

class Hierarcy 
{ 
    public IList<Level1> Level1; 
    public Test GetTest(int ID) 
    { 
     return this 
      .Level1 
      .SelectMany(level => level.Test) 
      .Where(test => test.ID == ID) 
      .First(); 
    } 
} 

Une fois que vous obtenez la classe Test, vous ont toutes ses propriétés:

Test t = myHierarchy.GetTest(someId); 

// do something 
int i = test.PropertyA; 
string s = text.PropertyB; 

Si vous êtes intéressés à obtenir une valeur d'une propriété dynamique, en utilisant son nom seulement, vous pouvez le faire en utilisant la réflexion:

Test t = myHierarchy.GetTest(someId); 

// this will print all properties and their values 
foreach (PropertyInfo pi in t.GetType().GetProperties()) 
{ 
    Console.WriteLine("Name:{0}, Value:{1}", 
     pi.Name, 
     pi.GetValue(pi, null)); 
} 

Dans les deux exemples, la requête réelle n'est exécutée qu'une seule fois, ce qui peut être significatif s'il y a beaucoup d'objets dans vos collections.

0

Vous devez utiliser la chaîne de méthodes. Vous ne pouvez pas utiliser l'expression de requête. Au moins pour sélectionner une partie. Le repos peut rester en tant qu'expression de requête.

hiearchyObject.Level1.SelectMany(x=>x.Test).Where(test=>test.ID.Equals(ID)).Select(selector).First(); 

N'ayez pas de PC pour le tester maintenant.

également dans la méthode, vous devez soit déclarer la méthode tout comme acording générique sélecteur (mêmes paramètres génériques) ou utiliser public static TResult GetTest<TResult> (.. , Func<Test, TResult> selector)

+1

ne peut-il faire simplement 'select selector (test)'? – CodesInChaos

+0

Parce que dans votre cas, il crée une nouvelle méthode, qui appelle simplement la méthode de sélection. Dans mon cas, vous appelez directement en utilisant la méthode du sélecteur. – Euphoric

1

Je suppose que vous voudrez peut-être quelque chose comme ceci:

public static TResult GetTest(hierarchyObject, int ID, Func<Test, TResult> selector) 
{ 
    return (from level1 in hierarchyObject.Level1 
      from test in level1.Test 
      where test.ID.Equals(ID) 
      select selector(test)).First(); 
} 
Questions connexes