zoukankan      html  css  js  c++  java
  • 老蜗牛写采集:获取数据(正则篇)

    致歉

         首先感谢博友对这个系列的支持,很多加群的人都问我啥时候更新,我一直回答尽快,结果一拖就一年了。因为工作和生活占据我大量的时间,所以只能跟大伙说声抱歉。

    使用正则获取数据

      前两篇讲到如何采集html数据,那采集回来肯定要截取我们有用的部分,举个例子。我们要采集搜狐新闻的社会栏目,地址如下:

      http://news.sohu.com/shehuixinwen.shtml

      我们首先获取到新闻列表,看上两章介绍到使用xNet获取到搜狐新闻的社会栏目的html源码,当然你可以使用httprequest或者第三方组件。代码如下:

    var html = string.Empty;
                using (var request = new xNet.HttpRequest())
                {
                    html = request.Get("http://news.sohu.com/shehuixinwen.shtml").ToString();
                }
    

      得到html值:

    <!doctype html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/ xhtml1-transitional.dtd">
    
    
    <script type="text/javascript">
      var pvinsight_page_ancestors = '143746642;143746651';
    </script>
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head>
    <meta http-equiv="content-type" content="text/html; charset=gb2312" />
    <title>社会新闻-搜狐新闻</title>
    <script type="text/javascript" src="http://www.sohu.com/sohuflash_1.js"></script>
    <meta http-equiv="X-UA-Compatible" content="IE=EmulateIE7" />
    <meta name="description" content="搜狐社会新闻关注社会民生、百姓问题。精品栏目:社会万象、百姓生活" />
    <meta name="keywords" content="社会,社会新闻,万象,百姓,口述" />
    <meta name="robots" content="all" />
    
    
    <link type="text/css" rel="stylesheet" href="http://css.sohu.com/upload/global1.4.1.css" />
    <link rel="stylesheet" href="http://news.sohu.com/upload/zhengyufeng/xinwenerjiye/style1.css" />
    <script type="text/javascript" src="http://js.sohu.com/library/jquery-1.7.1.min.js"></script>
    <script type="text/javascript" src="http://news.sohu.com/upload/2013page/j.js"></script>
    <!--[if IE 6]>
        <script src="http://news.sohu.com/upload/zhengyufeng/pngAlaph.js"></script>
        <script>DD_belatedPNG.fix('#header,h3,h3 span,.shipin,.dashiye_list li,.liushengji_list li,#imgText b,img,.followScroll a,#contentA .left .tit span');
        </script>
    <![endif]-->
    
    .....
    
    
    
    <script language="javascript">
    if(_wratingId !=null){
    document.write('<scr'+'ipt type="text/javascript">');
    document.write('var vjAcc="'+_wratingId+'";');
    document.write('var wrUrl="http://sohu.wrating.com/";');
    document.write('try{vjTrack();}catch(e){}');
    document.write('</scr'+'ipt>');
    }
    </script>
    <script> require(["sjs/matrix/ad/passion"]);</script>
    <!--SOHU:SUB_FOOT_DIV-->
     
    
    
    </body>
    </html>
    

      

      因为html比较大,所以不显示全部,为了防止搜狐改版,我还是截取一段样板

    					<div class="article-list">
    					<div class="article">
                            <h3><span class="com-num"><a target="_blank" href="#">comment num</a></span><a target="_blank" href="http://www.sohu.com/a/190778382_119562">“五假副部”现形始末:被指讲话稿都念不顺</a></h3>
                            <p>...<a target="_blank" href="http://www.sohu.com/a/190778382_119562">阅读全文>></a></p>
    					</div>
    					
    					<div class="pic-group">
    					</div>
    					
    					<div class="fun clear">
                            <div class="share">
                                    <ul>
                                            <li class="s-t">分享到 |</li>
                                            <li class="blg"><a title="·??í?????ü????" href="javascript:void(0)"></a></li>
                                            <li class="qq"><a title="·??í??QQ????" href="javascript:void(0)"></a></li>
                                            <li class="rrw"><a title="·??í????????" href="javascript:void(0)"></a></li>
                                            <li class="db"><a title="·??í????°ê" href="javascript:void(0)"></a></li>
                                            <li class="itb"><a title="·??í??i?ù°?" href="javascript:void(0)"></a></li>
                                    </ul>
                            </div>
    					<!--	<div class="label">±ê????<a target="_blank" href="#">??????</a> <a target="_blank" href="#">???ú</a> <a target="_blank" href="#">????</a></div> -->
    						<div class="time"> 发表于 2017-09-09 13:03</div>
    					</div>
    					</div>
    

      

      那我们要获取新闻列表的标题和连接地址怎么获取了?  那么就要介绍本篇的核心,使用正则,一讲到正则很多人会觉得很难,因为写法比较火星语。第二就是测试正则,市面上有很多测试工具,包括在线的都有,看你的喜好了,这里我要介绍一个超级无敌好用的测试工具,大家可以去网上下载或者在本文最后的会有下载链接,这个工具名叫:RegExBuilder  为啥说他好用,主要是他采用即时匹配,这样对新手可以一步步的调试编写正则。使用上面的工具可以得到以下正则匹配新闻列表和连接地址代码:

    <h3>[^>]*>[^>]*>[^>]*>[^>]*><a.target="_blank"shref="(?<url>[^"]*)[^>]*>(?<title>[^<]*)  

      写得比较粗犷,估计一百个人有一百个写法,所以这也是正则有魔力的地方,入门难,入门后小菜一碟。这里要说明一下,(?<title>[^<]*)是可以通过 title 这个关键字获取值,后面代码会写到。但在javascript、java、php等是按索引获取的,所以C#还是比较人性化滴

      使用代码获取我们要的数据,首先得定义一个新闻类:

        class NewsItem
        {
            public string Title { get; set; }
            public string Url { get; set; }
            public string Content { get; set; }
        }
    

      逻辑代码

                var html = string.Empty;
                using (var request = new xNet.HttpRequest())
                {
                    html = request.Get("http://news.sohu.com/shehuixinwen.shtml").ToString();
                }
    
                var newsList = new List<NewsItem>();
                var mc = Regex.Matches(html, @"<h3>[^>]*>[^>]*>[^>]*>[^>]*><a.target=""_blank""shref=""(?<url>[^""]*)[^>]*>(?<title>[^<]*)");
                foreach (Match m in mc)
                {
                    var newsItem = new NewsItem();
                    newsItem.Title = m.Groups["title"].Value;
                    newsItem.Url= m.Groups["url"].Value;
    
                    //按索引获取,具体看RegExBuilder工具的索引
                    newsItem.Url = m.Groups[1].Value;
                    newsItem.Title = m.Groups[2].Value;
              newsList.Add(newsItem); }

      

      注意转译字符串哦,不是两个正则不一样,然后就可以得到整个新闻的列表,有人会提问,那下一页呢?嘿嘿...车只能开到这了。

      获取新闻内容,拿到地址后,可以用xNet获取html源码,然后分析,示例如下:

      先用RegExBuilder编写正则代码,得到:

    <articlesclass="article">(?<content>.+?)</article>
    

      这里要勾选Singleline选项,Singleline顾名思义就是全部按单行匹配,就是有换行也按单行,还有其他几种匹配模式,其实都可以按字面意思去理解。譬如:

      IgnoreCase:忽略大小写

      Multiline:多行匹配

      RightToLeft:从右到左匹配

      其他可以参考这位道友的文章,http://blog.csdn.net/qq_33729889/article/details/63035440

      获取数据的逻辑代码

                foreach (var newItem in newsList)
                {
                    using (var request = new xNet.HttpRequest())
                    {
                        html = request.Get(newItem.Url).ToString();
                    }
    
                    Match m = Regex.Match(html, @"<articlesclass=""article"">(?<content>.+?)</article>", RegexOptions.Singleline);
                    if (m.Success)
                    {
                        newItem.Content = m.Groups["content"].Value;
                    }
                }
    

      以上就是简单使用正则获取html数据的案例。

    一些简单正则的使用

      其实会使用一些简单的东西基本上就能满足我们的开发需求

      譬如:<div>数据</div>

      最简单的写法:<div>(w+)</div> 括号是你要取的数据w是匹配所有的字符,+是代表一个以上,如果使用*就是包含零个字符

      进阶一点的写法:<[^>]*>(w+)</div>            [^>]*是如果非>则一直匹配

      更多的正则教程可以参考http://www.cnblogs.com/zery/p/3438845.html

     附上正则匹配小工具下载地址:

     http://www.jb51.net/softs/389196.html

    C#.NET开源项目、机器学习、足球赛事资料库 

      开源Q群:302961959

      足球研究技术群:142780296

  • 相关阅读:
    Jmeter之写入测试结果到Excel文件
    jmeter之BeanShell 断言
    jmeter-csv数据文件设置之线程共享模式
    LoadRunner生成随机位数的字符串
    linux命令操作
    LoadRunner函数
    vi常用操作
    LoadRunner常见问题
    面试题库
    jmeter持续集成化(二)---jenkins+ant+jmeter
  • 原文地址:https://www.cnblogs.com/weitaoxiaozhu/p/7512579.html
Copyright © 2011-2022 走看看