比较如何使用和不使用正则表达式完成下面提到的两个任务。问题:
基于SMS的食品交付的格式将是:
PABUSOG斜线或逗号重复无数次@
//数量只能是数字。为简单起见,假设数量始终为整数
e.g。 PABUSOG STRFRY_SMAI / 2 HSHBRWN_BRGR / 1 COFEEFLT / 1 @ En311
它将捕获以下内容:
STRFRY_SMAI - 2 HSHBRWN_BRGR - 1 COFEEFLT - 1
这是我的示例代码://使用正则表达式
String message = "PABUSOG ASD_ASD/1 ASD_ASA/2";
Pattern pattern = Pattern.compile("PABUSOG(\\s+([A-Z]+_[A-Z]+)(/|,)([0-9]))+"
,Pattern.CASE_INSENSITIVE);
Matcher m = pattern.matcher(message);
try
{
if (m.matches())
{
String food = m.group(2);
String quantity = m.group(4);
System.out.println(food + " -- " + quantity + "\\n");
}
}
catch (NullPointerException e)
{
}
显示ASD_ASA - 2,它会覆盖第一个ASD_ASD / 1。
必须显示
ASD_ASD - 1
ASD_ASA - 2
答案 0 :(得分:2)
使用单个正则表达式为您提供组内的所有数据,您无法做到这一点。并且也不需要复杂的正则表达式。但是如果您更喜欢正则表达式,请尝试迭代搜索模式。
if (!message.startsWith("PABUSOG")) {
return;
}
Pattern pattern = Pattern.compile("([A-Z_]+)[/,]([0-9])+", Pattern.CASE_INSENSITIVE);
Matcher m = pattern.matcher(message);
while (m.find()) {
String food = m.group(1);
String quantity = m.group(2);
System.out.println(food + " -- " + quantity);
}
如果没有复杂的正则表达式,您可以使用String
API执行以下操作:
// Check for correct header
if (!message.startsWith("PABUSOG")) {
return;
}
// split by whitespaces
String[] items = message.split("\\s+");
// skip header and iterate over remaining items
for (String item : Arrays.asList(items).subList(1, items.length)) {
// split each item by / or ,
String[] foodQuantity = item.split("[/,]");
assert foodQuantity.length == 2;
String food = foodQuantity[0];
String quantity = foodQuantity[1];
System.out.println(food + " -- " + quantity);
}
要跳过以@
开头的项目,您可以添加
if (item.startsWith("@")) {
break; // or continue if it can be not the last
}
内部循环或以下列方式限制subList
,如果您确定此类项始终存在并终止序列:Arrays.asList(items).subList(1, items.length - 1)
。
顺便说一句,您的模式[A-Z]+_[A-Z]+
与您的示例中的COFEEFLT
不匹配。