在Java中解析字符串有哪些不同的方法?

时间:2008-08-05 23:49:54

标签: java string parsing

对于解析播放器命令,我经常使用split方法通过分隔符拆分字符串,然后通过一系列if s或{{1来计算其余部分}}上课。在Java中解析字符串有哪些不同的方法?

15 个答案:

答案 0 :(得分:19)

我真的很喜欢正则表达式。只要命令字符串相当简单,您就可以编写一些可能需要几页代码来手动解析的正则表达式。

我建议您查看http://www.regular-expressions.info以获取正则表达式的详细介绍,以及Java的具体示例。

答案 1 :(得分:15)

我假设您正在努力使命令界面尽可能宽容。如果是这种情况,我建议您使用类似于此的算法:

  1. 读入字符串
    • 将字符串拆分为标记
    • 使用字典将同义词转换为常用表单
    • 例如,将“hit”,“punch”,“strike”和“kick”全部转换为“hit”
    • 对无序的包容性基础执行操作
    • 无序 - “将猴子打在脸上”与“猴子脸上的脸”是一回事
    • 包容 - 如果该命令应该是“在脸上打猴子”并且它们提供“打孔猴子”,那么你应该检查这匹配的命令数量。如果只有一个命令,请执行此操作。拥有命令优先级甚至可能是个好主意,即使有匹配,它也会执行最佳操作。

答案 2 :(得分:13)

手动解析很有趣......开头:)

实际上,如果命令不是很复杂,您可以像命令行解释器中使用的那样处理它们。您可以使用以下库列表:http://java-source.net/open-source/command-line。我认为您可以从apache commons CLIargs4j开始(使用注释)。它们有很好的文档记录,使用起来非常简单。它们自动处理解析,您唯一需要做的就是读取对象中的特定字段。

如果你有更复杂的命令,那么创建一个正式的语法可能是一个更好的主意。有一个非常好的库,带有用于语法的图形编辑器,调试器和解释器。它被称为ANTLR(和编辑器ANTLRWorks)并且它是免费的:)还有一些示例语法和教程。

答案 3 :(得分:7)

我会查看Java migrationsZork,并倾向于简单Natural Language Processor(通过令牌化或正则表达式驱动),例如以下内容(来自此链接):

    public static boolean simpleNLP( String inputline, String keywords[])
    {
        int i;
        int maxToken = keywords.length;
        int to,from;
        if( inputline.length() = inputline.length()) return false; // check for blank and empty lines
        while( to >=0 )
        {
            to = inputline.indexOf(' ',from);
            if( to > 0){
                lexed.addElement(inputline.substring(from,to));
                from = to;
                while( inputline.charAt(from) == ' '
                && from = keywords.length) { status = true; break;}
            }
        }
        return status;
    }

...

任何让程序员再次看到Zork的理由在我的书中都很好,只需要留意Grues。

...

答案 4 :(得分:6)

Sun本身建议远离StringTokenizer并改为使用String.spilt方法。

您还需要查看Pattern类。

答案 5 :(得分:6)

对ANTLR / ANTLRWorks的另一次投票。如果你创建了两个版本的文件,一个是用于实际执行命令的Java代码,另一个是没有(只有语法),那么你就拥有了该语言的可执行规范,非常适合测试,对于文档来说是一个福音如果您决定移植它,那么节省大量时间。

答案 6 :(得分:4)

如果要解析命令行,我建议使用Commons Cli

  

Apache Commons CLI库提供了一个用于处理命令行界面的API。

答案 7 :(得分:4)

尝试JavaCC Java的解析器生成器。

它有很多用于解释语言的功能,并且在Eclipse上得到了很好的支持。

答案 8 :(得分:2)

@CodingTheWheel继承你的代码,有点清理并通过eclipse( ctrl + shift + f )并在此处插入: )

包括每行前面的四个空格。

public static boolean simpleNLP(String inputline, String keywords[]) {
    if (inputline.length() < 1)
        return false;

    List<String> lexed = new ArrayList<String>(); 
    for (String ele : inputline.split(" ")) {
        lexed.add(ele);
    }


    boolean status = false;
    to = 0;
    for (i = 0; i < lexed.size(); i++) {
        String s = (String) lexed.get(i);
        if (s.equalsIgnoreCase(keywords[to])) {
            to++;
            if (to >= keywords.length) {
                status = true;
                break;
            }
        }
    }
    return status;
}

答案 9 :(得分:1)

JCommander似乎相当不错,虽然我还没有测试过。

答案 10 :(得分:1)

split方法可以将字符串拆分为指定子字符串表达式regex的数组。 它的参数有两种形式,即:split(String regex)和split(String regex, int limit),其中split(String regex)实际上是通过调用split(String regex,int limit)来实现的, 限制为0 。然后,当限制&gt; 0 限制&lt; 0 代表什么?

jdk 解释时: limit&gt; 0 子数组长度达到限制,即,如果可能,可以 limit-1 细分,保留为子字符串(除了字符数限制为字符串的1倍)分裂结束);

limit&lt; 0 表示对数组的长度没有限制;

limit = 0 字符串空字符串的结尾将被截断。 StringTokenizer类是出于兼容性原因而保留的遗留类,因此我们应该尝试使用String类的split方法。 参考link

答案 11 :(得分:1)

如果您的文字包含一些分隔符,那么您可以使用split方法 如果文本包含不规则字符串,则表示格式不同,则必须使用regular expressions

答案 12 :(得分:1)

空格上的简单字符串标记符应该可以工作,但是有很多方法可以做到这一点。

以下是使用标记生成器的示例:

String command = "kick person";
StringTokenizer tokens = new StringTokenizer(command);
String action = null;

if (tokens.hasMoreTokens()) {
    action = tokens.nextToken();
}

if (action != null) {
    doCommand(action, tokens);
}

然后令牌可以进一步用于参数。这一切都假设参数中没有使用空格...所以你可能想要推出自己的简单解析机制(比如获取第一个空格并在之前使用文本作为动作,或者如果你不介意那么使用正则表达式)速度命中),只是将其抽象出来,以便可以在任何地方使用。

答案 13 :(得分:1)

如果语言很简单,就像

一样

VERB NOUN

然后用手拆分效果很好。

如果它更复杂,你应该真正研究像ANTLR或JavaCC这样的工具。

我在http://javadude.com/articles/antlrtut有一个关于ANTLR(v2)的教程,可以让你了解它是如何工作的。

答案 14 :(得分:1)

当命令的分隔符String总是相同的String或char(如“;”)y建议您使用StrinkTokenizer类时:

StringTokenizer

但是当分隔符变化或复杂时,建议您使用常规表达式,这可以由String类本身使用,方法分割,从1.4开始。它使用java.util.regex包中的Pattern类

Pattern