typeof< _>的使用活动模式 [英] Use of typeof<_> in active pattern
问题描述
给出以下人为设计的活动模式:
Given the following contrived active pattern:
let (|TypeDef|_|) (typeDef:Type) (value:obj) =
if obj.ReferenceEquals(value, null) then None
else
let typ = value.GetType()
if typ.IsGenericType && typ.GetGenericTypeDefinition() = typeDef then Some(typ.GetGenericArguments())
else None
以下内容:
let dict = System.Collections.Generic.Dictionary<string,obj>()
match dict with
| TypeDef typedefof<Dictionary<_,_>> typeArgs -> printfn "%A" typeArgs
| _ -> ()
给出错误:
模式匹配中的意外类型应用程序.预期为->"或其他令牌.
Unexpected type application in pattern matching. Expected '->' or other token.
但这可行:
let typ = typedefof<Dictionary<_,_>>
match dict with
| TypeDef typ typeArgs -> printfn "%A" typeArgs
| _ -> ()
为什么这里不允许使用 typedefof
(或 typeof
)?
Why is typedefof
(or typeof
) not allowed here?
推荐答案
即使您使用参数化的活动模式(参数是某些表达式),编译器也会将参数解析为模式(与表达式相反)),因此语法受到更多限制.
Even if you're using a parameterized active pattern (where the argument is some expression), the compiler parses the argument as a pattern (as opposed to an expression), so the syntax is more restricted.
I think this is essentially the same problem as the one discussed here: How can I pass complex expression to parametrized active pattern? (I'm not sure about the actual compiler implementation, but the F# specification says that it should parse as a pattern).
作为一种解决方法,您可以在引号内编写任何表达式,因此可以执行以下操作:
As a workaround, you can write any expression inside a quotation, so you could do this:
let undef<'T> : 'T = Unchecked.defaultof<_>
let (|TypeDef|) (typeExpr:Expr) (value:obj) =
let typeDef = typeExpr.Type.GetGenericTypeDefinition()
// ...
let dict = System.Collections.Generic.Dictionary<string,obj>()
match dict with
| TypeDef <@ undef<Dictionary<_,_>> @> typeArgs -> printfn "%A" typeArgs
| _ -> ()
这篇关于typeof< _>的使用活动模式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!