E4053#
无效的 "self" 类型:必须是类型构造器。
当你试图为一个不是类型构造器的类型定义方法或实现 trait 时,会出现这个错误。
属于类型构造器的类型:
元组:
(Int, Bool)
enum
s,struct
s,trait
s, new types (type
), and error types (type!
).
不属于类型构造器的类型:
函数类型:
(Int) -> Bool
类型参数:如
fn f[T](x : T) -> T
中的T
错误示例#
为非类型构造器的类型定义方法。
fn f[T](self : T) -> Int { // Error: Invalid type for "self": must be a type constructor. ignore(self) 0 } fn g(self : (Int) -> Unit) -> Unit { // Error: Invalid type for "self": must be a type constructor. self(0) }
为非类型构造器的类型实现方法。
pub trait A { f(Self) -> Int } // Without constraints impl[X] A for X with f(self : X) -> Int { // Error: Invalid type for "self": must be a type constructor. ignore(self) 0 } // With constraints impl[X: Default] A for X with f(self : X) -> Int { // Error: Invalid type for "self": must be a type constructor. ignore(self) 0 }
建议#
当你希望为一个非类型构造器的类型定义方法时,可以使用新类型将其包装起来。
pub(all) type Wrap[T] T
fn f[T](self : Wrap[T]) -> Int {
ignore(self)
0
}
fn g(self : Wrap[(Int) -> Unit]) -> Unit {
(self._)(0)
}
impl[X] A for Wrap[X] with f(self : Wrap[X]) -> Int {
ignore(self)
0
}
但这样一来,每次调用方法时你都需要用 Wrap
来包装该值。
如果你需要为类型参数实现特征(trait),也可以考虑使用特征(trait)的默认实现。
impl A with f(self : Self) -> Int {
ignore(self)
0
}
如果你希望只为满足特定约束的类型提供实现,可以将这些约束添加到特征(trait)的定义中。
trait A: Default {
f(Self) -> Int
}
impl A with f(self : Self) -> Int {
ignore(self)
0
}