Joe*_*ler 36
正如Robert Jeppeson指出的那样,C#中的"静态类"只是创建一个无法实例化或继承的类,并且只有静态成员.以下是您在F#中完全实现的方法:
[<AbstractClass; Sealed>]
type MyStaticClass private () =
static member SomeStaticMethod(a, b, c) =
(a + b + c)
static member SomeStaticMethod(a, b, c, d) =
(a + b + c + d)
Run Code Online (Sandbox Code Playgroud)
这可能有点过分,因为AbstractClass
私有构造函数都会阻止你创建类的实例,但是,这就是C#静态类所做的 - 它们被编译为带有私有构造函数的抽象类.该Sealed
属性阻止您继承此类.
如果您像在C#中那样添加实例方法,这种技术不会导致编译器错误,但从调用者的角度来看,没有区别.
F# 中没有定义静态类型的工具。
第一种选择是定义一个模块,但它缺乏重载函数的能力(这就是您所追求的)。第二种选择是声明具有静态成员的普通类型。
关于第二种方法,这正是您的老问题所接受的答案所描述的。我重构了代码以使其更容易解释。首先,定义一个虚拟的单例判别联合:
type Overloads = Overloads
Run Code Online (Sandbox Code Playgroud)
其次,您利用静态成员可以重载的事实:
type Overloads with
static member ($) (Overloads, m1: #IMeasurable) = fun (m2: #IMeasurable) -> m1.Measure + m2.Measure
static member ($) (Overloads, m1: int) = fun (m2: #IMeasurable) -> m1 + m2.Measure
Run Code Online (Sandbox Code Playgroud)
inline
第三,使用关键字将这些重载方法的约束传播到 let-bounds :
let inline ( |+| ) m1 m2 = (Overloads $ m1) m2
Run Code Online (Sandbox Code Playgroud)
当您能够使用此方法重载 let-bounds 时,您应该创建一个包装器模块来保存这些函数并标记您的类型private
。
我不确定是否有静态类之类的东西。我相信,C# 类级别上的“静态”是在 2.0 中引入的,主要是为了方便(避免私有构造函数和编译时检查不存在实例成员)。您无法检查类型并得出它是静态的结论:http : //msdn.microsoft.com/en-us/library/system.reflection.typeinfo.aspx
更新:MSDN 声明静态类是一个密封类并且只有静态成员:http : //msdn.microsoft.com/en-us/library/79b3xss3(v=vs.80).aspx
所以,你现在正在做的就是做这件事的方法。
《 F#组件设计指南》对此进行了解释。
[<AbstractClass; Sealed>]
type Demo =
static member World = "World"
static member Hello() = Demo.Hello(Demo.World)
static member Hello(name: string) = sprintf "Hello %s!" name
let s1 = Demo.Hello()
let s2 = Demo.Hello("F#")
Run Code Online (Sandbox Code Playgroud)
仍然可以定义实例方法,但是当没有构造函数可用时,您无法实例化该类。
归档时间: |
|
查看次数: |
5327 次 |
最近记录: |