#!/usr/bin/a68g --script #
# -*- coding: utf-8 -*- #
MODE GEN = VOID; # hint/flag generator contructs #
MODE YIELDINT = PROC(INT)GEN;
MODE GENINT = PROC(YIELDINT)GEN;
PROC is perfect square = (INT n)BOOL:
ENTIER (sqrt(n)+0.5) ** 2 = n; # Round to nearest integer #
PROC gen int = (YIELDINT yield)GEN:
FOR i DO yield(i) OD;
PROC gen square = (GENINT gen, YIELDINT yield)GEN:
gen((INT value)VOID: yield(value*value));
PROC gen sum = (GENINT gen, YIELDINT yield)GEN:
BEGIN
INT sum := 0;
gen((INT value)VOID: yield(sum +:= value))
END;
PROC gen perfect square = (GENINT gen, YIELDINT yield)GEN:
BEGIN
gen((INT value)VOID:
IF is perfect square(value) AND value NE 1 THEN
yield(value) # Yield the perfect square sum #
FI
)
END;
PROC head = (GENINT gen)INT:
BEGIN
INT return;
gen((INT i)VOID: ( return := i; GOTO done ));
done: return
END;
MODE PIPEINT = PROC(GENINT, YIELDINT)GEN;
MODE SINKINT = PROC(GENINT)INT;
OP AND = (GENINT source, PIPEINT pipe)GENINT: pipe(source,##);
OP AND = (GENINT source, SINKINT sink)INT: sink(source);
BEGIN
# INT result := head(gen perfect square(gen sum(gen square(gen int,##),##),##)); #
INT result := gen int AND gen square AND gen sum AND gen perfect square AND head;
printf(($"This sum is a perfect square: "gl$, result))
END
No comments:
Post a Comment