SoftMemes
SoftMemes

Reputation: 5702

In F#, return true if expression matches pattern?

I am looking for a shorter/neater way of doing the equivalent of the following (for any pattern known at compile time):

let f x = match x with | ['A'::_] -> true ; | _ -> false

is there a way of doing this in general, i.e. return true iff an expression matches a given pattern?

Upvotes: 6

Views: 1251

Answers (3)

kaefer
kaefer

Reputation: 5741

You may be thinking of an Active Pattern here, specifically its single-case form. It would allow you to create a pattern which returns a boolean value:

let (|F|) = function 
    | ['A'::_] -> true
    | _ -> false

let (F x) = [['A']] // val x : bool = true

The Active Pattern can be parameterized. Of the (n + 1) arguments it accepts, the first n get passed to the syntactic function, and the last argument is the value matched.

let (|G|) e = function
    | [d::_] when d = e -> true
    | _ -> false

let (G 'A' y) = [['A']] // val y : bool = true

Upvotes: 4

Søren Debois
Søren Debois

Reputation: 5688

In f#, patterns are not values themselves, and there is no mechanism for converting them to values(*). So, no, there is no neater way.

That said, you may have other options depending on why you're interested in checking whether a pattern matches. Caring about whether a pattern matches but not about which values were matched seems a bit unusual to me, so maybe there's an opportunity for refactoring.

As a simple example, suppose you're doing this:

let t = match e with <pattern> -> true | _ -> false 
...
if t then
    (* Do something. *)
else 
    (* Do something else. *)
...

In that case, you could consider instead doing this:

...
match e with 
  <pattern> -> (* Do something. *)
| _         -> (* Do something else. *)
...

(Supposing the test happens only once, of course.)

(*) Ignoring reflection and quotations.

Upvotes: 4

Lee
Lee

Reputation: 144136

You could shorten it slightly using function:

let f = function ['A'::_] -> true | _ -> false

Upvotes: 10

Related Questions