是否有一个简单的实现即可在通用F#查询中使用谓词函数 [英] Is there an easy implementation to use a predicate function in a generic F# query

查看:53
本文介绍了是否有一个简单的实现即可在通用F#查询中使用谓词函数的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想使用通用查询功能,例如:

I want to use a generic query function like:

let filter predicateFn =
    predicateFn |>
    fun f s -> query { for x in s do 
                       where (f(x)) 
                       select x }

其中f应该是谓词函数.显然,这不能转换为sql查询.但是是否有解决此问题的方法.我已经看到了C#的示例解决方案.

Where f should be a predicate function. Obviously, this cannot be translated to a sql query. But is there a solution for this problem. I have seen sample solutions for C#.

方法来自:Web,Cloud& Daniel Mohl的F#移动解决方案.

Approach taken from: Web, Cloud & Mobile Solutions with F# by Daniel Mohl.

要澄清的示例:

let userSorter = fun (u:users) -> u.Login

let sorted  =
    query { for user in dbConn.GetDataContext().Users do 
                sortBy ((fun (u:users) -> u.Login)(user))
                select user.Login }

基本上,我想用userSorter代替lambda.因为上面的代码正在运行,但这将失败:

Basically, I want to replace the lambda by the userSorter. As it is the above code runs, but this will fail:

let userSorter = fun (u:users) -> u.Login

let sorted  =
    query { for user in dbConn.GetDataContext().Users do 
                sortBy (userSorter(user))
                select user.Login }

推荐答案

终于找到了已经在Stackoverflow上的解决方案:

Finally found the solution, already on Stackoverflow:

open System.Linq
open Microsoft.FSharp.Quotations
open Microsoft.FSharp.Quotations.Patterns

let runQuery (q:Expr<IQueryable<'T>>) = 
  match q with
  | Application(Lambda(builder, Call(Some builder2, miRun, [Quote body])), queryObj) ->
      query.Run(Expr.Cast<Microsoft.FSharp.Linq.QuerySource<'T, IQueryable>>(body))
  | _ -> failwith "Wrong argument"

let test () =
  <@ query { for p in db.Products do
             where ((%predicate) p)
             select p.ProductName } @>
  |> runQuery
  |> Seq.iter (printfn "%s")

应归功于Tomas Petricek,您可以得到我的赏金!

Credits should go to Tomas Petricek, you can have my bounty!

要与"T"类型的任何查询结果匹配,请参阅我的其他 Q&A

To match against any query result of type 'T see my other Q&A

这篇关于是否有一个简单的实现即可在通用F#查询中使用谓词函数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆