2016-06-21 5 views
1

Entity Frameworkクエリに配列を含めることはできません。たとえば、これは失敗します。なぜEntity Frameworkクエリで配列を使用できないのですか?

var myRow = DbContext.myTable.Single(d => d.Property1 == myArray[0].Property1); 

しかし、私は最初にこのように変数にその要素を割り当てた場合:

var property1 = myArray[0].Property1; 
var myRow = DbContext.myTable.Single(d => d.Property1 == property1); 

を次にそれが動作します。なぜコンパイラーは私たちのためにこれをしませんか?これはすでに最適化を行い、他の多くの状況で構文的砂糖によるショートカットを提供しています。コンパイラが配列要素をバックグラウンドで一時変数にコピーするのを妨げる曖昧さの原因はありますか?それとも別の理由?

+0

これはC#コンパイラの制限ではなく、Linq to Entitiesプロバイダの制限です。 –

+1

コードの2番目の部分では、式の一部となる定数値を使用しているためです。最初のコード部分のlinqを式に変換することはできません。 –

+0

LINQ-to-EF/LINQ-to-SQLプロバイダによってSQLに変換されないほとんどの特定のメソッド/プロパティについて、多くの類似した(正確には重複しない)議論があります。私。 http://stackoverflow.com/questions/3360772/linq-contains-case-insensitiveには他のディスカッションへのリンクがあります。 –

答えて

3

Linq-to-objectsはこれをうまく処理できます。式をSQLに変換しようとするlinq-to-EF(またはLinq-to-SQL)です。値を変数に入れると、値を使用することをプロバイダに指示し、式を評価しません。

なぜコンパイラがこれを行うことができないのですか?

コンパイラは、SQLに変換される式とクエリがコンパイルされる前に評価される式を区別するようにはプログラムされていないためです。

LINQクエリは、クエリを使用して、結果を求めるまでを実行し、実際にはないことを意味し、遅延実行を使用しています。それまでは、フィルタ、投影、グループ化、集計などを構成する個々の式で構成されるクエリです。式d => d.Property1 == myArray[0].Property1を評価すると、ではなく、の式が評価されます。 、それはできないSQLに変換しようとします。

+0

コンパイラは、非同期的に(指定されたインデックスの要素が複数回変更されてから式が評価されるとき)同期的に実行される式ツリーを区別できないため(インデックス付きアクセスをその結果に変換する可能性があります) –

関連する問題