最大的網站源碼資源下載站,
一、弄清結構再動手
要想輕松的抽取rss信息,自然先要了解它的結構,所謂“知己知彼,百戰不殆”嘛。
1、rss的結構
我們先打開百度新聞一個rss鏈接,如果你再多打開幾個別的網站的rss鏈接,會發現他們都有大致相同的結構。而我們在揭秘rss(上)中為大家講解的其實就是編成實現這樣的一個xml文件。
為了能夠方便地對這樣的xml文檔進行處理,在本文里,我們使用c#作為開發的語言。
分析整個rss鏈接后,我們知道rss大致的結構入圖1。

2、抽取的原理
知道了結構,我們還要知道結構中各部分的含義。在圖1中rss節點表示當前是一個rss文件,它由一個channel節點及其子節點組成,其中一些子節點提供關于頻道本身的信息,比如title表示頻道的名稱(“百度互聯網新聞”)。
channel節點又包含多個item子節點,而item節點就是程序需要處理的部分,因為它對應著每條實際的新聞項信息, 每個item節點又通過其子節點提供關于這條新聞的詳細信息,比如title表示新聞的標題(“微軟im稱王”),link對應新聞實際的鏈接。
rss具體規范可查看http://blogs.law.harvard.edu/tech/rss
知道了這些后,要編程就不困難啦。我們只需提取并顯示出channel和item下的各條信息就可以了。現在來看看具體的實現方法吧。
二.做個程序讀新聞
對rss有一定了解后,我們開始編寫程序。先還是需要一個最簡單的界面。新建一個win form 工程,在form上放置一個label,一個文本框txturl用來輸入rss鏈接(就是各網站rss鏈接中包含的地址),一個按鈕bnread用來執行讀取新聞, 一個treeview樹形控件treerss顯示讀出的新聞項。
1、定義裝載結構
根據上面分析的rss結構,我們首先來建立一個rss類,用它來裝載rss鏈接中channel和item的各條信息。代碼如下:
public class rss
{
public struct channel
{
public string title;
public hashtable items;
}
public struct item
{
public string title;
public string description;
public string link;
}
}
channel結構將存儲channel節點包含的所有子節點信息,其中items成員字段是一個hashtable集合,程序會將item結構作為對象加入集合,用來存儲channel下的所有item節點。這里我只讀取了有限的幾個節點,讀者可以根據實際需要擴展整個結構定義。 2、從rss鏈接中獲取新聞信息
現在我們就可以開始編寫讀取函數,將抽取出的rss信息放入上面設計好的結構中。
c#提供了專門的類來訪問xml, 使我們能夠輕松地讀出rss的內容。代碼如下:
xmltextreader reader = new xmltextreader(url);
xmlvalidatingreader valid = new xmlvalidatingreader(reader);
valid.validationtype = validationtype.none;
xmldocument xmldoc= new xmldocument();
xmldoc.load(reader);
使用xmldocument類將txturl中輸入的rss鏈接加載后,首先通過foundchildnode函數,找到channel節點。
private xmlnode foundchildnode(xmlnode node,string name)
{
xmlnode childlnode = null;
for (int i=0;i < node.childnodes.count;i++)
{
if ( node.childnodes[i].name == name && node.childnodes[i].childnodes.count > 0 )
{
childlnode = node.childnodes[i];
return childlnode;
}
}
return childlnode;
}
xmlnode rssnode = foundchildnode(xmldoc,"rss");
xmlnode channelnode = foundchildnode(rssnode,"channel");
然后我們就可以遍歷它的子節點,根據子節點的name屬性,讀取我們需要的信息。
rss.channel channel=new rss.channel();
channel.items=new hashtable();
{
switch ( channelnode.childnodes[i].name )
{
case "title":
{
channel.title = channelnode.childnodes[i].innertext;
break;
}
case "item":
{
rss.item item=this.getrssitem(channelnode.childnodes[i]);
channel.items.add(channel.items.count,item );
break;
}
}
}
如果發現是item子節點,就調用getrssitem函數,同樣通過遍歷子節點的方法,將其子節點內容填入item結構中,然后再添加到channel結構的items集合中。因為本程序并不關心添加到集合的鍵值,只需要它是不重復的值,所以我傳入了count屬性。
3.將讀出的信息顯示在程序中
將rss內容讀出后,就需要把信息展示給用戶了。我們這里用的是基本的treeview方法,通過遍歷channel結構的items集合,將其標題添加到treeview中。
private void viewrss(rss.channel channel)
{
treerss.beginupdate();
treerss.nodes.clear();
treenode channelnode=treerss.nodes.add(channel.title );
channelnode.tag="";
for (int i=0;i <channel.items.count ;i++)
{
rss.item item=(rss.item)channel.items[i];
treenode itemnode=channelnode.nodes.add(item.title );
itemnode.tag=item.link;
}
treerss.expandall();
treerss.endupdate();
}
同時我們還可以設置treeview的每個子節點的tag屬性為它對應的鏈接。以便當選中子節點時就可以通過讀取tag屬性訪問具體的信息。
private void treerss_afterselect(object sender, system.windows.forms.treevieweventargs e)
{
treenode itemnode=e.node ;
string url=itemnode.tag.tostring();
if (url.length!=0)
system.diagnostics.process.start( url);
}
程序運行效果如圖2。

三.小結
怎么樣,一個簡單的rss新聞閱讀器就按前面所說輕松完成了,容易吧。雖然它還有很多不足,但如果大家通過這個例子學會了抽取rss鏈接信息的基本方法,那就足夠了!