【问题标题】:Repeated replacement of characters in String重复替换字符串中的字符
【发布时间】:2014-02-14 10:05:22
【问题描述】:

我正在尝试创建一个 Android 应用程序,它将普通的十六进制代码转换为在 smali 中使用的反转代码。除了当我在 String 上使用 replace 或 replaceAll 方法时,一切都运行良好,它甚至替换了已经替换的字符

例如,

String stringInvert = string.replace("F", "0")
    .replace("E" , "1")
    .replace("D" , "2")
    .replace("C" , "3")
    .replace("B" , "4")
    .replace("A" , "5")
    .replace("9" , "6")
    .replace("8" , "7")
    .replace("7" , "8")
    .replace("6" , "9")
    .replace("5" , "A")
    .replace("4" , "B")
    .replace("3" , "C") 
    .replace("2" , "D")
    .replace("1" , "E")
    .replace("0" , "F"); 

如你所见,第一个F变成了0,其他的字母也同样改变了,但是后面的0变成了F,这也把已经改变的F变回了F。所以,总而言之,只有7 之前的字母/数字被反转(因为它们在代码中被替换),其他的由于双重反转而保持不变。我什至尝试了 replaceAll 方法,它给出了相同的结果。那么有没有其他方法或解决这个问题的方法?

完整代码在这里 - http://pastebin.com/dB23JmQG

对不起,如果代码很难看,我是在 AIDE 中完成的

谢谢

【问题讨论】:

    标签: java android string


    【解决方案1】:

    您可以创建一个Map<Character, Character> 来保存您的映射。

    然后只需迭代其他原始String

    Map<Character, Character> m = new HashMap<>();
    m.put('F','0');
    ....
    
    StringBuilder sb = new StringBuilder();
    for(char c : originalString.toCharArray()){
       sb.append(map.get(Character.toUpperCase(c)));
    } 
    String finalString = sb.toString();
    

    【讨论】:

      【解决方案2】:

      您可以尝试用这样的多个步骤替换:

      String stringInvert = string
      .replace("F", "null")
      .replace("E" , "one")
      .replace("D" , "two")
      .replace("C" , "three")
      .replace("B" , "four")
      .replace("A" , "five")
      .replace("9" , "six")
      .replace("8" , "seven")
      .replace("7" , "8")
      .replace("6" , "9")
      .replace("5" , "A")
      .replace("4" , "B")
      .replace("3" , "C") 
      .replace("2" , "D")
      .replace("1" , "E")
      .replace("0" , "F")
      .replace("null", "0")
      .replace("one","1")
      .replace("two","2" )
      .replace("three","3" )
      .replace("four","4" )
      .replace("five","5" )
      .replace("six","6" )
      .replace("seven","7" );
      

      不漂亮也不聪明,但简单有效:)

      【讨论】:

      • 谢谢。完美运行,它简短而简单,不需要在现有代码中修改much :)
      【解决方案3】:

      您可以通过在覆盖其位置之前将十六进制数字替换为临时字符来解决此问题。

      这类似于冒泡排序算法。 例如,让我们使用以下字符串: FF00F0

      1. 首先将 F 变成某个字符。 '*' 例如。 字符串现在是 **00*0
      2. 把0变成F 字符串现在是:**FF*F
      3. 最后把 * 变成 0。

      有很多更有效的解决方案,但这个解决方案简单快捷。

      【讨论】:

        【解决方案4】:

        这不适用于字符到其他字符的随机映射,但由于您的有一个模式,您可以创建一个函数,使用它们的 char/int 值转换每个字符,例如:

        static char convert(char c){
            int n = c;
            n = n - 70; // Adjust for capital F
            n = n * -1; // So earlier letters become larger numbers
            n += 48; // Adjust back to zero
            return (char)n;
        }
        

        此方法将获取任何字母字符并返回等效的数字字符(并且数字字符的等效函数应该清楚),因此只需循环转换每个字符即可。

        如果您关心速度,这应该很快,尤其是如果您可以使用 char 数组而不是字符串。

        【讨论】:

          【解决方案5】:

          另一种解决方案是使用Integer API:

          String stringToInvert = "A1F56C";
          
          StringBuilder sb = new StringBuilder();
          for (char c : stringToInvert.toCharArray()) {
              sb.append(Integer.toHexString(15 - Integer.valueOf(c + "", 16)));
          }
          
          System.out.println(sb.toString().toUpperCase());
          

          输出:

          5E0A93

          【讨论】:

            猜你喜欢
            • 2011-10-10
            • 2021-06-17
            • 2012-10-05
            • 2014-11-05
            • 2022-01-07
            • 2020-12-19
            • 2014-08-23
            相关资源
            最近更新 更多