-1

次のコードが機能していません:

var x = from user in db.tblUsers
        select new
        {
            user.Id,
            user.FirstName,
            user.LastName,
            NumOfWins = SqlFactory.GetNumberOfWinsByUser(user.Id)
        };

TblBindingSource.DataSource = x.OrderByDescending(user => user.NumOfWins);
dataGridView1.DataSource = TblBindingSource.DataSource; //<-- fail here

エラー:

メソッド'Int32GetNumberOfWinsByUser(Int32)'には、SQLへの変換がサポートされていません。

SqlFactory.GetNumberOfWinsByUser(user.Id)私はそれが良い値を返すことを知っています。誰かがこれについて私を助けることができますか?前もって感謝します。

4

2 に答える 2

2

答えはエラーにあります。linq を SQL に変換するエンティティ フレームワークなどの linq プロバイダーを使用していることは明らかです。メソッド SqlFactory.GetNumberOfWinsByUser(user.Id) を SQL ステートメントに変換できません。使用したい場合は、次のようにする必要があります。

from user in db.tblUsers.ToList()
          select new { user.Id, user.FirstName, user.LastName, NumOfWins =     SqlFactory.GetNumberOfWinsByUser(user.Id) };

これにより、最初にデータをメモリにフェッチしてから、選択ステートメントで変換を適用するように強制されます。

上記は非常に非効率的だと思いますが、それは単なる推測です。

于 2013-03-05T14:14:32.850 に答える
0

この種の関数の Linq2SQL クエリへの埋め込みを行う方法があります。ただし、関数 (GetNumberOfWinsByUser()この場合) 自体Expression<Func<>>を、プロバイダーによって式を SQL に変換できる型として記述できる場合に限ります。

これは Tomáš Petříček によって考案され、彼のブログで次のように説明されています。

http://toasp.net/blog/dynamic-linq-queries.aspx

式を定義する方法について説明します。

Expression<Func<Nwind.Product, decimal?>> calcPrice = 
  (p) => p.UnitPrice * 1.19m;

次に、それを Linq to SQL クエリに埋め込みます。

var q = 
   from p in db.Products.ToExpandable()  
   where calcPrice.Expand(p) > 30.0m
   select new { 
     p.ProductName, 
     OriginalPrice = p.UnitPrice,
     ShopPrice = calcPrice.Expand(p) };

彼が作成した拡張メソッドToExpandable()を使用します (コードはダウンロード可能です)。

これにより、部分的な結果セットをメモリに実体化することなく、クエリ全体を SQL に解析して DB サーバーで実行できます。非常に効率的で、非常に複雑なクエリを処理できるようにする必要があります。一般的に、ロジックを式にカプセル化すると、再利用性に優れた単純なコードになることがわかりました。

私はこれをプロジェクトで広範囲に使用しましたが、非常にうまく機能します。ただし、表現をよく理解する必要があります。

于 2013-03-05T14:40:47.873 に答える