J'ai le SQL suivant, que j'essaie de traduire en LINQ:
SELECT f.value
FROM period as p
LEFT OUTER JOIN facts AS f ON p.id = f.periodid AND f.otherid = 17
WHERE p.companyid = 100
J'ai vu l'implémentation typique de la jointure externe gauche (c'est-à-dire, into x from y in x.DefaultIfEmpty()
etc.) mais je ne sais pas comment introduire l'autre condition de jointure ( AND f.otherid = 17
)
ÉDITER
Pourquoi la AND f.otherid = 17
condition fait-elle partie de JOIN plutôt que de la clause WHERE? Parce qu'il f
peut ne pas exister pour certaines lignes et je veux toujours que ces lignes soient incluses. Si la condition est appliquée dans la clause WHERE, après le JOIN - alors je n'obtiens pas le comportement souhaité.
Malheureusement ceci:
from p in context.Periods
join f in context.Facts on p.id equals f.periodid into fg
from fgi in fg.DefaultIfEmpty()
where p.companyid == 100 && fgi.otherid == 17
select f.value
semble être équivalent à ceci:
SELECT f.value
FROM period as p
LEFT OUTER JOIN facts AS f ON p.id = f.periodid
WHERE p.companyid = 100 AND f.otherid = 17
ce n'est pas tout à fait ce que je recherche.
Réponses:
Vous devez introduire votre condition de jointure avant d'appeler
DefaultIfEmpty()
. J'utiliserais simplement la syntaxe de la méthode d'extension:Ou vous pouvez utiliser une sous-requête:
la source
cela fonctionne aussi, ... si vous avez plusieurs jointures de colonnes
la source
Je sais que c'est " un peu tard ", mais juste au cas où quelqu'un aurait besoin de le faire dans la syntaxe de la méthode LINQ ( c'est pourquoi j'ai trouvé cet article au départ ), voici comment procéder:
la source
.Select(fact.Value)
devrait être.Select(f => f.Value)
Une autre option valide consiste à répartir les jointures sur plusieurs clauses LINQ , comme suit:
la source
Peut être écrit à l'aide de la clé de jointure composite. De plus, s'il est nécessaire de sélectionner des propriétés des côtés gauche et droit, LINQ peut être écrit comme
la source
Il me semble qu'il est utile d'envisager de réécrire votre code SQL avant d'essayer de le traduire.
Personnellement, j'écrirais une telle requête comme une union (même si j'éviterais complètement les valeurs nulles!):
Je suppose donc que je suis d'accord avec l'esprit de la réponse de @ MAbraham1 (bien que leur code ne semble pas lié à la question).
Cependant, il semble que la requête soit expressément conçue pour produire un résultat de colonne unique comprenant des lignes en double - en fait des valeurs nulles en double! Il est difficile de ne pas conclure que cette approche est imparfaite.
la source