c#采集文章

/*
 *BLOGUSER  博主的名字
 * http://blog.youkuaiyun.com
 */
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
using HtmlAgilityPack;


namespace Collector
{


    public partial class Form1 : Form
    {
       // private Task[] tasks = null; //提供线程操作
        private const string BLOGUSER = "jyb"; //博客用户名  
        private const string BLOGURL = "http://92jyb.com";
        private const string PAGECOUNTPATH = "//div[@id='papelist']/span[1]"; //总页数PATH  
        private const string ARTICLEURLPATH = "//span[@class='link_title']/a[1]"; //文章URL的PATH      
        private const string ARTICLETITLEPATH = "//div[@class='article_title']/h3/span/a"; //文章标题PATH  
        private const string POSTDATEPATH = "//span[@class='link_postdate']"; //文章创建日期PATH  
        private const string ARTICLECONTENTPATH = "//div[@id='article_content']"; //文章内容PATH  
        private List<string> articleUrlList = new List<string>(); //所有文章的URL  
        private object moniter = new object();
        private Stopwatch stopwatch = new Stopwatch();
        private int cnt = 0;


        public Form1()
        {
            InitializeComponent();
        }
        /// <summary>  
        /// 单篇文章采集  
        /// </summary>  
        /// <param name="state"></param>  
        void CollectArticle(object state) {
            Interlocked.Increment(ref cnt);
            lock (moniter) {
                SetStatuText(string.Format("总共{0}篇文章, 正在采集中第{1}篇.", articleUrlList.Count, cnt));
                string articleUrl = (string)state;
                string firstArticleHtml = GetHtmlSource(articleUrl, Encoding.UTF8);
                if (string.IsNullOrEmpty(firstArticleHtml)) return;
                HtmlNode rootNode = GetHtmlNodeByHtml(firstArticleHtml);
                string articleTitle = GetNodeInnerText(rootNode, ARTICLETITLEPATH);
                string postDate = GetNodeInnerText(rootNode, POSTDATEPATH);
                string articleContent = GetNodeInnerText(rootNode, ARTICLECONTENTPATH);
                //采集结果处理:保存到数据库或其它......  
                string blogFile = BLOGUSER + ".txt";
                using (StreamWriter sw = new StreamWriter(blogFile, true)) {
                    sw.WriteLine(articleUrl);
                    sw.WriteLine(articleTitle);
                    sw.WriteLine(postDate);
                    sw.WriteLine(articleContent);
                }
            }
        }


        private void TaskEnded(Task[] task) {
            SetStatuText("采集结束,耗时 " + stopwatch.Elapsed.Minutes + "分" + stopwatch.Elapsed.Seconds + "秒");
        }  
        //获取总页数  
        private int GetPageCount(string pageCountUrl)
        {
            HtmlNode rootNode = GetHtmlNodeByUrl(pageCountUrl, Encoding.UTF8);
            if (rootNode == null)
                return 0; 
            string pageCountText = GetNodeInnerText(rootNode, PAGECOUNTPATH);
            int firstIndex = pageCountText.LastIndexOf("共") + 1;
            int lastIndex = pageCountText.LastIndexOf("页");
            string result = pageCountText.Substring(firstIndex, lastIndex - firstIndex);
            return Convert.ToInt32(result);
        }






        //通过网页URL获取HtmlNode  
        private HtmlNode GetHtmlNodeByUrl(string url, Encoding encoding)
        {
            string html = GetHtmlSource(url, encoding);
            if (string.IsNullOrEmpty(html)) return null;


            HtmlAgilityPack.HtmlDocument document = new HtmlAgilityPack.HtmlDocument();
            document.LoadHtml(html);
            HtmlNode rootNode = document.DocumentNode;
            return rootNode;
        }


        //通过网页html源代码获取HtmlNode  
        private HtmlNode GetHtmlNodeByHtml(string htmlSource)
        {
            HtmlAgilityPack.HtmlDocument document = new HtmlAgilityPack.HtmlDocument();
            document.LoadHtml(htmlSource);
            HtmlNode rootNode = document.DocumentNode;
            return rootNode;
        }


        /// <summary>  
        /// 获取网页源代码  
        /// </summary>        
        private string GetHtmlSource(string url, Encoding encoding)
        {
            string result = "";
            try
            {
                WebRequest request = WebRequest.Create(url);
                using (WebResponse response = request.GetResponse())
                using (StreamReader reader = new StreamReader(response.GetResponseStream(), encoding))
                    result = reader.ReadToEnd();
            }
            catch
            {
                result = "";
            }
            return result;
        }


        private string GetNodeInnerText(HtmlNode srcNode, string path)
        {
            HtmlNode temp = srcNode.SelectSingleNode(path);
            if (temp == null)
                return null;
            return temp.InnerText;
        }


        private void SetStatuText(string s)
        {
            this.SafeCall(() =>
            {
                lblStatusInfo.Text = s;


            });
        }
        //开始采集按钮
        private void button1_Click(object sender, EventArgs e) {
            stopwatch.Restart();
            Task.Factory.StartNew(() => {
                cnt = 0;
                int pageCount = GetPageCount(BLOGURL + "/" + BLOGUSER);
                if (pageCount == 0)
                    return;


                //所有文章的URL  
                for (int pageIndex = 1; pageIndex <= pageCount; pageIndex++) {
                    string pageIndexUrl = BLOGURL + "/" + BLOGUSER + "/article/list/" + pageIndex.ToString();
                    HtmlNode rootNode = GetHtmlNodeByUrl(pageIndexUrl, Encoding.UTF8);
                    if (rootNode == null)
                        continue;


                    HtmlNodeCollection ArticleUrlList = rootNode.SelectNodes(ARTICLEURLPATH);
                    foreach (HtmlNode articleUrlNode in ArticleUrlList) {
                        string articleUrl = BLOGURL + articleUrlNode.Attributes["href"].Value;
                        articleUrlList.Add(articleUrl);
                    }
                }
            }).ContinueWith((x) => {
                TaskFactory taskFactory = new TaskFactory();
                Task[] tasks = new Task[articleUrlList.Count];
                for (int i = 0; i < articleUrlList.Count; i++) {
                    tasks[i] = new Task(CollectArticle, articleUrlList[i]);
                    tasks[i].Start();
                }
                taskFactory.ContinueWhenAll(tasks, TaskEnded, TaskContinuationOptions.None);
            });  
        }
    }


    public static class Extenstions
    {
        public static void SafeCall(this Control ctrl, Action callback)
        {
            if (ctrl.InvokeRequired)
                ctrl.Invoke(callback);
            else
                callback();
        }
    }
}
    

预览图片见:http://www.cnblogs.com/xxpyeippx/archive/2008/03/31/1131211.html运行环境windows nt/xp/2003 or above.net Framework 1.1SqlServer 2000 开发环境 VS 2003目的学习了网络编程,总要做点什么东西才好。于是想到要做一个网页内容采集器。作者主页: http://www.fltek.com.cn使用方式测试数据采用自cnBlog。见下图用户首先填写“起始网页”,即从哪一页开始采集。然后填写数据库连接字符串,这里是定义了采集到的数据插入到哪个数据库,后面选择表名,不必说了。网页编码,不出意外的话,中国大陆都可以采用UTF-8爬取文件名的正则:呵呵 这个工具明显是给编程人员用的。正则都要直接填写啦。比如说cnblogs的都是数字的,所以写了\d建表帮助:用户指定要建立几个varchar型的,几个text型的,主要是放短数据和长数据啊。如果你的表里本来就有列,那就免啦。程序里面没有做验证哦。网页设置里面:采集内容前后标记:比如说都有 xxx,如果我要采集xxx就写“到”,意思,当然就是到之间的内容啦。后面的几个文本框是显示内容的。点击“获取URL”可以查看它捕获的Url对不对的。点击“采集”,可以把采集内容放到数据库,然后就用 Insert xx () (select xx) 可以直接插入目标数据了。程序代码量非常小(也非常简陋),需要的改动一下啦。不足 应用到了正则表达式、网络编程由于是最简单的东西,所以没有用多线程,没有用其他的优化方法,不支持分页。测试了一下,获取38条数据,用了700M内存啊。。。。如果有用的人 ,可以改一下使用啦。方便程序员用,免写很多代码。Surance Yin@ Surance Center 转载请注明出处
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值