我正在尝试在WinRT 8.1应用程序中的F#项目中使用Lex.Db数据库。
我正在按照这个C#教程进行操作。我已经成功地将Lex.Db引用添加到F#项目中,并且教程中的简单调用已经转换为f#并编译(例如:let db = new DbInstance("demo")
)。
问题在于这段C#代码:
db.Map<Contact>().Key(i => i.Id)
-- 编辑 --
为了让其他人不必再继续阅读,F# 3.0中几乎不存在这个问题。请参见下面kvb的评论。解决方案如下:
db.Map<Contact>().Key(fun i => i.Id)
-- /编辑 ---
Key
函数需要一个Expression<Func<Contact,'a>>
类型的参数,但我无法在F#中构建它。
一个非常相似的问题出现在如何将LinQ表达式从F#传递到C#代码中。推荐的解决方案是使用LeafExpressionConverter.QuotationToLambdaExpression
。
我尝试了以下方法:
type Contact() =
member val Id = 0 with get, set
member val FirstName = "" with get, set
let db = new DbInstance("Demo")
let idExpr = LeafExpressionConverter.QuotationToLambdaExpression
<@ fun (c : Contact) -> c.Id @>
db.Map<Contact>().Key(idExpr) |> ignore // <- Error
这会在idExpr
上产生编译错误:
类型不匹配。期望一个Expression<Func<Contact,'a>>
,但是给出了一个Expression<(Contact -> int)>
。类型'Func<Contact,'a>'
与类型'Contact -> int'
不匹配。
这个问题:从F#函数创建Expression<Func<T, bool>>似乎直接解决了问题,但是该解决方案使用了Microsoft.FSharp.Linq.QuotationEvaluation,在F# 3.0 for WinRT中找不到。
如何将<@ fun (c : Contact) -> c.Id @>
转换为Expression<Func<Contact,'a>>
?
db.Map<Contact>.Key(fun i -> i.Id)
会发生什么? F# 3.0应该在你传递一个lambda表达式到期望一个Expression
的位置时应用类型导向转换。 - kvb