【问题标题】:Swap two letters in a string交换字符串中的两个字母
【发布时间】:2014-10-11 16:18:07
【问题描述】:

我想交换一个字符串中的两个字母。例如,如果输入是WH,则字符串中所有出现的W 都应替换为H,所有出现的H 应替换为W。字符串WelloHorld 将变为HelloWorld

我知道如何替换单个字符:

str = str.replace('W', 'H');

但我不知道如何交换字符。

【问题讨论】:

    标签: java regex string


    【解决方案1】:
    public String getSwappedString(String s)
    {
    char ac[] = s.toCharArray();
    for(int i = 0; i < s.length(); i++)
    {
       if(ac[i] == 'H')
         ac[i]='W';
       else if(ac[i] == 'W')
         ac[i] = 'H'; 
    }
    
    s = new String(ac);
    return s;
    }
    

    【讨论】:

      【解决方案2】:

      Java8 真的很简单

      static String swap(String str, String one, String two){
          return Arrays.stream(str.split(one, -1))
              .map(s -> s.replaceAll(two, one))
              .collect(Collectors.joining(two));
      }
      

      使用示例:

      public static void main (String[] args){
          System.out.println(swap("???", "?", "?"));
      }
      

      我敦促您不要将 Character 用于交换功能,因为它会破坏包含 BMP 之外的字母的字符串

      如果你想扩展它以使用任意字符串(不仅仅是字母),你可以引用提供的字符串:

      static String swap(String str, String one, String two){
          String patternOne = Pattern.quote(one);
          String patternTwo = Pattern.quote(two);
          return Arrays.stream(str.split(patternOne, -1))
              .map(s -> s.replaceAll(patternTwo, one))
              .collect(Collectors.joining(two));
      }
      

      【讨论】:

      • 尝试在hello[world] 中交换[] 时抛出PatternSyntaxException
      • 自从问到关于拆分字母的问题,我没有费心让它与其他字符一起使用......您可以检查Java作为字母保存的代码点:Character.isLetter('[')false,而Character.isLetter(Character.toCodePoint("?".charAt(0), "?".charAt(1)))true...无论如何这可以很容易地解决
      【解决方案3】:

      您可能需要三个替换调用才能完成此操作。

      第一个将其中一个字符更改为中间值,第二个进行第一次替换,第三个将中间值替换为第二次替换。

      String str = "Hello World";
      
      str = star.replace("H", "*").replace("W", "H").replace("*", "W");
      

      编辑

      针对以下有关在String 中交换字符的这种方法的正确性的一些担忧。即使String 中已经存在*,这也将起作用。但是,这需要在返回新的String 之前首先转义任何出现的* 并取消转义这些额外步骤。

      public static String replaceCharsStar(String org, char swapA, char swapB) {
          return org
                  .replace("*", "\\*")
                  .replace(swapA, '*')
                  .replace(swapB, swapA)
                  .replaceAll("(?<!\\\\)\\*", "" + swapB)
                  .replace("\\*", "*");
      
      }
      

      编辑 2

      阅读其他一些答案后,一个新版本不仅适用于 Java 8,还可以替换需要在正则表达式中转义的字符,例如[] 并考虑到使用 char 原语来操作 String 对象的担忧。

      public static String swap(String org, String swapA, String swapB) {
          String swapAEscaped = swapA.replaceAll("([\\[\\]\\\\+*?(){}^$])", "\\\\$1");
          StringBuilder builder = new StringBuilder(org.length());
      
          String[] split = org.split(swapAEscaped);
      
          for (int i = 0; i < split.length; i++) {
              builder.append(split[i].replace(swapB, swapA));
              if (i != (split.length - 1)) {
                  builder.append(swapB);
              }
          }
      
          return builder.toString();
      
      }
      

      【讨论】:

      • 如果字符串已经包含 '*' 怎么办?然后修改不需要的字符。
      • 在这种情况下,您必须使用替代的中间字符。如果这将在生产代码中使用,最好选择一些晦涩的东西,我可能应该添加它作为警告。
      • 如果我们保证某些字符没有被使用,那么我们可以从中选择一个。否则最好循环遍历字符并根据条件修改它们。
      • 当然你可以检查这些字符的存在。关键是这是循环遍历String 的替代方法。更喜欢哪一个将取决于使用它的情况。在这个简单的Hello World 案例中,这并不重要。但话又说回来,循环 char 数组对于单个字符可能编码为多个 chars 的语言并不理想。
      • @TheLostMind,我理解您的担忧,发布此答案的原因并不是表明它比已经存在的数组答案更好,而只是提供使用 replace 函数的替代方法提到捷豹。
      【解决方案4】:

      字符串扫描方法的稍微好一点的版本,没有显式的数组和索引访问:

      StringBuilder sb = new StringBuilder();
      for (char c : source_string.toCharArray()) {
        if (c == 'H') sb.append("W");
        else if (c == 'W') sb.append("H");
        else sb.append(c);
      }
      return sb.toString();
      

      【讨论】:

        【解决方案5】:

        您可以遍历字符串的字符数组,并在看到任一字符时交换:

        private static String swap(String str, char one, char two) {
            char[] chars = str.toCharArray();
            for (int i = 0; i < chars.length; i++) {
                if (chars[i] == one) {
                    chars[i] = two;
                } else if (chars[i] == two) {
                    chars[i] = one;
                }
            }
            return String.valueOf(chars);
        }
        

        【讨论】:

          【解决方案6】:

          你也可以试试这个代码。

          System.out.println("WelloHorld".replaceAll("W", "H~").replaceAll("H(?!~)", "W").replaceAll("(?<=H)~", ""));
          

          输出:

          HelloWorld
          

          使用输入字符串中不存在的任何字符代替~

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2023-03-23
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2015-12-21
            • 1970-01-01
            相关资源
            最近更新 更多