3

私たちは皆、何かが特定のタイプである場合のパターンマッチングに慣れています。

match x with
| Y(x) :: tail -> ... // assumes List.head(x) is of type Y(x)

しかし、何かが特定のタイプではない場合、どうすればケースを一致させることができますか?例えば、

match x with
| Not Y(_) :: tail -> ... // List.head(x) is definitely not a Y

ありがとう!

4

2 に答える 2

4

これに対処する通常の方法は、最初に、不要なケースを明示的に除外する句を作成することだと思います。次に、残りのすべてのケースを処理するために使用できます_(除外するケースのコードを記述する必要がありますが、パターンマッチングを完了するには、とにかくそれを記述する必要があります)。

match x with
| Y _ :: tail -> ()
| _ :: tail -> // List.head(x) is definitely not a Y

これは間違いなく回避策のように感じますが、それがあなたにできる最善のことだと思います。複数のケースを除外したい場合は、次のように書くことができます。

match x with
| (Y _ | (Z (1 | 2 | 3 | 4)) :: tail -> ()
| _ :: tail -> // Excludes all "Y x" and "Z n when n \in 1,2,3,4"

とにかく、これは非常に興味深い質問です。パターンの言語を、否定を表現するための特別なパターンで拡張できるかどうか疑問に思っています...興味深いことに、これはアクティブなパターンを使用して直接記述できるものではありません。

于 2011-02-22T15:03:10.457 に答える
4

直接のサポートはありませんが、部分的にアクティブなパターンNotを使用できます。

type Color = | Red | Green | Blue

let (|NotRed|_|) = function
    | Red -> None
    | color -> Some color

let rec print = function
    | (NotRed head) :: tail -> 
        printfn "%A is Not Red" head
        print tail
    | _ :: tail -> print tail
    | _ -> ()

print [Red; Green; Blue]

出力

Green is Not Red
Blue is Not Red
于 2011-02-22T17:12:20.957 に答える