| 1 | = Inline function = |
| 2 | |
| 3 | The inline function refactoring step substitutes the selected application with the corresponding function body and executes compensations. The function may consist of one or more function clauses and may have guard expression(s), inline can handle these cases. In the example the {{{sort/1}}} application is inlined. The application is replaced with a case expression. |
| 4 | |
| 5 | {{{ |
| 6 | -module(in). |
| 7 | |
| 8 | -export([sort/2]). |
| 9 | |
| 10 | sort(A, B) -> |
| 11 | sort({A, B}). |
| 12 | |
| 13 | sort({A, B}) when A > B -> |
| 14 | {A, B}; |
| 15 | sort({A, B}) -> |
| 16 | {B, A}. |
| 17 | }}} |
| 18 | |
| 19 | {{{sort/1}}} inlined: |
| 20 | |
| 21 | {{{ |
| 22 | -module(in). |
| 23 | |
| 24 | -export([sort/2]). |
| 25 | |
| 26 | sort(A, B) -> |
| 27 | case {A, B} of |
| 28 | {A, B} when A > B -> |
| 29 | {A, B}; |
| 30 | {A, B} -> |
| 31 | {B, A} |
| 32 | end. |
| 33 | |
| 34 | sort({A, B}) when A > B -> |
| 35 | {A, B}; |
| 36 | sort({A, B}) -> {B, A}. |
| 37 | }}} |
| 38 | |
| 39 | == Side conditions == |
| 40 | |
| 41 | * Applying the inline function must not cause variable name conflicts. A variable name conflict arises when the same variable name is used in the body of the function clause and in the scope of the selected function application, except the variables which are bound in the formal parameters where the structure of the formal and the actual parameters are equivalent. |
| 42 | |
| 43 | * If the function is defined in other module: |
| 44 | * the function do not contain local (not exported) function applications in its body. |
| 45 | * macro name conflicts must not occur in the current module, that is, macro names used in the functions must refer to the same macro definition in the current and in the definition module. This applies to macros used in these macros too. |
| 46 | * record name conflicts must not occur in the current module, that is, record names used in the functions must refer to the same record definition in the current and in the definition module. |
| 47 | |
| 48 | * If the user does not specify a function application or the specified function does not exist, the transformation starts an interaction to ask the user to specify one. The user has to select a function from a radio group. |
| 49 | |
| 50 | |
| 51 | == Transformation steps and compensations == |
| 52 | |
| 53 | 1. Find the corresponding function definition and copy the function clause(s) and create (if it is needed) a corresponding structure from the expressions of the body(ies), the guard expressions (if there is any) and from the patterns of the function clause(s). |
| 54 | |
| 55 | 2. Where the actual and formal parameters are structurally equivalent, create variable name pairs and rename the corresponding variables in the copied body. |
| 56 | |
| 57 | 3. Where the formal and structural parameters are not equivalent, create a match expression from these parameters. The left hand side is a tuple from the formal parameters, and the right hand side is a tuple from the actual parameters. |
| 58 | |
| 59 | 4. If the function consists of |
| 60 | * one clause and does not have guard expression and the body of the function contains only one expression and match expressions should not be created from the parameters, replace the application with this single expression. |
| 61 | * one clause and does not have guard expression and the body of the function contains more than one expression and the parent expression of the selected application is a clause, replace the application with the sequence of the expressions from the body of the function clause extended with the created match expression. |
| 62 | * one clause and does not have guard expression and the body of the function contains more than one expression and the selected application is a subexpression: |
| 63 | * create a begin-end block from the sequence of the expressions from the body of the function clause extended with the created match expression |
| 64 | * replace the application with this begin-end block. |
| 65 | * more than one clause, or it has guard expressions (or both) or variables appear multiple times with the same name in a pattern list: |
| 66 | * create a case expression from the function clause body(ies) expression(s), guard and pattern expressions. |
| 67 | * replace the application with this case expression. |
| 68 | |
| 69 | 5. If the definition of the function is in another module |
| 70 | * qualify the applications in the copied body which call exported functions from the defining module. |
| 71 | * qualify the applications in the copied body which call imported functions. |
| 72 | * copy or import record and macro definitions to the current module which are used in the copied body(ies). |