zoukankan      html  css  js  c++  java
  • 利用正则表达式获取博客园随笔(三)

      到昨晚为止,我们已经获取第一页的数据了,但是这是不是有很大的局限性呢?比如如果我要获取前3页的,那我是不是要改代码?我们点击第二页的时候浏览器上面是不是还是显示“http://www.cnblogs.com/”?那我们把鼠标放在第二页上,就可以发现博客园的分页方式,我们把这个地址再地址栏中输入也还是可以到达第二页,所以说我们的想法是正确的。所以我们可以再界面上加一个文本框(用来输入我们要获取的页数),然后再放一个按钮用来查询。

    代码如下:

     1 int page=1;
     2             try
     3             {
     4                 page = Convert.ToInt32(txtPage.Text.Trim());
     5             }
     6             catch
     7             { 
     8                 MessageBox.Show("请输入数字","提示"); 
     9             }
    10             for (int i = 1; i <= page; i++)
    11             {
    12                 Html = Html + GetHtml("http://www.cnblogs.com/p" + i);
    13             }
    14             Thread thread = new Thread(new ThreadStart(() =>
    15             {
    16                 GetContent gc = new GetContent();
    17                 gc.getResults += new GetContent.CnblogsEventHandler(gc_getResults);
    18                 gc.getResult(Html);
    19             }
    20                 ));
    21             thread.IsBackground = true;
    22             thread.Start();
    View Code
     1     public class GetContent
     2     {
     3         public delegate void CnblogsEventHandler(List<CnblogsResult> results);
     4         public event CnblogsEventHandler getResults;
     5         public List<CnblogsResult> getResult(string Html)
     6         {
     7            List<CnblogsResult> results = new List<CnblogsResult>();
     8             Regex regexContent = new Regex("<div class="post_item_body">(?<content>.*?)<div class="clear"></div>", RegexOptions.Singleline);//获取单个随笔数据
     9             Regex regexProperty = new Regex("<h3><a.*?href="(?<href>.*?)".*?>(?<Title>.*?)</a></h3>.*?<a .*? class="lightblue".*?>(?<Author>.*?)</a>.*?发布于.*?(?<time>.*?)<span",
    10     RegexOptions.Singleline);//获取标题、时间、链接、作者等
    11             if (regexContent.IsMatch(Html))
    12             {
    13                 var blog = regexContent.Matches(Html);
    14                 int i = 1;
    15                 foreach (Match item in blog)
    16                 {
    17                     CnblogsResult result = new CnblogsResult();
    18                     if (regexProperty.IsMatch(item.ToString()))
    19                     {
    20                         var Property = regexProperty.Match(item.ToString());
    21                         result.Title = Property.Groups["Title"].Value;
    22                         result.Author = Property.Groups["Author"].Value;
    23                         result.time = Property.Groups["time"].Value;
    24                         result.href = Property.Groups["href"].Value;
    25                         result.Rank = i;
    26                         i++;
    27 
    28                     }
    29                     results.Add(result);
    30                 }
    31             }
    32             if (getResults != null)
    33             {
    34                 getResults(results);
    35             }
    36             return results;
    37         }
    38     }
    View Code

    其中CnblogsResult是我定义的一个实体类:

    1 public class CnblogsResult
    2     {
    3         public int Rank { get; set; }
    4         public string Title { get; set; }
    5         public string Author { get; set; }
    6         public string time { get; set; }
    7         public string href { get; set; }
    8     }
    View Code

    然后再Form类里加一段方法:

     1         void gc_getResults(List<CnblogsResult> results)
     2         {
     3             DataTable dt = new DataTable();
     4             dt.Columns.Add("Rank");
     5             dt.Columns.Add("Title");
     6             dt.Columns.Add("Author");
     7             dt.Columns.Add("time");
     8             dt.Columns.Add("href");
     9             foreach (var item in results)
    10             {
    11                 dt.Rows.Add(item.Rank, item.Title, item.Author, item.time, item.href);
    12             }
    13             Invoke(new Action(() =>//委托主线程来完成数据绑定
    14             {
    15                 dgvCnblogs.DataSource = dt;
    16             }
    17             ));
    18         }
    View Code

    到这里呢,我们已经可以获取任意页数的数据了(当然是整数的)。但是还是有个问题,就是如果我们要查询的页数多了,界面会处于一个假死的状态,那我们要如何避免呢?眼尖的朋友估计都看到了线程了,没错,就是通过线程方法来给gridview进行一条条数据的加载,这样界面就不会处于假死状态了。这个的话,我们就明天来探讨吧。还是那句话,大家如果有其他更好的方法,欢迎探讨。

      话说这些代码里的线程、Lambda表达式、事件与委托、正则都是我当初刚参加工作的时候刚接触的时候写的,写的不好的地方大家请见谅(这之后也没怎么接触过这些东西了)。

  • 相关阅读:
    cscope的使用
    关于函数指针
    linux内核源码目录(转)
    lcc之内存分配
    符号管理之符号表
    监听UITextFiled文本发生改变
    Debugging Tools for Windows__from WDK7
    WinDBG__独立安装文件
    20160215
    QT Creator 代码自动补全
  • 原文地址:https://www.cnblogs.com/suixingerxing/p/3233470.html
Copyright © 2011-2022 走看看