This rule will never be matched: Why?

Viewed 106

I have the following function:

let hasColumnValue<'columnType> columnName (value: 'columnType) (row: KeyValuePair<int, ObjectSeries<string>>) =
    let columnValue =
        Series.get columnName row.Value :?> 'columnType

    match columnValue with
    | value -> true
    | _ -> false

The default pattern matching is flagged as "This rule will never be matched"

=> I don't understand why

Thanks in advance

2 Answers

The reason is that you can't pattern match on values, so the first case acts as a catch-all. I would suggest replacing the entire match expression with columnValue = value.

First pattern always matches because it's binding to variable. If variable with same name exists, it gets shadowed. But, if name refers to literal binding, then pattern succeeds if value equals to underlying constant value

let x = 1
[<Literal>] 
let Three = 3

match 2 with
| Three -> printfn "Three"
| x -> printfn "%d" x 
// prints 2

match 3 with
| Three -> printfn "Three"
| x -> printfn "%d" x 
// prints Three

In your case it will be most clear to use equality instead of pattern matching

 let hasColumnValue<'columnType when 'columnType: equality> columnName (value: 'columnType) (row: KeyValuePair<int, ObjectSeries<string>>) =
    let columnValue =
        Series.get columnName row.Value :?> 'columnType

    columnValue = value
Related