FUNCTION free_variables_of
(expr : generic_expression) : SET [0:?] OF generic_variable;
LOCAL typenames : SET OF STRING := stripped_typeof(expr); result : SET OF generic_variable := []; exprs : LIST OF generic_expression := []; END_LOCAL; IF 'GENERIC_LITERAL' IN typenames THEN RETURN (result); END_IF; IF 'GENERIC_VARIABLE' IN typenames THEN result := result + expr; RETURN (result); END_IF; IF 'QUANTIFIER_EXPRESSION' IN typenames THEN exprs := QUERY (ge <* expr\multiple_arity_generic_expression.operands | NOT (ge IN expr\quantifier_expression.variables)); REPEAT i := 1 TO SIZEOF (exprs); result := result + free_variables_of (exprs[i]); END_REPEAT; REPEAT i := 1 TO SIZEOF (expr\quantifier_expression.variables); result := result - expr\quantifier_expression.variables[i]; END_REPEAT; RETURN (result); END_IF; IF 'UNARY_GENERIC_EXPRESSION' IN typenames THEN RETURN (free_variables_of (expr\unary_generic_expression.operand)); END_IF; IF 'BINARY_GENERIC_EXPRESSION' IN typenames THEN result := free_variables_of (expr\binary_generic_expression.operands[1]); RETURN (result + free_variables_of (expr\binary_generic_expression.operands[2])); END_IF; IF 'MULTIPLE_ARITY_GENERIC_EXPRESSION' IN typenames THEN REPEAT i := 1 TO SIZEOF (expr\multiple_arity_generic_expression.operands); result := result + free_variables_of ( expr\multiple_arity_generic_expression.operands[i]); END_REPEAT; RETURN (result); END_IF; -- IN this CASE the SUBTYPE shall NOT contain any variable (see IP1 in -- generic_expression). RETURN (result); END_FUNCTION; -- free_variables_of
|