2009-09-11 8 views
1

J'ai un DataTable et une liste d'objets. Je dois retourner toutes les lignes dans le DataTable où une propriété dans la liste est une certaine valeur. La liste est seulement utilisée pour filtrer la datatable (mais la colonne de filtre n'est pas contenue dans la datatable). Je suis sûr que cela doit être possible avec LINQ.Join DataTable with List <SomeObject>

Le DataTable contient:

MembershipID Username Password 
1    blah  blah  
2    blah  blah  
3    blah  blah  

Ma liste contient:

MembershipID Profile1 Profile2 Profile3 DifferentID 
1    blah  blah  blah A    
2    blah  blah  blah B    
3    blah  blah  blah C    

J'ai besoin de revenir (comme DataTable) - par exemple: pour GetUsersByDifferentID ("B"):

MembershipID Username Password 
2    blah  blah  
... 

Je pourrais obtenir la deuxième table en tant que DataTable si cela faciliterait la tâche, mais je pense que ce dont j'ai besoin est possible avec LI NQ. Je n'arrive pas à comprendre la syntaxe magique.

Répondre

2

Vous pouvez le faire en utilisant une jointure:

List<ListItem> listItems = //whatever 
DataTable dtItems = //whatever 

IEnumerable<DataRow> matchingRows = listItems 
    .Join( dtItems.AsEnumerable(), 
      listItem => listItem.MembershipID, 
      row => row.Field<int>("MembershipID"), 
      (r,li) => new { DifferentId = li.DifferentId, Row = r }) 
    .Where(ji => ji.DifferentID == "B") 
    .Select(ji => ji.Row); 

Modifier la clause where d'utiliser la valeur réelle que vous voulez faire correspondre ...

+0

Voilà, merci. :) – Echilon

+0

@Lee quand j'ai essayé de retourner 'ListCollection', il lance une exception. {{System.NotSupportedException: LINQ to Entities ne reconnaît pas la méthode System.Data.EnumerableRowCollection1 [System.Data.DataRow] AsEnumerable (System. Data.DataTable) 'méthode, et cette méthode ne peut pas être traduite en une expression de magasin. – joshua

1

Je ne suis pas sûr à ce sujet parce que je ne pouvais pas comprendre que beaucoup sur datatable que vous mentionnez au sujet mais vous pouvez essayer cette

var usersByDifferentId = yourList.Where(a=> a["DifferentID"] == "B").Select(a=> new {a["UserName"],a["MemberShipID"],a["Password"]}); 
+0

Je dois cela, mais l'inverse, pour revenir correspondant lignes du datatable basé sur le DifferentID dans la liste . – Echilon

+0

J'ai mis à jour ma réponse, pouvez-vous l'essayer? –

0

Je pense que vous voulez quelque chose comme:

var memberIds = myList.Where(u => u.DifferentID == "B").Select(a => a.MembershipID); 
var credentials = myDataTable.Where(d => memberIds.Contains(d.MembershipID)); 

Il peut être un moyen plus efficace de le faire, mais quelque chose comme ça devrait fonctionner.

2

Que diriez-vous de quelque chose comme ceci. Disons que votre liste est une collection de cette classe:

public class SomeMemberClass 
{ 
    public int MembershipId { get; set; } 
    public char DifferentId { get; set; } 
    //..some more properties 
} 

Ensuite, vous pouvez faire quelque chose comme ceci:

DataTable table = new DataTable(); 
table.Columns.Add("MembershipId", typeof(int)); 
table.Columns.Add("UserName"); 
table.Columns.Add("Password"); 

List<SomeMemberClass> list = new List<SomeMemberClass>(); //or get the list from somewhere else... 
var differntIds = list.Select(s => s.DifferentId).Distinct(); 

var result = table.AsEnumerable() 
         .Where(dt => differntIds 
         .Contains((int)dt["MembershipId"])) 
         .CopyToDataTable(); 

En fait, tout d'abord obtenir toutes les années distinctes de DifferentId puis de les utiliser pour regarder à travers votre table .

+0

Je pense que vous êtes proche. Je ne pense pas que vous ayez à vous soucier des entrées de liste distinctes car il semble que l'OP utilise la liste comme référence de recherche. La façon dont je l'ai compris est: passez dans le DifferentID, parcourez la liste et obtenez le MembershipID, puis utilisez cela pour renvoyer la ligne correspondante du DataTable (et renvoyez-la comme son propre DataTable). –

+0

Je fais juste distinct, de sorte que lorsque vous appelez Contient sur la liste, il doit regarder à travers moins d'éléments. – BFree