如何在String Java中找到并替换3个或更多个字符的3个或更多字符?

时间:2022-12-27 19:21:33

I need to check if the line contains strings that must be eliminated and indicate which symbols would be eliminated.
A character sequence is replaced by underscores (""), accordingly with the sequence length, if there are three or more contiguous characters with the same symbol. for example, the line ", _, @, @, @, @, $, $, , #, #,!" would be transformed into ", _, _, _, _, _, _, $, $, _, #, #,!" After the process of elimination.
I need to do this only with String or StringBuilder, Regex, ect... (Only Basic coding of Java).
Can't use arrays also. Thanks in advance.
This is what i tried:

我需要检查该行是否包含必须删除的字符串,并指出哪些符号将被删除。如果有三个或更多具有相同符号的连续字符,则字符序列将被下划线(“”)替换,因此将与序列长度替换。例如,行“,_,@,@,@,@,$,$ ,,#,#,!”将被转换为“,_,_,_,_,_,_,$,$,_,#,#,!”消除过程之后。我只需要使用String或StringBuilder,Regex等等(仅限Java的基本编码)。也不能使用数组。提前致谢。这是我试过的:

public static void main(String[] args) {    
    String linha = "##,$$$$,%%%%,@%@@@,!!!!", validos = "$#%!@";        
        for (int i = 0; i < validos.length(); i++) {
            linha = linha.replaceAll("\\" + validos.charAt(i) + "{3,}", "_");
        }
        System.out.println (linha);
    }
}

The problem here is that replaces a sequence with just one "_", and i don't know which chars are replaced.

这里的问题是只用一个“_”替换序列,我不知道哪些字符被替换。

4 个解决方案

#1


0  

Surely you can do this in many ways, and probably this is a good exercise to do by yourself. Here you have a basic implementation using just basic loop structures and nothing fancy like StringUtils libraries... Note that your previous loop implementation would have missed several occurrences of the same character repeated in different locations of linha.

当然,你可以通过多种方式做到这一点,这可能是你自己做的一个很好的练习。在这里你有一个基本的实现,只使用基本的循环结构,没有像StringUtils库这样的花哨......注意你之前的循环实现会错过在linha的不同位置重复出现的同一个字符的几次出现。

static int index(String lookInStr, char lookUpChr) {
    return lookInStr.indexOf(new String(new char[] { lookUpChr, lookUpChr, lookUpChr }));
}

public static void main(String[] args) {
    String linha = "####,@@@@@@@@,$$$$,%%%%,@%@@@,!!!!", validos = "$#%!@";
    for (int i = 0; i < validos.length(); i++) {
        char currentSearchChar = validos.charAt(i);
        do {
            int index = index(linha, currentSearchChar);
            if (index >= 0) {
                int count = -1;
                do {
                    count++;
                } while (linha.charAt(count + index) == currentSearchChar && count + index < linha.length() - 1);
                String replacementSeq = "";
                for (int j = 0; j < count; j++) {
                    replacementSeq += "-";
                }
                linha = linha.replaceAll("\\" + validos.charAt(i) + "{" + count + ",}", replacementSeq);
            }
        } while (index(linha, currentSearchChar) >= 0);
    }
    System.out.println(linha);
}

#2


0  

If you are trying to replace three characters at once, and you want three underscores instead, you are just missing this:

如果您尝试一次替换三个字符,而您想要三个下划线,那么您只是错过了这个:

linha = linha.replaceAll("\\" + validos.charAt(i) + "{3,}", "___");

If you want them separated by commas:

如果你想用逗号分隔它们:

linha = linha.replaceAll("\\" + validos.charAt(i) + "{3,}", "_,_,_");

#3


0  

Basically, this splits the string into separate blocks, then checks the length of the blocks and either returns the original block, or replaces it with underscores.

基本上,这会将字符串拆分为单独的块,然后检查块的长度并返回原始块,或用下划线替换它。

static String convert(String s) {
    StringBuilder sb = new StringBuilder();

    for(int i = 0; i < s.length(); i++) {
        char c = s.charAt(i);
        StringBuilder tempSb = new StringBuilder();

        for(; i < s.length(); i++) {
            char d = s.charAt(i);

            if(d != c) {
                i--;
                break;
            } else {
                tempSb.append(d);
            }
        }

        String t = tempSb.toString();
        if(t.length() < 3) {
            sb.append(t);
        } else {
            sb.append(repeat("_", t.length()));
        }
    }

    return sb.toString();
}

public static void main(String[] args) {
    String x = convert("##,$$$$,%%%%,@%@@@,!!!!");
    System.out.println(x); // ##,____,____,@%___,____
}

And here's the simple repeat method:

这是简单的重复方法:

static String repeat(String s, int repeatCount) {
    StringBuilder sb = new StringBuilder();

    for(int i = 0; i < repeatCount; i++) {
        sb.append(s);
    }

    return sb.toString();
}

#4


0  

Haven't really implemented this, but this is something you may look at:

没有真正实现这一点,但这是你可能会看到的:

In Matcher, there is find(int start), start() and end()

在Matcher中,有find(int start),start()和end()

Have a pattern for the '3-or-more-repetitive char' (you may refer to the comment in your question).

有一个'3或更多重复字符'的模式(你可以参考你的问题中的评论)。

psuedo code is something like this:

psuedo代码是这样的:

int lastEndingPosition = 0;
StringBuilder sb;

while (matcher can find next group) {
  // add the unmatched part
  sb.append( substring of input string from lastEndingPosition to matcher.start() ); 

  // add the matched part
  sb.append( "-" for matcher.end() - matcher.start() times);
  lastEndingPosition = matcher.end();
}
sb.append( substring of input string from lastEndingPosition to the end);

Probably there are some more elegant way to do this. This is just one alternative

可能有更优雅的方式来做到这一点。这只是一种选择

#1


0  

Surely you can do this in many ways, and probably this is a good exercise to do by yourself. Here you have a basic implementation using just basic loop structures and nothing fancy like StringUtils libraries... Note that your previous loop implementation would have missed several occurrences of the same character repeated in different locations of linha.

当然,你可以通过多种方式做到这一点,这可能是你自己做的一个很好的练习。在这里你有一个基本的实现,只使用基本的循环结构,没有像StringUtils库这样的花哨......注意你之前的循环实现会错过在linha的不同位置重复出现的同一个字符的几次出现。

static int index(String lookInStr, char lookUpChr) {
    return lookInStr.indexOf(new String(new char[] { lookUpChr, lookUpChr, lookUpChr }));
}

public static void main(String[] args) {
    String linha = "####,@@@@@@@@,$$$$,%%%%,@%@@@,!!!!", validos = "$#%!@";
    for (int i = 0; i < validos.length(); i++) {
        char currentSearchChar = validos.charAt(i);
        do {
            int index = index(linha, currentSearchChar);
            if (index >= 0) {
                int count = -1;
                do {
                    count++;
                } while (linha.charAt(count + index) == currentSearchChar && count + index < linha.length() - 1);
                String replacementSeq = "";
                for (int j = 0; j < count; j++) {
                    replacementSeq += "-";
                }
                linha = linha.replaceAll("\\" + validos.charAt(i) + "{" + count + ",}", replacementSeq);
            }
        } while (index(linha, currentSearchChar) >= 0);
    }
    System.out.println(linha);
}

#2


0  

If you are trying to replace three characters at once, and you want three underscores instead, you are just missing this:

如果您尝试一次替换三个字符,而您想要三个下划线,那么您只是错过了这个:

linha = linha.replaceAll("\\" + validos.charAt(i) + "{3,}", "___");

If you want them separated by commas:

如果你想用逗号分隔它们:

linha = linha.replaceAll("\\" + validos.charAt(i) + "{3,}", "_,_,_");

#3


0  

Basically, this splits the string into separate blocks, then checks the length of the blocks and either returns the original block, or replaces it with underscores.

基本上,这会将字符串拆分为单独的块,然后检查块的长度并返回原始块,或用下划线替换它。

static String convert(String s) {
    StringBuilder sb = new StringBuilder();

    for(int i = 0; i < s.length(); i++) {
        char c = s.charAt(i);
        StringBuilder tempSb = new StringBuilder();

        for(; i < s.length(); i++) {
            char d = s.charAt(i);

            if(d != c) {
                i--;
                break;
            } else {
                tempSb.append(d);
            }
        }

        String t = tempSb.toString();
        if(t.length() < 3) {
            sb.append(t);
        } else {
            sb.append(repeat("_", t.length()));
        }
    }

    return sb.toString();
}

public static void main(String[] args) {
    String x = convert("##,$$$$,%%%%,@%@@@,!!!!");
    System.out.println(x); // ##,____,____,@%___,____
}

And here's the simple repeat method:

这是简单的重复方法:

static String repeat(String s, int repeatCount) {
    StringBuilder sb = new StringBuilder();

    for(int i = 0; i < repeatCount; i++) {
        sb.append(s);
    }

    return sb.toString();
}

#4


0  

Haven't really implemented this, but this is something you may look at:

没有真正实现这一点,但这是你可能会看到的:

In Matcher, there is find(int start), start() and end()

在Matcher中,有find(int start),start()和end()

Have a pattern for the '3-or-more-repetitive char' (you may refer to the comment in your question).

有一个'3或更多重复字符'的模式(你可以参考你的问题中的评论)。

psuedo code is something like this:

psuedo代码是这样的:

int lastEndingPosition = 0;
StringBuilder sb;

while (matcher can find next group) {
  // add the unmatched part
  sb.append( substring of input string from lastEndingPosition to matcher.start() ); 

  // add the matched part
  sb.append( "-" for matcher.end() - matcher.start() times);
  lastEndingPosition = matcher.end();
}
sb.append( substring of input string from lastEndingPosition to the end);

Probably there are some more elegant way to do this. This is just one alternative

可能有更优雅的方式来做到这一点。这只是一种选择