Recursion 与现有变量的模式匹配

Recursion 与现有变量的模式匹配,recursion,map,f#,nested,Recursion,Map,F#,Nested,我有一个嵌套贴图的结构: [<RequireQualifiedAccess>] type NestedMap = | Object of Map<string,NestedMap> | Value of int 这是我的代码: let rec pruneWithKeyValue (keyvalue: string * int) (json: NestedMap) = let condition ck cv = let

我有一个嵌套贴图的结构:

[<RequireQualifiedAccess>]
type NestedMap =
    | Object of Map<string,NestedMap>
    | Value of int    
这是我的代码:

let rec pruneWithKeyValue (keyvalue: string * int) (json: NestedMap) =
    let condition ck cv  = 
        let tgtKey = (fst keyvalue)
        let tgtVal = (snd keyvalue)
        match (ck, cv) with
        | (tgtKey, NestedMap.Value(tgtVal)) -> 
            printfn ">>> Found match : "
            printfn "       ck = %s    " ck 
            printfn "       tgtKey and tgtVal == %s, %i" tgtKey tgtVal
            true
        | _ -> false
    match json with
    | NestedMap.Object nmap -> 
        if (nmap |> Map.exists (fun k v -> condition k v)) then 
            json
        else
            printfn "Expanding w keyvalue: (%s,%i): " (fst keyvalue) (snd keyvalue)
            let expanded = nmap |> Map.map (fun k v -> pruneWithKeyValue keyvalue v) 
            NestedMap.Object(expanded |>  Map.filter (fun k v -> v <> NestedMap.Object (Map.empty)))  
    | _ -> NestedMap.Object (Map.empty)

let pruned = pruneWithKeyValue ("S",20) l1
let res = (pruned = l1)
代码表示输出数据结构保持不变(
val remainsTheSame:bool=true
)。更有趣的是,包含函数正在搜索的键值对的
keyvalue
元组被修改了:

>>> Found match : 
       ck = Y    
       tgtKey and tgtVal == Y, 1
这就是问题所在。事实上,如果我硬编码
keyvalue
元组:

let rec pruneWithKeyValue (keyvalue: string * int) (json: NestedMap) =
    let condition ck cv  = 
        let tgtKey = (fst keyvalue)
        let tgtVal = (snd keyvalue)
        match (ck, cv) with
        | ("S", NestedMap.Value(20)) -> 
            printfn ">>> Found match : "
            printfn "       ck = %s    " ck 
            printfn "       tgtKey and tgtVal == %s, %i" tgtKey tgtVal
            true
        | _ -> false
    match json with
    | NestedMap.Object nmap -> 
        if (nmap |> Map.exists (fun k v -> condition k v)) then 
            json
        else
            printfn "Expanding w keyvalue: (%s,%i): " (fst keyvalue) (snd keyvalue)
            let expanded = nmap |> Map.map (fun k v -> pruneWithKeyValue keyvalue v) 
            NestedMap.Object(expanded |>  Map.filter (fun k v -> v <> NestedMap.Object (Map.empty)))  
    | _ -> NestedMap.Object (Map.empty)

let pruned = pruneWithKeyValue ("S",20) l1
let remainsTheSame = (pruned = l1)

这可能很琐碎,但我不明白
keyvalue
在哪里以及如何被修改,从而阻止我使用参数化键值元组获得正确的输出。

您无法对现有变量进行模式匹配,在您的原始代码中
tgtKey
tgtVal
将是新的绑定,与将被遮蔽的现有项目无关

因此,改变你的比赛:

    match (ck, cv) with
    | (tgtKey, NestedMap.Value(tgtVal)) -> 
致:

或者只是:

    match (ck, cv) with
    | x when x = (tgtKey, NestedMap.Value(tgtVal)) -> 

您无法对现有变量进行模式匹配,在原始代码中,
tgtKey
tgtVal
将是新绑定,与将被隐藏的现有绑定无关

因此,改变你的比赛:

    match (ck, cv) with
    | (tgtKey, NestedMap.Value(tgtVal)) -> 
致:

或者只是:

    match (ck, cv) with
    | x when x = (tgtKey, NestedMap.Value(tgtVal)) -> 

您无法对现有变量进行模式匹配,在原始代码中,
tgtKey
tgtVal
将是新绑定,与将被隐藏的现有绑定无关

因此,改变你的比赛:

    match (ck, cv) with
    | (tgtKey, NestedMap.Value(tgtVal)) -> 
致:

或者只是:

    match (ck, cv) with
    | x when x = (tgtKey, NestedMap.Value(tgtVal)) -> 

您无法对现有变量进行模式匹配,在原始代码中,
tgtKey
tgtVal
将是新绑定,与将被隐藏的现有绑定无关

因此,改变你的比赛:

    match (ck, cv) with
    | (tgtKey, NestedMap.Value(tgtVal)) -> 
致:

或者只是:

    match (ck, cv) with
    | x when x = (tgtKey, NestedMap.Value(tgtVal)) -> 

是的,谢谢。我忘记了在模式上使用卫士:“请注意,由于模式中不能使用文字以外的值,如果必须将输入的某些部分与值进行比较,则必须使用when子句。”是的,谢谢。我忘记了在模式上使用卫士:“请注意,由于模式中不能使用文字以外的值,如果必须将输入的某些部分与值进行比较,则必须使用when子句。”是的,谢谢。我忘记了在模式上使用卫士:“请注意,由于模式中不能使用文字以外的值,如果必须将输入的某些部分与值进行比较,则必须使用when子句。”是的,谢谢。我忘记了在模式上使用卫士:“请注意,由于不能在模式中使用文字以外的值,如果必须将输入的某些部分与值进行比较,则必须使用when子句。”