Version 1 (modified by manualwiki, 13 years ago) (diff) |
---|
Extract function
A function definition might contain an expression or a sequence of expressions which can be considered as a logical unit, hence a function definition can be created from it. The extracted function is lifted to the module level, and it is parameterized with the free variables of the original expressions: those variables which are bound outside of the expressions, but the value of which is used by the expressions.
Extracting the new function two_sol:
-module(quadratic). -export([f/0]). solve(A,B,C) -> D := B * B - 4 * A * C, if D == 0 -> {-B / 2 / A}; D > 0 -> S = math:sqrt(D), {-(B+S)/2/A, -(B-S)/2/A}. D < 0 -> no_solution end.
Result:
-module(quadratic). -export([f/0]). solve(A,B,C) -> D := B * B - 4 * A * C, if D == 0 -> {-B / 2 / A}; D > 0 -> two_sol(A, B, D); D < 0 -> no_solution end. two_sol(A, B, D) -> Sqrt = math:sqrt(D), {-(B+S)/2/A, -(B-S)/2/A}.
Side conditions
- The name of the new function should not conflict with another function, either defined in the same module, or imported from another module (overloading). Furthermore, the name should be a legal function name.
- If one of the above conditions fails, the transformation starts an interaction to ask for a new function name.
- The starting and ending positions should delimit a sequence of expressions.
- Variables with possible binding occurrences in the selected sequence of expressions should not appear outside of the sequence of expressions.
- The extracted sequence of expressions cannot be part of a guard sequence.
- The extracted sequence of expressions cannot be part of a pattern.
- The extracted sequence of expressions cannot be part of macro definition.
Transformation steps and compensations
- Collect all variables that the selected sequence of expressions depends on.
- Collect variables from the selected variables in step 1, which has binding occurrence out of the selected part of the module.
- Add a new function definition to the current module with a single alternative. The name of the function is an argument to the refactoring. The formal parameter list consists of the variables selected in step 2.
- Replace the selected sequence of expressions with a function call expression, where the name of the function is given as an argument to the refactoring, and the actual parameter list consists of the variables selected in step 2.
- The order of the variables must be the same in steps 3 and 4.
- If the selected expression is a block-expression, eliminate the begin-end keywords from the expression in the body of the created new function.