【问题标题】:Best way to split a string containing question marks and equals拆分包含问号和等号的字符串的最佳方法
【发布时间】:2014-05-16 13:13:16
【问题描述】:

有一个问题,我有一个 java 字符串:

String aString="name==p==?header=hello?aname=?????lname=lastname";

我需要在问号后面加上等号。

结果应该是键/值对:

name = "=p=="
header = "hello"
aname = "????"
lname = "lastname"

问题是aname和lname变成:

name = ""
lname = "????lname=lastname"

我的代码只是通过aString.split("\\?",2)进行拆分
这将返回 2 个字符串。一个包含键/值对,第二个字符串包含 字符串的其余部分。如果我在字符串中找到问号,我会递归第二个字符串以进一步分解它。

private String split(String aString)
 {
    System.out.println("Split: " + aString);
    String[] vals = aString.split("\\?",2);
    System.out.println("  - Found: " + vals.length);
    for ( int c = 0;c<vals.length;c++ )
       {
        System.out.println("  - "+ c + "| String: [" + vals[c] + "]" );
        if(vals[c].indexOf("?") > 0 )
          {
            split(vals[c]);
           }
        }
    return ""; // For now return nothing...
 }

有什么想法可以允许使用 的名称吗?
免责声明: 是的,我的正则表达式技能非常低,所以我不知道这是否可以通过正则表达式来完成。

【问题讨论】:

  • 为什么p没有被提取为key?
  • @Evan 有道理。您是否知道键(名称、标题、名称、lname)始终相同或来自特定集合?
  • 最终会的。现在,我试图在问号上分开。当我拆分这些时,我会得到一个字符串 "name==p==" ,然后我将拆分 ("\\=",2) 它得到键/值对
  • 嗯小鸡派...我明白你在说什么...即:我可以通过读取下一个键来执行诸如提取值之类的操作。
  • 问题在于您的输入。您不应使用也是特殊字符的字符(在您的情况下为=?)。如果您需要这些字符作为键名或值,您应该对它们进行转义,例如name=&amp;#61;p&amp;#61;&amp;#61;?header=hello?aname=&amp;#63;&amp;#63;&amp;#63;&amp;#63;?lname=lastname

标签: java string split


【解决方案1】:

您可以让正则表达式完成所有繁重的工作,首先将您的字符串分成两对:

String[] pairs = aString.split("\\?(?!\\?)");

那个正则表达式的意思是“a ? not跟着a ?”,它给出:

[name==p==, header=hello, aname=????, lname=lastname]

然后也将结果拆分为名称/值,仅拆分第一个“=”:

String[] split = pair.split("=", 2); // max 2 parts

把它们放在一起:

String aString = "name==p==?header=hello?aname=?????lname=lastname";
for (String pair : aString.split("\\?(?!\\?)")) {
    String[] split = pair.split("=", 2);
    System.out.println(split[0] + " is " + split[1]);
}

输出:

name is =p==
header is hello
aname is ????
lname is lastname

【讨论】:

    【解决方案2】:

    你可以这样试试

    String[] vals = "Hello??Man?HowAreYou????".split("\\?+");
    System.out.println(vals[0]+vals[1]+vals[2]);
    

    输出

    HelloManHowAreYou

    但是作为aname=?????你想得到你可以替换 ????? 五个问题用其他符号标记并在拆分后替换回?????

    String processed="Hello????Good? ? ....???".replace("????","*");
    

    输出

    Hello*Good? ? ....???
    

    比对?使用split

    【讨论】:

    • 您的替换仅在输入中有 4 个问号时才有效。如果有更多或更少怎么办?
    • @Absurd-Mind 是的,同意!!!但在我开始编辑我的答案之前,我看到Bohemian 发布的答案已经存在。
    【解决方案3】:

    这里是代码,你正在寻找。

    使用 Split 和 HashMap 实现。

    经过测试和执行。

    import java.util.HashMap;
    import java.util.Map;
    
    
        public class Sample {
    
            public static void main(String[] args) {
                // TODO Auto-generated method stub
    
    
        //      String[] vals = "Hello??Man?HowAreYou????".split("\\?+");
        //      System.out.println(vals[0]+vals[1]+vals[2]);
    
                String query="name==p==?header=hello?aname=?????lname=lastname";
                   String[] params = query.split("\\?");  
                    Map<String, String> map = new HashMap<String, String>();  
                    for (String param : params)  
                    {  
                        String name = param.split("=")[0];  
                        String value = param.substring(name.length(),param.length());  
                        map.put(name, value);  
                        System.out.println(name);
                        if(name.equals("")){
                            value+="?";
                        }
                        System.out.println(value.replaceAll(" ", ""));
                    }  
    
            }
    
        }
    

    【讨论】:

      【解决方案4】:

      我假设您正在解析 URL。正确的方法是编码所有特殊字符,如 ?&amp;=,它们是值或名称。

      更好的解决方案:编码字符

      String name = "=p==";
      String aname = "aname=????";
      String lname = "lastname";
      String url = "name=" + URLEncoder.encode(name, "UTF-8") +
                   "?aname=" + URLEncoder.encode(aname, "UTF-8") +
                   "?lname=" + URLEncoder.encode(lname, "UTF-8");
      

      之后你有这样的东西:

      name=&#61;p&#61;&#61;?aname=&#63;&#63;&#63;&#63;?lname=lastname
      

      这可以很容易地拆分和解码。

      其他解决方案:输入解析错误

      如果你坚持,这也有效。您可以使用正则表达式:

      Pattern pattern = Pattern.compile("(\\w+?)=(\\S+?\\?+)");
      Matcher m = pattern.matcher(query + "?");
      while (m.find()) {
          String key = m.group(1);
          String value = m.group(2);
          value = value.substring(0, value.length() - 1);
          System.out.println(key + " = " +value);
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-04-06
        • 2021-07-30
        • 1970-01-01
        • 1970-01-01
        • 2013-03-30
        相关资源
        最近更新 更多