当前位置:  开发笔记 > 编程语言 > 正文

在组合泛型和非泛型类时,键入变量转义范围

如何解决《在组合泛型和非泛型类时,键入变量转义范围》经验,为你挑选了1个好方法。

我在F#中有一个带有单个类型参数的泛型类,并且想要创建一个包含工厂方法的静态类.当我编写类时,F#编译器会生成与"转换其范围的类型变量"相关的错误.我的问题是为什么错误存在以及如何解决它.

我创建了一个最小尺寸代码段来演示此问题:

type Foo<'a>(element : 'a) =

    member this.Copy () = Bar.Create(element)

and Bar =

    static member Create(element : 'a) = new Foo<'a>(element)

类型中的相互递归是因为我希望类型Foo<'a>能够在静态类中调用工厂方法.上面的代码片段没有编译,错误是:"类型推断导致类型变量a逃避其范围.考虑添加显式类型参数声明或调整代码以减少通用." 错误被注册为位于类的Create方法中Bar.不幸的是,我并不是真的了解这个问题,也不知道如何解决它.有任何想法吗?

这是另外一个观察.片段

type Foo<'a>(element : 'a) =

    member this.Element = element

and Bar =

    static member Create(element : 'a) = new Foo<'a>(element)

编译.所以问题似乎与基于类Copy()方法的类型推断有关Foo<'a>.此外,该片段

type Foo<'a>(element : 'a) =

    member this.Copy () = Bar.Create(element)

and Bar =

    static member Create<'a>(element) = new Foo<'a>(element)

是一个更像C#的代码版本(其中静态方法明确地是通用的),它也没有编译,错误"这段代码不够通用.类型变量'a不能一概而论,因为它会逃避其范围."



1> kvb..:

递归成员的类型推断通常需要至少对某些定义进行类型注释.但是,有时您可以通过重新排序定义来避免这种情况,至少可以在简化的复制中使用:

type Bar = 
    static member Create(element) = Foo(element)
and Foo<'a>(element:'a) =
    member this.Copy() = Bar.Create(element)

(请注意,我甚至取消了对注释elementBar.Create).

不幸的是,我不知道在任何特定情况下都会有一个易于理解的解释.

推荐阅读
臭小子
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有