# OVERLOAD, TEMPLATE and OPERATOR extensions Part of the [pitfalls index](../PITFALLS.md). ## OVERLOAD - OVERLOAD is reserved and prefixes FUNCTION/PROCEDURE (after PUBLIC/PRIVATE for methods). Every same-name definition must opt in. - Count, canonical parameter types, array rank and (for non-VOID definitions) return type distinguish signatures; a PROCEDURE counts as VOID. BYREF/BYVAL and array bounds do not. - Calls prefer exact static types, then marked IMPLICIT construction and the existing CHAR/STRING bridge for scalar BYVAL parameters; ordinary functions retain their existing numeric coercions. A known expected result type (assignment, BYVAL argument, RETURN, condition, subscript, CASE comparison) must match the overload's return type exactly; `(T) x` only prefers T and otherwise converts. Without a context, return-only-distinct candidates need one DEFAULT return or remain ambiguous. DEFAULT never resolves competing parameter signatures. - Each name and canonical parameter signature permits only one DEFAULT return, including across invisible units; different parameter signatures may each have their own. Only non-VOID OVERLOAD functions accept RETURNS DEFAULT. - Call visibility filters the set, but duplicate signatures (parameters and return type) conflict across all inputs. MAIN and builtins cannot be overloaded. - NEW supports overloads; DECLARE, fields and arrays needing default construction require a matching no-argument NEW. - Private access is checked after selection, never used to select a public fallback. ## TEMPLATE - Top-level FUNCTION/PROCEDURE/CLASS only; all template parameters are types, with at most one final pack. - Substituted BYVAL parameters allow marked constructors and CHAR/STRING bridges, but numeric widening still fails (`Max(1, 2.5)` fails). Deduction recognizes T and array element T, never the T inside Box. - When multiple ordinary/template functions share a name, every definition must specify OVERLOAD; exact ordinary definitions win, then non-variadic templates, then variadic templates, with same-tier ties ambiguous. An expected result type filters ordinary definitions but not templates. Explicit arguments select templates only. - Packs are final non-array parameters and expand only in call/constructor argument lists; pack fields are rejected, including in variadic classes. - Unsupported: non-type parameters, SIZEOF..., member/operator templates, specialization, bare injected class name, pointer-alias templates, DEFAULT returns (including methods in class templates). Pointer-linked generic containers remain unsupported; use fixed fields or other supported value layouts. - Class instances follow ordinary constructor rules, so a parameterized NEW alone does not permit `DECLARE B : Box` without arguments. - Template instances share the first requester's visibility for their cached body; positional constants come from the template declaration. Instantiation depth is limited to 64. - Lexing: empty source lists `<>` are invalid and lex as inequality; `>>` remains two tokens, but adjacent `<-` and `>=` merge. Expression lookahead treats `A < B, C > (D)` as a template call; parenthesize comparisons to avoid that ambiguity. ## OPERATOR - Unary/binary operators require OVERLOAD FUNCTION, with supported arity and at least one record/class/enum operand. Pointer aliases alone do not qualify. - Exact-first matching considers visible globals and left-class members together, with marked BYVAL construction after directly supported builtins. The result type joins the match when the context supplies one; ties are errors, including private/public ties. Without a context, return-only-distinct candidates need a unique DEFAULT return or remain ambiguous; defaults do not resolve global/member ties, and casts only prefer their target type. - Comparison and logic result types are declared, not assumed BOOLEAN; a strict BOOLEAN context requires an overload returning BOOLEAN. CASE comparisons must return BOOLEAN. AND/OR overloads evaluate both operands. - Temporary member receivers are destroyed at statement end, including exception exits; ordinary DECLARE objects remain function-scoped. - Explicit calls use OPERATOR+(a,b) or a.OPERATOR+(b). - Assignment uses member-only OVERLOAD PROCEDURE OPERATOR<- with one explicit parameter; it is selected before fallback same-class copying. Keyword NEW retains its allocation/rebinding path.