Рефакторинг в Eclipse / Java: примените «Метод извлечения» (Alt + Shift + M) впоследствии

1

Я хочу знать, можно ли заменить какой-либо код вызовом метода, извлеченного ранее.

Например, у меня есть класс с похожими шаблонами:

public class ExtractMethodDemo {
    public void doSequence() {
        long n1; n2;
        // Compute and print count
        n1 = 70;
        n2 = compute(n1);                                        // <-- 1st
        System.out.printf("Input %4s, output = %s.%n", n1, n2);  // <-- occurrence
        ....
        // Compute and print count again
        n2 = n2 % 100;
        n1 = compute(n2);                                        // <-- Nth
        System.out.printf("Input %4s, output = %s.%n", n2, n1);  // <-- occurrence
    }
}

Я рефакторинг использую метод, но по какой-то причине некоторые вхождения по-прежнему не рефакторируются (возможно, если Replace additional occurrences... не отмечены, или если один и тот же код вставлен позже):

public void doSequence() {
    long n1; n2;
    // Compute and print count
    n1 = 70;
    n2 = doAll(n1);                                          // <--- method extracted
    // ....
    // Compute and print count again
    n2 = n2 % 100;
    n1 = compute(n2);                                        // <--- oops! this one is
    System.out.printf("Input %4s, output = %s.%n", n2, n1);  // <--- still old style
}

private long doAll(long n) {
    long n2; // (BTW: not the n2 declared in doSequence!)
    n2 = compute(n);
    System.out.printf("Input %4s, output = %s.%n", n, n2);
    return n2;
}

Возможно ли повторное преобразование последовательностей повторной обработки:

public void doSequence() {
    long n1; n2;
    // Compute and print count
    n1 = 70;
    n2 = doAll(n1);
    // ....
    // Compute and print count again
    n2 = n2 % 100;
    n1 = doAll(n2);    // <--- would be great to apply same refactoring afterwards
}
  • 0
    В крайнем случае, я мог бы заново встроить весь код и снова извлечь метод, но это не элегантно ...
Теги:
refactoring

1 ответ

1
Лучший ответ

Может быть, крошечный бит лучше, чем повторная инкрустация кода, - это Извлечь метод на весь корпус нового кода, с проверкой Replace Additional Occurrences, а затем встроить новый метод из исходного вызова. Таким образом, вы рискуете выбрать неправильные линии для извлечения.

Обновление: Вот пример:

Вы начинаете с

extractableCode(1);
extractableCode(2);
extractableCode(3);

и извлеките исходный блок, оставив вас с

extractedMethod(1);
extractableCode(2);
extractableCode(3);
...
function extractedMethod(int i) {
    extractableCode(i);
}

Ваш путь будет заключаться в inline extractMethod, затем повторите извлечение с помощью Replace All Occurrences. Я предлагаю вместо этого извлечь изнутри extractedMethod():

extractedMethod(1);
secondExtractedMethod(2);
secondExtractedMethod(3);
...
function extractedMethod(int i) {
    secondExtractedMethod(i);
}
function secondExtractedMethod(int i) {
    extractableCode(i);
}

Затем введите свой первоначальный вызов первому извлеченному методу:

secondExtractedMethod(1);
secondExtractedMethod(2);
secondExtractedMethod(3);
...
function secondExtractedMethod(int i) {
    extractableCode(i);
}

И затем, возможно, переименуйте второй извлеченный метод. Это только немного отличается от того, что вы изначально предлагаете, но оно может быть немного более надежным.

  • 0
    Благодарю. Простите, я не понимаю последовательность действий, в частности, что такое «все тело нового кода». В моем примере ... 1. Я выбираю две забытые строки (N-е вхождение) 2. Извлечение в новый метод (например, doAll2). 3.?
  • 0
    Я добавил пример; надеюсь, теперь стало понятнее.
Показать ещё 1 комментарий

Ещё вопросы

Сообщество Overcoder
Наверх
Меню