当前位置: 首页 > 知识库问答 >
问题:

Java匹配字符串,直到第一次出现另一个字符串

郎翔
2023-03-14

我面临着与Java的匹配器的其他问题。我试图使用正则表达式匹配我的JSON的内容,而不使用外部库。我的JSON看起来像这样:

[
{
"FIRST":"Tom",
"LAST":"Hanks",
"SUFFIX":""
},
{
"FIRST":"Sammy",
"LAST":"Davis",
"SUFFIX":"Jr."
}
]

但是,我只想匹配上半部分中的单词,即在第一个}之前,匹配。我试图创建一个新的模式和匹配器,但我不知道如何进行,也不知道如何在第一次出现},

Pattern pattern = Pattern.compile("\"([^\"]*)\"");
Matcher matcher = pattern.matcher(loadJSONtoString(fileName).toString());
Pattern pattern2 = Pattern.compile("},");
Matcher matcher2 = pattern2.matcher(loadJSONtoString(fileName).toString());
while(matcher.find())
   {
         myList.add(matcher.group());
         //if matcher2 encounters }. for the first time: break;  
   }

共有1个答案

班思源
2023-03-14

因为您明确表示不想使用外部库,所以我假设您意识到使用正则表达式解析JSON需要很长的路要走,并且您应该真正使用JSON解析库。

在这种情况下,考虑JSON解析库本身是如何工作的。它实际上使用正则表达式。但是它有许多正则表达式,而不是一个正则表达式,每个正则表达式都是为了识别JSON语法的某些元素而设计的:带引号的字符串、数字、开括号或闭括号等。解析器根据这些正则表达式和由它们构建的东西来定义JSON语法:“字段”是一个带引号的字符串,后面跟着一个冒号,后面跟着一个值,“值”是一个带引号的字符串、一个数字、一个数组或一个对象“对象”是一个打开的大括号,后面跟着零个或多个字段,后面跟着一个关闭的大括号,等等。

使用正则表达式编写非常简单的解析器的一个好方法是定义一个返回“令牌”的正则表达式将每个标记定义为一个捕获组,并用“|”分隔它们,以便正则表达式可以匹配其中任何一个标记。您可以通过检查哪个捕获组匹配来确定找到了哪个令牌。(只有一个匹配。)然后反复使用正则表达式返回令牌,直到得到想要的令牌。

下面是一个简单的正则表达式,它可能适合您:

Pattern pattern = Pattern.compile("\"([^\\\"]*)\"|({)|(})|(\\[)|(\\])|(:)|,");

比赛分组如下:

  1. 引用的字符串
  2. 一个打开的支架
  3. 紧撑
  4. 一个开放的方括号
  5. 一个紧密的方括号
  6. 一个冒号

请注意,逗号没有捕获组,因为它是一种噪音,我们并不太关心它,并且正则表达式中与引用字符串匹配的部分排除了引号本身,因此您不必在解析过程中删除引号。

您需要构建一个函数,将此正则表达式应用于字符串的其余部分(即尚未解析的内容),然后在匹配组上循环,并返回匹配组的编号及其内容。对于某些匹配项,内容不会那么有趣(如果它匹配冒号,则内容将始终是冒号),但对于带引号的字符串,内容将是字符串本身。

假设有一个名为JsonScanner的类,它有两种方法:

  • getNextToken应用正则表达式并返回令牌的编号(即匹配组的编号)

现在您可以重复调用这些:

JsonScanner scanner(text);
scanner.getNextToken(); // should return '[' token
scanner.getNextToken(); // should return '{' token
scanner.getNextToken(); // should return quoted string
scanner.getContent(); // will return "FIRST"
etc.

实际上,您应该检查返回值是否符合预期,如果不符合预期,则抛出错误。

一旦读取了第一个对象(scanner.getNextToken()返回“}”标记),就可以停止扫描。

请注意,这是一个非常简单的实现。例如,引用的字符串正则表达式不处理字符串中的转义字符。如果您想实际验证JSON,您也必须返回逗号令牌,并确保逗号被正确使用。但这是大意。我自己也用这个策略编写了简单的解析器。

J2EE实际上包含一个名为JsonParser的类,它基本上为您实现了这个策略。它包含一个下一个方法,该方法返回一个标识令牌和内容的事件。

这里有人使用了类似的方法,除了使用一组捕获组而不是使用单个正则表达式,而是使用一组独立的正则表达式,并依次应用每个正则表达式,直到其中一个匹配。

 类似资料:
  • 我正在处理一个关于codingbat的问题,这个问题说:给定一个字符串和第二个“单词”字符串,我们会说这个单词匹配字符串,如果它出现在字符串的前面,除了它的第一个字符不需要完全匹配...在匹配时,返回字符串的前面,或以其他方式返回空字符串。所以,所以用字符串“河马”,“嗨”这个词返回“嗨”,“xip”返回“臀部”。单词长度至少为1。我不能解决它,但在网上找到了一个解决方案,代码如下所示。代码工作,

  • 问题内容: 我有类似’keepme:cutme’或’string-without-separator’之类的字符串,应分别成为’keepme’和’string- without-separator’。可以在PostgreSQL中完成吗?我试过了: 但这会留在字符串中,如果字符串中没有字符串,它将无法正常工作。 问题答案: 用途 : 如果分隔符不存在,则返回整个字符串。而且很容易获得第二或第三部分等

  • 我想解析一个字符串,看看它是匹配整个字符串还是子字符串。我试过这个: 但我的问题是:

  • 我想匹配string1和以下行中出现的任何内容: 直到遇到以下情况: 因此,在上述4种情况下,使用正确的正则表达式,粗体显示的结果将是匹配的: ['string 1','string 2','string 3'] [“字符串 1” , “字符串 2” , “字符串3”] ['string1.domain.com ',' string2.domain.com ',' string3.domain.c

  • 本文向大家介绍统计某一字符或字符串在另一个字符串中出现的次数相关面试题,主要包含被问及统计某一字符或字符串在另一个字符串中出现的次数时的应答技巧和注意事项,需要的朋友参考一下

  • 我正在尝试编写一个模式,该模式将只匹配按字面解释的字符串的第一个字符(可以是任何字符,也可以是空白)。 给定这个函数,它使用“非常没有魔力”来匹配作为参数给出的字符串,然后高亮显示该字符串,我如何修改它,使它只高亮显示第一个字符? 例如,在下面的文本中调用,只会在后面跟着,而不是在任何其他地方突出显示。目前,它突出显示整个给定字符串。 Lorem ipsum do{^(lor sit amet,