C#解析字符串的一部分

时间:2016-01-15 16:35:51

标签: c# regex parsing

我们有一个打印出日志行的应用程序。在日志行中,我们还打印出xml中的完全syncML Payload。我需要解析syncML有效负载。实际的xml并删除其他所有内容。

日志行看起来像这样。

`2016-01-06T15:13:45.188-0500 [DEBUG] {} Logger
[{{Correlation,(longID)}{Uri,POST (post
URL)}{host,(HOST)}{userID,(userID)}}] - request class SyncML: <?xml
version="1.0" encoding="UTF-8" standalone="yes"?></ns3:SyncML>`

请求类的正则表达式如下。

 Regex request = new Regex(@"request class SyncML");
   String line;
   while ((line = sr.ReadLine()) != null)
   {
    if(req.Success)
     {
         Match req = request.Match(line);
         string s = line.Substring(line.IndexOf("<?xml "));
     }
   }

request.Match(line)之后,在VS中显示完整的一行。所以我知道比赛真的是成功的。

然而,当我line.SubString(line.IndexOF...时,我得到System.ArgumentOutOfRangeException。当我检查打印输出indexOf它是-1。

也许我正在使用这个错误。我想我的问题是我需要做些什么才能删除所有内容

5 个答案:

答案 0 :(得分:1)

如果&#34; <?xml&#34;字符串从下一行开始,使用:

Regex request = new Regex(@"request class winmo.SyncML");
String line;
while ((line = sr.ReadLine()) != null)
{
 if(req.Success)
 {
  Match req = request.Match(line);
  var xmlLine = line = sr.ReadLine();
  if (null == xmlLine) break;
  string s = xmlLine.Substring(line.IndexOf("<?xml "));
 }
}

或者,您可以针对新编辑的示例改进正则表达式:

Regex request = new Regex(@"^.+request class winmo.SyncML[^\<]+(\<\?xml [^`]+)`");
string line;
while ((line = sr.ReadLine()) != null)
{
 Match req = request.Match(line);
 if(req.Success)
  string s = req.Group[1].Value;
}

此外,您可以使用改进的Regex一次搜索多行:

Regex request = new Regex(@"^.+request class winmo.SyncML[^\<]+(\<\?xml [^`]+)");
var lines = new List<String>(5);
string line;
while ((line = sr.ReadLine()) != null)
{
 //NOTE:You'll need to make sure this gets enough of your log file to get what you want
 lines.Add(line);
 while(lines.Count>4) 
    lines.RemoveAt(0);

 Match req = request.Match(string.Join("\r\n", lines);
 if(req.Success)
  string s = req.Group[1].Value;
}

答案 1 :(得分:0)

尝试使用

"<?xml" 

而不是

"<?xml "

,我在xml之后看不到那个空格。

此问题已经过编辑。所以,如果字符串格式化为多行,你应该这样做:

while((line = sr.ReadLine))!= null){

    if(req.Success){

         Math req = request.Match(line);
         if(line.contains("<?xml")){
              stirng s = line.Substring(line.IndexOf(@"<?xml"));
         }
    }
}

答案 2 :(得分:0)

也许你想要这样的东西:

String line;
while ((line = sr.ReadLine()) != null)
{
  if(line.Contains("<?xml "))
  {
      string s = line.Substring(line.IndexOf("<?xml "));
      // do something useful with s
  }
}

答案 3 :(得分:0)

如果您将整个日志作为长字符串,则可以使用substring(x)indexof(string)来删除您感兴趣的区域之前的所有内容。我正在做出您的假设最后一行,初始日志信息之后的所有内容都是想要的xml的一部分。

string sFullLog = ReadFullLogAsASingleString();//Could be taxing in large logs
string sXML = sFullLog.Substring(sFullLog.IndexOf("<?xml"));

<击> 我看到提供的示例是一个日志条目,该日志条目的xml为intrest。

答案 4 :(得分:0)

你的正则表达式看起来错了它应该是正则表达式请求=新的正则表达式(@&#34;请求类SyncML&#34;);