拆分计算器的输入字符串

时间:2012-01-09 17:42:59

标签: java string split expression

我正在尝试将用户给出的输入分成我的计算器。 例如, 如果用户输入“23 + 45 *(1 + 1)”,我希望将其拆分为[23,+,45,*,(,1,+,1,)]。

3 个答案:

答案 0 :(得分:7)

您所寻找的是词法分析器词法分析器将输入拆分为您可以阅读的块(称为令牌)。

幸运的是,你的词法分析器很简单,可以手工编写。对于更复杂的词法分析器,您可以使用flex(如“快速词法分析器” - 而非Adobe Flex),或(因为您使用的是Java)ANTLR(注意,ANTLR更多而不只是一个词法分析员。)

只需提供一个正则表达式列表,每个令牌匹配一个(请注意,由于您的输入非常简单,您可以取消此列表并将它们全部合并到一个正则表达式中。但是,更多信息高级词法分析器,它有助于为每个标记执行一个正则表达式)例如

\d+
\+
-
*
/
\(
\)

然后启动循环:当有更多要解析的字符时,请遍历每个正则表达式并尝试将它们与字符串的开头匹配。如果匹配,请将第一个匹配的组添加到输入列表中。否则,继续匹配(如果它们都不匹配,告诉用户他们有语法错误)。

伪代码:

List<String>input = new LinkedList<String>();
while(userInputString.length()>0){
    for (final Pattern p : myRegexes){
        final Matcher m = p.matcher(userInputString);
        if(m.find()) {
            input.add(m.group());
            //Remove the token we found from the user's input string so that we
            //can match the rest of the string against our regular expressions.
            userInputString=userInputString.substring(m.group().length());
            break;
        }
    }
}

实施说明:

  • 您可能希望将^字符添加到所有正则表达式中。这样可以确保将匹配项锚定在字符串的开头。我的伪代码假设你已经这样做了。

答案 1 :(得分:1)

我认为使用 stacks 来拆分操作数和运算符并评估表达式会更合适。在计算器中,我们通常使用中缀符号来定义算术表达式。

Operand1 op Operand2

检查许多此类情况中使用的Shunting-yard algorithm以解析数学表达式。 This也是一本很好的读物。

答案 2 :(得分:0)

这可能有点草率,因为我还在学习,但它确实将它们分成了字符串。

公共类TestClass {

public static void main(String[] args)
{
    Scanner sc = new Scanner(System.in);
    ArrayList<String> separatedInput = new ArrayList<String>();
    String input = "";

    System.out.print("Values: ");
    input = sc.next();

    if (input.length() != 0)
    {
        boolean numberValue = true;
        String numbers = "";

        for (int i = 0; i < input.length(); i++)
        {
            char ch = input.charAt(i);
            String value = input.substring(i, i+1);

            if (Character.isDigit(ch))
            { numberValue = true; numbers = numbers + value; }

            if (!numberValue)
            { separatedInput.add(numbers); separatedInput.add(value); numbers = ""; }
            numberValue = false;

            if (i == input.length() - 1)
            {
                if (Character.isDigit(ch))
                { separatedInput.add(numbers); }
            }
        }

    }
    System.out.println(separatedInput);
 }

}