How do I implement an abstract function with multiple implementations?
← Function Extension · Ref: Q589
An abstract function can have any number of concrete implementations. Each implementation uses 'is' to extend the abstract and must match the signature exactly.
MULTIPLE IMPLEMENTATIONS
Define the abstract once, implement many times:
MathOp as pure abstract -> a as Float, b as Float <- result as Float?
AddOp is MathOp as pure -> a as Float, b as Float <- result as Float: a + b
SubOp is MathOp as pure -> a as Float, b as Float <- result as Float: a - b
STRATEGY PATTERN
Store implementations in variables typed as the abstract function:
currentOp as MathOp: AddOp result <- currentOp(10.0, 5.0)
Swap implementations at runtime without classes.
LIST OF FUNCTIONS
Collect implementations for iteration:
ops <- [AddOp, SubOp, MulOp] for op in ops stdout.println(op(10.0, 5.0))
See Q588 for function extension basics. See Q51 for abstract functions. See Q214 for strategy pattern. See Q590 for dynamic function implementations.
Example
defines module qa.function.abstractimpl defines function //Abstract function: math operation contract MathOp as pure abstract -> operandA as Float operandB as Float <- result as Float? AddOp is MathOp as pure -> operandA as Float operandB as Float <- result as Float: operandA + operandB SubtractOp is MathOp as pure -> operandA as Float operandB as Float <- result as Float: operandA - operandB MultiplyOp is MathOp as pure -> operandA as Float operandB as Float <- result as Float: operandA * operandB defines program AbstractFunctionImplDemo() stdout <- Stdout() //Direct calls stdout.println(`Add: ${AddOp(10.0, 3.0)}`) stdout.println(`Sub: ${SubtractOp(10.0, 3.0)}`) stdout.println(`Mul: ${MultiplyOp(10.0, 3.0)}`) //Strategy pattern: swap at runtime currentOp as MathOp: AddOp stdout.println(`Current (add): ${currentOp(5.0, 2.0)}`) currentOp: MultiplyOp stdout.println(`Current (mul): ${currentOp(5.0, 2.0)}`) //List of operations operations <- List() of MathOp operations += AddOp operations += SubtractOp operations += MultiplyOp for operation in operations stdout.println(`Result: ${operation(8.0, 4.0)}`)
Common mistakes
E50001 — A pure function cannot call non-pure methods like stdout.println(). Pure functions must be side-effect free. See ek9 -h E50001 for details.
Incorrect:
AddOp is MathOp as pure -> operandA as Float operandB as Float <- result as Float: operandA + operandB stdout.println(result)
Correct:
AddOp is MathOp as pure -> operandA as Float operandB as Float <- result as Float: operandA + operandB
Other ways to ask this
- How do I create multiple function implementations?
- Can I have several functions extending the same abstract?
- How do I use abstract functions for strategy pattern?
Coming from another language?
Java: strategy pattern requires interface + multiple classes. Python: pass different functions directly (no type checking). Rust: closures with Box<dyn Fn>. Kotlin: functional types + lambda. EK9: abstract function + multiple 'is' implementations, true function polymorphism.
Keywords: swap, handler, visitor, polymorphism, list, extend, multiple, function, abstract, implementation, strategy, sealed