fsharp icon indicating copy to clipboard operation
fsharp copied to clipboard

Unable to write SRTP constraints for method

Open nikonthethird opened this issue 7 years ago • 5 comments

When writing the same inline method using statically resolved type parameters two times, first without specifying any type parameters and letting the compiler figure everything out, then by explicitly stating the type parameters and constraints, I can only get the first approach to work.

Repro steps

Place the following type into VS or VS Code.

type Summer () =

    member inline _this.SumBy (items, selector) =
        Seq.fold (fun acc item ->
            acc + selector item
        ) LanguagePrimitives.GenericZero items

    member inline _this.SumBy'<'T, ^U, ^V
                                when (^V or ^U) : (static member (+) : ^V * ^U -> ^V)
                                and ^V : (static member Zero : ^V)
                              > (items : 'T seq, selector : 'T -> ^U) : ^V =
        Seq.fold (fun acc item ->
            acc + selector item
        ) LanguagePrimitives.GenericZero items

The acc in the line acc + selector item of SumBy' will be underlined.

Expected behavior

Both SumBy and SumBy' should work.

Actual behavior

SumBy' shows the following:

sumby

Known workarounds

Letting the compiler figure everything out. I hope I didn't miss anything obvious...

Or you can do what's described in this comment.

Related information

  • Windows 10
  • .NET 4.7
  • VS 15.8.3 as well as VS Code 1.27.1 with Ionide 3.25.4

nikonthethird avatar Sep 11 '18 12:09 nikonthethird

Related to #392 and likely a bug, @dsyme do you agree?

cartermp avatar Sep 11 '18 16:09 cartermp

Another example for the same effect:

let inline plus< ^T1, ^T2, ^T3 when (^T1 or ^T2) : (static member (+) : ^T1 * ^T2 -> ^T3)> (x: ^T1) (y: ^T2) : ^T3 =
    x + y

TIHan avatar Sep 11 '18 18:09 TIHan

@TIHan interesting, your example is reported as an error in both VS & VS Code, while my example is reported only as a warning, and will run.

error_warning

nikonthethird avatar Sep 11 '18 19:09 nikonthethird

While digging around a bit more, I just noticed this comment in the F# source code: This helps the somewhat complicated type inference for AverageByNullable and SumByNullable, by making both type in a '+' the same.

And indeed, when I use this, the error in @TIHan 's example is gone (after editing the constraint as suggested by the compiler):

let inline plus' (x:'T) (y:'T) = Checked.(+) x y

let inline plus< ^T1, ^T2 when ^T1 : (static member (+) : ^T1 * ^T1 -> ^T2)> (x: ^T1) (y: ^T1) : ^T2 =
    plus' x y

nikonthethird avatar Sep 11 '18 19:09 nikonthethird

I do agree that being explicit should be ok in these cases. So I consider this a bug

dsyme avatar Sep 19 '18 13:09 dsyme