F#中泛型类型的运行时强制

时间:2012-01-26 23:22:29

标签: .net f#

我在F#中有一个带有显式泛型参数的基类。我正在尝试检查我使用的给定类型是否实现了特定的接口。我想“如果ob:?ISysAware那么”会做,但抱怨总是一样的:

let (|SysAware|_|) t = 
    match t with
    | :? ISysAware as p -> Some(p)
    | _ -> None

错误FS0008:从类型'a到ISysAware的此运行时强制或类型测试涉及基于此程序点之前的信息的不确定类型。某些类型不允许运行时类型测试。需要进一步的类型注释。

显然,我宁愿不在这里使用反射。 IsAssignableFrom会以高成本完成这个任务。

思想?

2 个答案:

答案 0 :(得分:14)

有些F#类型是值类型;添加box可确保仅对引用类型执行类型测试:

let (|SysAware|_|) t = 
    match box t with
    | :? ISysAware as p -> Some(p)
    | _ -> None

答案 1 :(得分:5)

错误的原因是类型检查器被混淆,因为它无法解决类型,解决方案 - 类似于pad是添加类型注释

let (|SysAware|_|) (t:obj) = 
    match t with
    | :? ISysAware as p -> Some(p)
    | _ -> None