Lyricdev
GitHub

LYR-SEM0126

an interface usable only as a constraint used as a value type

error · spec 05-interfaces

An interface that cannot be a value type — it has a static member, a static 'let', an associated type, a generic member, or mentions 'Self' beyond the receiver — is used as the type of a value: a binding, a field, a parameter, an optional, an 'is' test.

Explanation

A value of an interface carries a table of the conformer's functions, one slot per member. Some interfaces cannot be served that way: a static member or constant has no receiver to find the table through, an associated type or Self in a parameter differs per conformer, and a generic member is one function per instantiation. Such an interface is a constraint only.

Make the code generic over the interface instead: fn f<T :: [Sized]>(x: T).

Wrong

interface Sized {
    static fn size(): int;
}

struct Byte :: [Sized] {
    v: int,
    static fn size(): int { return 1; }
}

fn main(): void {
    let s: Sized = Byte { v = 0 };
    let _ = s;
}
interface Sized {
    static fn size(): int;
}

struct Byte :: [Sized] {
    v: int,
    static fn size(): int { return 1; }
}

fn sizeOf<T :: [Sized]>(_x: T): int { return T.size(); }

fn main(): void {
    let _ = sizeOf(Byte { v = 0 });
}