Замена нескольких символов в Java другими несколькими символами? - PullRequest
0 голосов
/ 02 мая 2020

Я видел, что на этот вопрос есть несколько похожих вопросов, но ответы там мне не очень помогли. В любом случае, у меня есть строка вроде «Сегодня суббота». Мне нужно изменить каждый символ 'a' на 'b' и каждый символ 'o' на 'f'. В основном, замена нескольких символов на несколько символов. Я попытался сделать что-то вроде этого:

String string.replace("a","b").replace("o","f");

Но это только первая замена. Я пытался использовать Stringbuilder:

stringBuilder.append(string);
for (int i=0; i<stringBuilder.length(); i++){
    char c=stringBuilder.charAt(i);
    if (c=='a'){
        I don't know how to replace it here to 'b'...
    }
}

stringBuilder.toString();

Я читал, что могу использовать карты, но никогда раньше не использовал их и не знаю, как это сделать. Может кто-нибудь помочь мне с этим?

1 Ответ

0 голосов
/ 02 мая 2020

Звучит так, будто вам нужен метод, аналогичный функции SQL TRANSLATE.

public static String translate(String input, String fromChars, String toChars) {
    if (fromChars.isEmpty() || fromChars.length() != toChars.length())
        throw new IllegalArgumentException();
    if (input == null || input.isEmpty())
        return input;
    char[] buf = input.toCharArray();
    for (int i = 0; i < buf.length; i++) {
        char ch = buf[i];
        for (int j = 0; j < fromChars.length(); j++) {
            if (fromChars.charAt(j) == ch) {
                buf[i] = toChars.charAt(j);
                break;
            }
        }
    }
    return new String(buf);
}

Тест

System.out.println(translate("Today is Saturday", "ao", "bf"));

Выход

Tfdby is Sbturdby

Вот версия, использующая Map, которая поддерживает символы Юникода из дополнительных плоскостей, например, Emojis:

public static String translate(String input, String fromChars, String toChars) {
    // Build codepoint mapping table
    if (fromChars.isEmpty() || fromChars.length() < toChars.length()) {
        throw new IllegalArgumentException("fromChars cannot be shorter than toChars (" +
                fromChars.length() + " < " + toChars.length() + ")");
    }
    Map<Integer, String> map = new HashMap<>();
    for (int fromIdx = 0, fromEnd, toIdx = 0; fromIdx < fromChars.length(); fromIdx = fromEnd) {
        fromEnd = fromChars.offsetByCodePoints(fromIdx, 1);
        String mapped = "";
        if (toIdx < toChars.length()) {
            int toEnd = toChars.offsetByCodePoints(toIdx, 1);
            mapped = toChars.substring(toIdx, toEnd);
            toIdx = toEnd;
        }
        if (map.put(fromChars.codePointAt(fromIdx), mapped) != null) {
            throw new IllegalArgumentException("Duplicate value in fromChars at index " + fromIdx + ": " +
                                               fromChars.substring(fromIdx, fromEnd));
        }
    }

    // Map codepoints
    if (input == null || input.isEmpty())
        return input;
    StringBuilder buf = new StringBuilder();
    for (int idx = 0, end; idx < input.length(); idx = end) {
        end = input.offsetByCodePoints(idx, 1);
        String mapped = map.get(input.codePointAt(idx));
        buf.append(mapped != null ? mapped : input.substring(idx, end));
    }
    return buf.toString();
}

Test

System.out.println(translate("Today is Saturday ?", "ao?r", "bf?"));

Выходные данные

Tfdby is Sbtudby ?

Обратите внимание, как удаляется r, поскольку toChars короче fromChars. Вот как работает функция SQL TRANSLATE.

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