Как это сделать в Regex - изменения базы кода - PullRequest
3 голосов
/ 24 июля 2011

У меня есть полная база кода на Java, члены которой названы:

String m_sFoo;
Array m_arrKeepThings;

Имена переменных / объектов включают как префикс m_ для обозначения члена, так и индикатор типа нотации в венгерском языке.

Я ищу способ выполнить однократную замену временного кода на (например, в описанных выше случаях):

Array keepThings;
String foo;

Конечно, есть много других альтернатив, но я надеюсь, что на основе двух примеров я смогу выполнить полное изменение. Спектакли не проблема, так как это одноразовое исправление.

Чтобы уточнить, если бы мне пришлось объяснить это в строках, это было бы:

  1. Совпадение слов, начинающихся с m_ [a-zA-Z].
  2. После m_ отбросьте все, что есть, до первой заглавной буквы.
  3. Измените первую заглавную букву на строчную .

Ответы [ 3 ]

1 голос
/ 24 июля 2011

Проверьте это сообщение: Regex, чтобы изменить на случай предложения

Как правило, я боюсь, что вы не можете изменить регистр букв с помощью регулярных выражений. Я бы порекомендовал вам реализовать простую утилиту (используя любой язык, который вы хотите). Вы можете сделать это в Java. Просто пройдите по дереву файлов, найдите шаблон типа m_[sidc]([A-Z]), возьмите захваченную последовательность, вызовите toLowerCase () и выполните замену.

Другим решением является поиск и замена m_sA, затем m_sB, ... m_sZ с использованием eclipse. Итого: 26 раз. Это немного глупо, но, вероятно, в любом случае быстрее, чем реализация и отладка собственного кода.

1 голос
/ 24 июля 2011

Если вы действительно уверены, что предлагаемое изменение не приведет к конфликтам (переменные, которые отличаются только префиксом), я бы сделал это с помощью строки perl:

perl -pi.bak -e "s/\bm_[a-z_]+([A-Z]\w*)\b/this.\u$1/g;" *.java

Это выполнит встроенное редактирование ваших исходных кодов Java, сохраняя при этом резервную копию с расширением .bak, заменяющую ваш шаблон между границами слов (\b) с использованием первой буквы замены (\u) несколько раз в строке .

Затем можно выполнить различие между файлами резервных копий и файлами результатов, чтобы проверить, все ли прошло хорошо.

0 голосов
/ 24 июля 2011

Вот некоторый Java-код, который работает. Это не просто регулярное выражение, но основано на:

Использование:

String str = "String m_sFoo;\n"
        + "Array m_arrKeepThings;\n"
        + "List<? extends Reader> m_lstReaders; // A silly comment\n"
        + "String.format(\"Hello World!\"); /* No m_named vars here */";
// Read the file you want to handle instead

NameMatcher nm = new NameMatcher(str);
System.out.println(nm.performReplacements());

NameMatcher.java

package so_6806699;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 *
 * @author martijn
 */
public class NameMatcher
{

    private String input;
    public static final String REGEX = "m_[a-z]+([A-Z0-9_\\$\\µ\\£]*)";
    public static final Pattern PATTERN = Pattern.compile(REGEX);

    public NameMatcher(String input)
    {
        this.input = input;
    }

    public String performReplacements()
    {
        Matcher m = PATTERN.matcher(input);
        StringBuilder sb = new StringBuilder();

        int oldEnd = 0;
        while (m.find())
        {
            int start = m.start();
            int end = m.end();

            String match = input.substring(start, end);
            String matchGroup1 = match.replaceAll(REGEX, "$1");
            if (!matchGroup1.isEmpty())
            {
                char[] match_array = matchGroup1.toCharArray();
                match_array[0] = Character.toLowerCase(match_array[0]);
                match = new String(match_array);
            }

            sb.append(input.substring(oldEnd, start));
            oldEnd = end;

            sb.append(match);
        }
        sb.append(input.substring(oldEnd));
        return sb.toString();
    }
}

Демонстрационный вывод :

String foo;
Array keepThings;
List<? extends Reader> readers; // A silly comment
String.format("Hello World!"); /* No m_named vars here */

Редактировать 0 : Поскольку знаки доллара ($), микро (µ) и фунт (£) являются допустимыми символами для переменных имени Java, я отредактировал регулярное выражение.

Редактировать 1: Кажется, что допустимо много нелатинских символов (éùàçè и т. Д.). Надеюсь, вам не придется обращаться с ними.

Редактировать 2: Я всего лишь человек! Так что знайте об ошибках, которые могут быть в коде! Сначала сделайте РЕЗЕРВНОЕ КОПИРОВАНИЕ!

Редактировать 3: Код улучшен. NPE был брошен, когда код содержит это: m_foo. Они будут обработаны.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...