Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Return types in shadowing members are not considered in generic constraint resolution to avoid ambiguity. #8794

Open
natalie-o-perret opened this issue Mar 25, 2020 · 4 comments
Labels
Area-Compiler-SRTP bugs in SRTP inference, resolution, witness passing, code gen Bug Impact-Low (Internal MS Team use only) Describes an issue with limited impact on existing code.
Milestone

Comments

@natalie-o-perret
Copy link
Contributor

natalie-o-perret commented Mar 25, 2020

Description

It seems that when a member is shadowing an inherited member with a different return type, the return type is not considered to avoid any ambiguity when the compiler is attempting to resolve the member.

Repro steps

Self-explanatory example:

type Mother() =
    member this.Hello() =
        Unchecked.defaultof<int32>

type Daughter() =
    inherit Mother()
    member this.Hello() =
        Unchecked.defaultof<string>

type SomeoneHolder<'Someone when 'Someone: (member Hello : unit -> string)> =
    { Someone: 'Someone }

let someoneHolder =
    { Someone = Daughter() }

Expected behavior

It should compile.

Actual behavior

It does not, with the error below:

[FS0001] A unique overload for method 'Hello' could not be determined based on type information prior to this program point.
A type annotation may be needed. Candidates: member Daughter.Hello : unit -> string, member Mother.Hello : unit -> int32

Known workarounds

None.

Related information

Provide any related information (optional):

The return type

  • Operating system: Windows 10 Enterprise
  • .NET Runtime kind (.NET Core, .NET Framework, Mono): .NET Core 3.1
  • Editing Tools (e.g. Visual Studio Version, Visual Studio): Rider
@NinoFloris
Copy link
Contributor

What was interesting to me wasn't so much that return types aren't considered (this is the default for both C# and F#) but that overload resolution takes shadowed members into account here.

@natalie-o-perret natalie-o-perret changed the title Return types in shadowing members are not considered for the generic constraint resolution. Return types in shadowing members are not considered in generic constraint resolution to avoid ambiguity. Mar 25, 2020
@natalie-o-perret
Copy link
Contributor Author

natalie-o-perret commented Mar 25, 2020

@NinoFloris I kinda disagree:

type Daddy() =
    member this.Hello() =
        Unchecked.defaultof<int32>

type SomeoneHolder<'Someone when 'Someone: (member Hello : unit -> string)> =
    { Someone: 'Someone }

let someoneHolder =
    { Someone = Daddy() }

[FS0001] This expression was expected to have type
'string'
but here has type
'int32'

Maybe we're not on the same page.

The return type needs to respect the signature given in the generic constraint.

So... why not the same behavior for a shadowing member?

Also, I don't think it's that surprising that shadowing members are actually processed by the generic constraint resolution process.

=> All in all there is an issue of consistency.

@dsyme
Copy link
Contributor

dsyme commented Sep 3, 2020

It does surprise me that the shadowed member is being taken into accdount.

Since this involves SRTP constraint resolution I will investigate as part of #6805.

@dsyme dsyme added the Impact-Low (Internal MS Team use only) Describes an issue with limited impact on existing code. label Sep 3, 2020
@abelbraaksma
Copy link
Contributor

abelbraaksma commented Nov 2, 2020

We (@kerry-perret and I) discussed this briefly over the weekend and found that the code as written is documented as not being allowed. Mainly, member constraints can only be used with SRTP, and cannot be used on types (i.e., even changing ' to ^ won't allow this code to compile):

image

Still, the error is confusing and it appears as if the compiler actually tries to resolve the member constraint here.

@dsyme dsyme added Area-Compiler-SRTP bugs in SRTP inference, resolution, witness passing, code gen and removed Area-Compiler labels Mar 31, 2022
@vzarytovskii vzarytovskii moved this to Not Planned in F# Compiler and Tooling Jun 17, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area-Compiler-SRTP bugs in SRTP inference, resolution, witness passing, code gen Bug Impact-Low (Internal MS Team use only) Describes an issue with limited impact on existing code.
Projects
Status: New
Development

No branches or pull requests

5 participants