当前位置:编程学习 > C#/ASP.NET >>

求已正则表达式--------望高手指点

   容格式如下:     
       <div id="div1">
          <div>....</div>
          <a>..</a>
          <ul>..</ul>
           ...
        </div>

  
    求一正则表达式,匹配一对div标签, 可能有嵌套的div,可能有其他的HTML标签!
    
   
      --------------------编程问答-------------------- 其实呢,我们只关心你的文本是什么?然后你想匹配出什么? --------------------编程问答--------------------

            string str = @"div prev<span>spanspanspan</span>
<div id=""div1"">
<ul><li>this is li</li></ul>
<div>OneDiv</div>
<a>this is a</a>
</div>
div next
<a>aaaa</a>";
            Regex reg = new Regex(@"(?is)<div\s*id=""div1"">(?:(?!</?div).)*(?:(?:(?<Open><div)(?:(?!</?div).)*)*(?:(?<-Open></div)(?:(?!</?div).)*))*(?(Open)(?!))</div>");
            Console.WriteLine(reg.Match(str).Value);
/*
<div id=""div1"">
<ul><li>this is li</li></ul>
<div>OneDiv</div>
<a>this is a</a>
</div>
*/
--------------------编程问答--------------------
//匹配嵌套的正则表达式,只能获取到最外层的指定标签内容。 如果要获取内部的 需要递归。
string restr = @"<(?:{0})\b[^>]*>(?><(?!/?(?:{0})\b)[^>]*>|<(?:{0})\b[^>]*>(?<DEPTH>)|</(?:{0})\b[^>]*>(?<-DEPTH>)|[^<]*)*(?(DEPTH)(?!))</(?:{0})\b[^>]*>";
//筛选多种标签可以 table|div|span 这样
restr = string.Format(restr, "table");
Regex re = new Regex(restr, RegexOptions.IgnoreCase);
MatchCollection matches = re.Matches("你的网页源码");
{
    //匹配到的内容
    aa.Value;
}


你说的问题属于正则的嵌套和递归问题,也是正则中最难的。 --------------------编程问答--------------------
//匹配嵌套的正则表达式,只能获取到最外层的指定标签内容。 如果要获取内部的 需要递归。
string restr = @"<(?:{0})\b[^>]*>(?><(?!/?(?:{0})\b)[^>]*>|<(?:{0})\b[^>]*>(?<DEPTH>)|</(?:{0})\b[^>]*>(?<-DEPTH>)|[^<]*)*(?(DEPTH)(?!))</(?:{0})\b[^>]*>";
//筛选多种标签可以 table|div|span 这样
restr = string.Format(restr, "div");
Regex re = new Regex(restr, RegexOptions.IgnoreCase);
MatchCollection matches = re.Matches("你的网页源码");
{
    //匹配到的内容
    aa.Value;
}


根据你的情况我改成div标签. restr = string.Format(restr, "div"); --------------------编程问答--------------------
引用 2 楼 huangwenquan123 的回复:
C# code

            string str = @"div prev<span>spanspanspan</span>
<div id=""div1"">
<ul><li>this is li</li></ul>
<div>OneDiv</div>
<a>this is a</a>
</div>
div next
<a>aaaa</a>";
            Rege……


   非常感谢你的回复!我试过你写的正则了,有点问题
   例如:
    <div>
    <a>...</a>
   <div id="div1">
      <div>..</div>
      .......
   </div>   
   <div>...</div>
    <a>....</a>
   </div>
   
    这样的话会从<div id="div1"> 匹配到最后一个</div>
     --------------------编程问答-------------------- 这个需要用到平衡组来实现 --------------------编程问答--------------------

void Main()
{
string test = @"<div id=""0"">

0

</div>

<div id=""1"">

1

<div id=""2"">

2

</div>

</div>";

Regex reg = new Regex(@"(?isx)                      #匹配模式,忽略大小写,“.”匹配任意字符

  <div[^>]*>                      #开始标记“<div...>”

  (?>                         #分组构造,用来限定量词“*”修饰范围

  <div[^>]*>  (?<Open>)   #命名捕获组,遇到开始标记,入栈,Open计数加1

  |                           #分支结构

  </div>  (?<-Open>)      #狭义平衡组,遇到结束标记,出栈,Open计数减1

  |                           #分支结构

  (?:(?!</?div\b).)*      #右侧不为开始或结束标记的任意字符

  )*                          #以上子串出现0次或任意多次

  (?(Open)(?!))               #判断是否还有'OPEN',有则说明不配对,什么都不匹配

  </div>                          #结束标记“</div>”

  ");

MatchCollection mc = reg.Matches(test);

foreach (Match m in mc)

{

Console.WriteLine( m.Value +"\r\n---------我是分隔线------");

}

/*
<div id="0">

0

</div>
---------我是分隔线------
<div id="1">

1

<div id="2">

2

</div>

</div>
---------我是分隔线------

*/
}
--------------------编程问答--------------------
引用 4 楼 gzdiablo 的回复:
C# code
//匹配嵌套的正则表达式,只能获取到最外层的指定标签内容。 如果要获取内部的 需要递归。
string restr = @"<(?:{0})\b[^>]*>(?><(?!/?(?:{0})\b)[^>]*>|<(?:{0})\b[^>]*>(?<DEPTH>)|</(?:{0})\b[^>]*>(?<-DEPTH>)|[^<]*)*(?(DEPTH)(?!))</(?:{0})……


   非常感谢你的回复!

   用你写的正则表达式,发现在比较多DIV嵌套的情况下,比较慢!得到结果也和2楼相似 --------------------编程问答--------------------
引用 7 楼 q107770540 的回复:
C# code

void Main()
{
    string test = @"<div id=""0"">

    0

</div>

<div id=""1"">

    1

    <div id=""2"">

        2

    </div>

</div>";

Regex reg = new Regex(@"(?isx)                  ……


    非常感谢您的回复!

    如果我想要 <div id=""2"">

        2

    </div>
     ID="2"里面匹配嵌套DIV的innerHTML,该怎么做呢?  --------------------编程问答-------------------- 学习了。 --------------------编程问答--------------------
引用 5 楼 k123xie 的回复:
引用 2 楼 huangwenquan123 的回复:

C# code

string str = @"div prev<span>spanspanspan</span>
<div id=""div1"">
<ul><li>this is li</li></ul>
<div>OneDiv</div>
<a>this is a</a>
</div>
div next
<a>a……

不会啊,不会匹配到最后一个div
你怎么测试的?发来看看
不要跟我说你用正则工具测试的。
--------------------编程问答--------------------
				string restr = @"
<div\b[^>]*?id=[""']?2[^>]*>( #开始的DIV标签 id=[""']?2 就是你想要的id=2
(?> #贪婪匹配
<(?!/?div\b)[^>]*> #判断所有匹配到的非div标签
|<div\b[^>]*>(?<D>) #当匹配到<div...>时捕捉组D +1
|</div\b[^>]*>(?<-D>) #当匹配到</div>时捕捉组D -1
|[^<]* #匹配标签外的文本
)* #多次匹配上面的 
(?(D)(?!))) #当匹配组为空时 从?>开始的意思就是 当匹配到<div>时我记录+1 </div>时记录-1 然后循环直到记录数为0时结束
</div\b[^>]*> #匹配结束符";
regex re = new Regex(restr, RegexOptions.IgnoreCase); 
MatchCollection matches = re.Matches("你的网页源码"); 

aa.Group[1].Value; //这个就是你想要的div id=2的标签内部的HTML
}
--------------------编程问答-------------------- 括号打成全角的了 再发一次

                string restr = @"
                    <div\b[^>]*?id=[""']?2[^>]*>(    #开始的DIV标签 id=[""']?2 就是你想要的id=2
                    (?>                                #贪婪匹配
                    <(?!/?div\b)[^>]*>                #判断所有匹配到的非div标签
                    |<div\b[^>]*>(?<D>)                #当匹配到<div...>时捕捉组D +1
                    |</div\b[^>]*>(?<-D>)            #当匹配到</div>时捕捉组D -1
                    |[^<]*                            #匹配标签外的文本
                    )*                                #多次匹配上面的 
                    (?(D)(?!)))                        #当匹配组为空时 从?>开始的意思就是 当匹配到<div>时我记录+1 </div>时记录-1 然后循环直到记录数为0时结束
                    </div\b[^>]*>                    #匹配结束符";
                regex re = new Regex(restr, RegexOptions.IgnoreCase); 
                MatchCollection matches = re.Matches("你的网页源码"); 
                { 
                    aa.Group[1].Value; //这个就是你想要的div id=2的标签内部的HTML
                }
补充:.NET技术 ,  C#
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,