2016-08-07 1 views
2

J'ai une requête linq qui produit une séquence de types anonymes. La requête est définie comme:Comment déclarer une variable globale pour une requête linq qui produit une séquence de types anonymes

var query = from a in Db.Table1 
    join b from Db.Table2 
    join... 
    ... 
    select new { 
    a.field1, a.field2, 
    b.field1, NewName = b.field2 }; 

Maintenant, je voudrais utiliser cette requête dans le scénario suivant:

if (x == 1) 
{ query = ... 
    ...rest of code_1 } 
if (x == 2) 
{ query = ... 
    ...rest of code_2 } 

« requête » de la première « si » utilisera différentes tables, jointures et où la déclaration que la requête de la seconde 'if', mais les deux auront exactement la même déclaration 'select new'. Pour cela, j'ai besoin de déclarer une variable 'query' qui sera visible dans les instructions 'if'.

Quand je suis « type » de la « requête » en utilisant:

query.GetType().ToString(); 

il me donne:

query type = 'System.Data.Objects.ObjectQuery`1[<>f__AnonymousType7`14[System.Int32,System.String,System.String,System.String,System.Nullable`1[System.DateTime],System.Decimal,System.Nullable`1[System.DateTime],System.Decimal,System.String,System.String,System.String,System.String,System.String,System.String]]' 

Je ne peux pas déclarer une classe distincte que je ne peux écrire dans un méthode que j'écris le code de. Comment dois-je déclarer une variable 'query'?

+0

Vous pouvez utiliser le 'IQeuryable'or non générique' dynamic'. – Michael

+0

On dirait beaucoup de problèmes juste pour créer des problèmes pour vous-même. –

+0

Avec IQueryable je ne serai pas en mesure d'utiliser plus tard if (query.Count()> 0) - ai-je raison? – phoenix

Répondre

1

La seule façon que je vois est de définir à l'aide exemple comme ceci:

var query = Enumerable.Repeat(new 
{ 
    field1 = default(int), 
    field2 = default(string), 
    field3 = default(string), 
    // other fields ...   
}, 0).AsQueryable(); 

field1, field2 etc., doivent être vos noms de propriétés en béton avec leurs types réels, dans l'ordre exact utilisé à l'intérieur les sélections intérieures.

+0

field1, field2 etc. sont juste des champs. Je ne voulais pas dire nom/propriété de a.field1 est le même que pour b.field1. Mais je comprends ce que vous voulez dire ... et j'en suis conscient. – phoenix

+0

Oui, désolé, c'est ce que je pensais. Mais j'avais besoin d'un nom/type concret pour faire un exemple. De toute façon, je pense que vous avez compris, je vais supprimer cette partie de la réponse. –

+0

J'ai oublié de mentionner que votre solution fonctionne parfaitement pour moi! – phoenix

0

Dans la continuité de cette solution, je voudrais demander la possibilité d'utiliser une instruction dynamique 'where'. Lors de la recherche pour cela, j'ai été redirigé plusieurs fois vers une solution basée sur la classe PredicateBuilder mais cela nécessite une syntaxe de méthode au lieu de la syntaxe de requête. Ai-je besoin de convertir ma requête en lambda ou existe-t-il un autre moyen d'y parvenir?

Mon plus « où » (comme je l'ai déjà quelques « où » conditions) déclaration devrait ressembler à:

where 
(a.field1 = a[0] and b.field1 = b[0]) || 
(a.field1 = a[1] and b.field2 = b[1]) || 
(a.field1 = a[2] and b.field2 = b[2]) || 
.... 
(a.field1 = a[a.Length] and b.field2 = b[b.Length])