Why this fires¶
A function's generic parameter list uses the same name both as a type parameter (e.g. in the return type, -> e) and as a row-variable tail in a with clause ({Fs | e}). Zolo's row-polymorphic effects let a function be generic over "whatever other effects the caller's own function needs" — but a single name can't mean both "a type" and "a set of extra effects" at once.
effect Fs { fn read(p: str) -> str }
fn collision<e>(f: fn() with {Fs | e} -> e) with {| e} -> e {
// ^ error[TE811]: generic parameter `e` is bound as both a type
// variable and a row variable; rename one
return f()
}Here e is used as the return type (-> e) AND as the row-variable tail ({Fs | e}) — ambiguous.
Fix it¶
Give the type parameter and the row variable different names:
fn collision<T, e>(f: fn() with {Fs | e} -> T) with {| e} -> T {
return f()
}See also¶
- /docs/algebraic-effects — row-polymorphic effects (
with {E | r}).