Java - 如何获取字符串中所有出现的特定字符并将它们移动到非预定义位置?

Java - How can one take all occurrences of a specific character in a string and shift them to a non-predefined position?

我想将字符串中的"cube root of"和"square root of"分别替换为“^(1/3)”和“^(1/2)”,但在操作数之后。

进行简单的替换会将“^(1/3)”和“^(1/2)”放在数字之前,但我需要它们在数字之后(我正在使用 ExpressionBuilder API 来自 exp4j,它需要这个)。

例如,给定这个字符串:

"cube root of 27 times cube root of 64 plus square root of 9 minus square root of 4"

我希望将其转换为:

"27^(1/3)*64^(1/3)+9^(1/2)-4^(1/2)"

这是我的尝试:

String equation = "cube root of 27 times square root of 45";
String r1 = equation.replaceAll("cube root of", "◊").replaceAll("square root of", "√")
        .replaceAll("times", "*").replaceAll("plus", "+").replaceAll("minus", "-")
        .replaceAll("divided by", "/").replaceAll(" ", "");

System.out.println(r1);
String r2 = null;
if (r1.contains("◊"))
{
    for (int i = r1.indexOf("◊")+1; i < r1.length(); i++)
    {
        if(Character.isDigit(r1.charAt(i)))
        {

        }
        else
        {
            System.out.println("i: " + i);
            r2 = r1.substring(r1.indexOf("◊")+1, i) + "^(1/3)" + r1.substring(i);
            break;
        }
    }
}
System.out.println(r2);

我已经为 "cube root of" 替换了一个临时字符“◊”(写出整个短语很乏味),我已经让它为我工作,我得到的输出是:

◊27*√45
i: 3
27^(1/3)*√45

所以它只适用于一个 "cube root of" 短语,而不是两个,并且无法使用 "square root of" 短语(它不在代码中,但我尝试在第一个代码中合并它if() 块,我在其中查看字符串是否包含“◊”符号。

我尝试在那个 if() 块中使用 OR r1.contains("√") 运算符,但它把我现有的代码搞砸了。我在网上到处寻找解决方案。我在我的程序中尝试过诸如 replaceCharAt(String s, int position, char c) 之类的方法来替换指定位置的字符,但我无法让它处理所有出现的指定短语。

我花了数周时间寻找解决方案,但找不到可以替换两个短语进行数学运算的解决方案。

非常感谢此处发布的任何帮助。

你好,这是一个简单的实现。首先,您可以累积与您拥有的正则表达式字符串匹配的所有值。您有以下正则表达式。

RegEx 类型 "cube" 或 "square" 后跟 "root of" 后跟数字。现在您已经构建了 RegEx,您可以使用

    String mydata = "some string with 'the data i want' inside";
Pattern pattern = Pattern.compile("'(.*?)'");
Matcher matcher = pattern.matcher(mydata);
if (matcher.find())
{
    System.out.println(matcher.group(0));
}

这将为您提取数字的值。一旦你这样做了,你需要用你想要的替换完整的正则表达式。

可能有更好的实现方式。这是我第一个想到的。基本上,在尝试替换任何内容之前,您需要更多地使用正则表达式。并将其视为一个完整的正则表达式,而不是试图将其划分为更小的元素。

假设您想将 "cube root of 123" 转换为“123^(1/3)”等(您的问题不清楚),捕获操作数并使用反向引用:

equation = equation.replaceAll("cube root of (\S+)", "^(1/3)")
                   .replaceAll("square root of (\S+)", "^(1/2)")
                   .replace("times", "*").replace("plus", "+").replace("minus", "-")
                   .replace("divided by", "/").replace(" ", "");

请注意,对于非正则表达式的替换,纯文本 replace() 就足够了(并且是首选)- 它仍然会替换所有出现的地方,但不使用正则表达式。


一些测试代码:

String equation = "cube root of 8 times square root of 4 plus cube root of 27 minus 3";
equation = equation.replaceAll("cube root of (\S+)", "^(1/3)")
                   .replaceAll("square root of (\S+)", "^(1/2)")
                   .replace("times", "*").replace("plus", "+").replace("minus", "-")
                   .replace("divided by", "/").replace(" ", "");
System.out.println(equation);

输出:

8^(1/3)*4^(1/2)+27^(1/3)-3