对象表达式,接口实现,详细语法

时间:2015-03-17 23:30:23

标签: visual-studio-2013 f#

我经常使用详细语法来创建通常为几行的单行表达式。通常我这样做,所以我可以使用Alt+'将整个表达式发送到F#interactive。例如,我可能会这样做:

let longLength list = let rec helper result = function [] -> result | _ :: t -> helper (result + 1L) t in helper 0L list

对于示例代码,假设已打开这些名称空间:

open System
open System.Collections
open System.Collections.Generic

我想将此对象表达式转换为单行:

let emptyEnumerator = {
    new IEnumerator<int> with member t.Current = raise(InvalidOperationException())
    interface IEnumerator with
        member t.MoveNext() = false
        member t.Reset() = ()
        member t.Current = raise(InvalidOperationException())
    interface IDisposable with member t.Dispose() = ()
    }

我发现我只能使用详细语法来完成它。通常,详细语法代码也会在轻量级语法下编译,但在这里,它不会。我也尝试使用相同的实现创建一个命名类,并且几乎相同的代码在轻量级和详细语法下编译:

open System
open System.Collections
open System.Collections.Generic

#light "off"
type A() = class interface IEnumerator<int> with member t.Current = raise(InvalidOperationException()) end interface IEnumerator with member t.MoveNext() = false member t.Reset() = () member t.Current = raise(InvalidOperationException()) end interface IDisposable with member t.Dispose() = () end end
let b = { new IEnumerator<int> with member t.Current = raise(InvalidOperationException()) end interface IEnumerator with member t.MoveNext() = false member t.Reset() = () member t.Current = raise(InvalidOperationException()) end interface IDisposable with member t.Dispose() = () end end }

#light "on"
type C() = class interface IEnumerator<int> with member t.Current = raise(InvalidOperationException()) end interface IEnumerator with member t.MoveNext() = false member t.Reset() = () member t.Current = raise(InvalidOperationException()) end interface IDisposable with member t.Dispose() = () end end
let d = { new IEnumerator<int> with member t.Current = raise(InvalidOperationException()) end interface IEnumerator with member t.MoveNext() = false member t.Reset() = () member t.Current = raise(InvalidOperationException()) end interface IDisposable with member t.Dispose() = () end end }

两个类定义都成功,但最后一行失败,带有“~vsB756.fsx(29,150):错误FS0010:表达式中的意外关键字'member'。在此点或其他标记之前或之前的预期不完整结构化构造。”

问题似乎出现在一系列成员定义中。 Visual Studio突出显示定义member部分中的第二个和第三个IEnumerator关键字,作为FS0010错误的原因。 (换句话说,突出显示的member关键字是引入IEnumerator.Reset()IEnumerator.Current定义的关键字。)

Visual Studio还会在end实现之前的开放式大括号(不匹配的“{”)和IDisposable关键字上报告“let”(不完整的值或函数定义)上的错误,但是我怀疑这是因为它未能识别IEnumerator实现中的三个成员,这导致它尝试解析其他成员作为第一个成员定义的一部分。

我是否忽略了语法中的某些内容?这是编译器中的错误吗?

0 个答案:

没有答案