是否有一个库,它在给定的两个字符串上提供占位符值?

问题描述

给定两个字符串

String command = "Header '{1}' has a value that ends with '{2}' (ignore case)";
String input = "Header 'some-value' has a value that ends with '123ws' (ignore case)";

我想获取价值地图。

0 -> some-value
1 -> 123ws

我引用了 this answer on Java Comparing two strings with placeholder values,根据我的使用情况稍微调整了它。

private static Map<Integer,Object> getUserInputMap(String command,String input) {

        System.out.println("\t" + command);
        System.out.println("\t" + input);

        command = command.replace("(","<");
        command = command.replace(")",">");
        input = input.replace("(","<");
        input = input.replace(")",">");

        Map<Integer,Object> userInputMap = new HashMap<>();

        String patternTemplate = command.replace("{0}","(.*)");
        patternTemplate = patternTemplate.replace("{1}","(.*)");
        patternTemplate = patternTemplate.replace("{2}","(.*)");

        Pattern pattern = Pattern.compile(patternTemplate);
        Matcher matcher = pattern.matcher(input);
        if (matcher.matches()) {
            for (int gi = 1; gi <= matcher.groupCount(); gi++) {
                String uin =  matcher.group(gi);
                uin = uin.replace("<","(");
                uin = uin.replace(">",")");
                userInputMap.put(gi - 1,uin);
            }

        }
        return userInputMap;
    }

但是,可能有很多极端情况。我担心我的解决方案是我可能会错过一个角落案例,然后是生产错误

是否有围绕此编写的成熟库?我正在检查 messageformat/StrSubstitutor,但我无法获得任何符合我预期的方法

解决方法

从已经格式化的字符串中获取除字符串以外的任何内容并不容易,我不会在这里处理。

您基本上知道占位符的格式,即 {digits},因此您可以通过以下方式拆分命令:command.split("\\{0|[1-9][0-9]*\\}"(不允许 {01} 等)。

然后遍历结果数组中的元素并在 input 中查找完全匹配。执行此操作时,您希望跟踪结束索引以从那里开始搜索,而不是再次从 input 开始。

快速简单的示例(未测试):

String[] parts = command.split("\\{0|[1-9][0-9]*\\}");
int paramStart = 0;
int index = 0;
for( String part : parts ) {  
  index = input.indexOf(part,index);
  if( index < 0) {
    //problem: command part hasn't been found - you probably want to end parsing here
  } 

  //the first part should be found at index 0 so ignore that
  if( index != 0 )
    //parameter value should be between the last part and the current one
   String parameterValue = input.substring(paramStart,index);
  } 

  //the next parameter starts after the current part
  paramStart= index + part.length();
}

//there seems to be a last placeholder at the end of the command
if(paramStart < input.length() - 1) {
  //get the substring here
}

这应该能够处理大多数情况,除了参数看起来像命令部分或占位符彼此相邻且无法区分的情况。以 "{1} - {2}" 和参数 "A - B""C - D" 为例 - 结果将是 "A - B - C - D",在这种情况下,如果没有更多参数,您将无法安全地确定这两个参数的值信息(您没有仅占位符的信息)。