问题 Seq seq类型作为F#中的成员参数


为什么这段代码不起作用?

type Test() =
  static member func (a: seq<'a seq>) = 5.

let a = [[4.]]
Test.func(a)

它给出以下错误:

The type 'float list list' is not compatible with the type 'seq<seq<'a>>'

2934
2017-07-29 10:24


起源



答案:


将您的代码更改为

type Test() = 
  static member func (a: seq<#seq<'a>>) = 5. 

let a = [[4.]] 
Test.func(a) 

诀窍在于a的类型。您需要明确允许外部seq保存seq <'a>的实例  seq <'a>的子类型。使用#符号启用此功能。


8
2017-07-29 11:31





错误消息描述了问题 - 在F#中, list<list<'a>> 与...不兼容 seq<seq<'a>>

upcast 通过制作,功能有助于解决这个问题 a 变成一个 list<seq<float>>,然后兼容 seq<seq<float>>

let a = [upcast [4.]]
Test.func(a)

编辑: 你(们)能做到 func 它接受的类型更灵活。原文只接受序列 seq<'a>。即使 list<'a> 器物 seq<'a>,类型不相同,编译器给你一个错误。

但是,您可以修改 func 接受任何类型的序列,只要该类型实现 seq<'a>,将内部类型写为 #seq

type Test() =
  static member func (a: seq<#seq<'a>>) = 5.

let a = [[4.]]
Test.func(a) // works

5
2017-07-29 10:29



为什么会这样呢?如果你写“let func(a:seq <'a seq>)= 5”。然后它没有任何向上转换。 - Oldrich Svec
我犯了同样的错误 - gist.github.com/497844 - Tim Robinson
我的错。你是对的。你对'let func(a:float seq)= 5'有什么解释吗?我们不必进行向上转换,对于seq seq,我们必须这样做吗? - Oldrich Svec
seq<'a> 和 seq<'b> 在F#中基本上是不同的类型,即使你(作为程序员)知道任何类型 'b 并转换为 'a。你必须手动进行代码转换;在这种情况下,与 upcast。但看到我编辑的答案...... - Tim Robinson
非常感谢你的帮助。现在我更了解它了。 - Oldrich Svec


答案:


将您的代码更改为

type Test() = 
  static member func (a: seq<#seq<'a>>) = 5. 

let a = [[4.]] 
Test.func(a) 

诀窍在于a的类型。您需要明确允许外部seq保存seq <'a>的实例  seq <'a>的子类型。使用#符号启用此功能。


8
2017-07-29 11:31





错误消息描述了问题 - 在F#中, list<list<'a>> 与...不兼容 seq<seq<'a>>

upcast 通过制作,功能有助于解决这个问题 a 变成一个 list<seq<float>>,然后兼容 seq<seq<float>>

let a = [upcast [4.]]
Test.func(a)

编辑: 你(们)能做到 func 它接受的类型更灵活。原文只接受序列 seq<'a>。即使 list<'a> 器物 seq<'a>,类型不相同,编译器给你一个错误。

但是,您可以修改 func 接受任何类型的序列,只要该类型实现 seq<'a>,将内部类型写为 #seq

type Test() =
  static member func (a: seq<#seq<'a>>) = 5.

let a = [[4.]]
Test.func(a) // works

5
2017-07-29 10:29



为什么会这样呢?如果你写“let func(a:seq <'a seq>)= 5”。然后它没有任何向上转换。 - Oldrich Svec
我犯了同样的错误 - gist.github.com/497844 - Tim Robinson
我的错。你是对的。你对'let func(a:float seq)= 5'有什么解释吗?我们不必进行向上转换,对于seq seq,我们必须这样做吗? - Oldrich Svec
seq<'a> 和 seq<'b> 在F#中基本上是不同的类型,即使你(作为程序员)知道任何类型 'b 并转换为 'a。你必须手动进行代码转换;在这种情况下,与 upcast。但看到我编辑的答案...... - Tim Robinson
非常感谢你的帮助。现在我更了解它了。 - Oldrich Svec