使用htmlparser爬蟲技術爬取電影網頁的所有下載連接

昨天,咱們利用webcollector爬蟲技術爬取了網易雲音樂17萬多首歌曲,並且還包括付費的在內,若是時間容許的話,能夠獲取更多的音樂下來,固然,也有小夥伴留言說這樣會下降國人的知識產權保護意識,誠然,咱們的重點在於如何靈活運用咱們已學的技術,這就須要咱們不斷的練習,不停的思索和深刻發掘,在瞭解了精髓和意義以後運用到實踐中才是技術的最高境界。html

今天呢,本着昨天的興趣,想來爬一爬電影資源,中途爲了找一個好用趁手的工具,也是費了很多心思,早上半天基本上都在學習和找資料的過程當中度過,下午開始才進入狀態,那麼, 今天咱們就來利用htmlparse爬取電影網頁中的所有電影下載連接。node

咱們先來認識一下htmlparser:git

HTMLParser具備小巧,快速的優勢,缺點是相關文檔比較少(英文的也少),不少功能須要本身摸索。對於初學者仍是要費一些功夫的,而一旦上手之後,會發現HTMLParser的結構設計很巧妙,很是實用,基本你的各類需求均可以知足。web

TMLParser的核心模塊是org.htmlparser.Parser類,這個類實際完成了對於HTML頁面的分析工做。這個類有下面幾個構造函數:api

  • public Parser ();
  • public Parser (Lexer lexer, ParserFeedback fb);
  • public Parser (URLConnection connection, ParserFeedback fb) throws ParserException;
  • public Parser (String resource, ParserFeedback feedback) throws ParserException;
  • public Parser (String resource) throws ParserException;public Parser (Lexer lexer);
  • public Parser (URLConnection connection) throws ParserException;
  • public static Parser createParser (String html, String charset);

對於大多數使用者來講,使用最多的是經過一個URLConnection或者一個保存有網頁內容的字符串來初始化Parser,或者使用靜態函數來生成一個Parser對象。ParserFeedback的代碼很簡單,是針對調試和跟蹤分析過程的,通常不須要改變.eclipse

這裏比較有趣的一點是,若是須要設置頁面的編碼方式的話,不使用Lexer就只有靜態函數一個方法了。對於大多數中文頁面來講,好像這是應該用得比較多的一個方法。
函數

 

一、前期準備,下載htmlparse壓縮包並配置到eclipse上,到下面網址能夠下載工具

 

http://htmlparser.sourceforge.net/,解壓後以下圖所示學習

二、網頁的分析與根據網頁源碼使用htmlparse編碼

 

一、這裏先分析與獲取一個電影介紹頁面的內容

 

 

 咱們如今先來獲取一個頁面的下載連接

/**
     * 獲取一個頁面的下載連接
     */
    public static String getMoiveDownloadUrl(String moiveIntroUrl) {
        // 頁面下載鏈接保存在這裏
        String moiveDownLoadUrl = "";
        try {
            // 首先根據頁面URL創建一個Parser.
            Parser parser = new Parser(moiveIntroUrl);
            // 使用parser中extractAllNodesThatMatch方法,這個有許多的過濾器,能夠幫助咱們過濾出咱們想要的內容,具體能夠看api的介紹
            // 這裏咱們使用連接文本過濾器,能夠過濾出連接裏面含ftp的內容,這樣就能夠取出咱們想要的連接
            NodeList nodelist = parser.extractAllNodesThatMatch(new LinkStringFilter("ftp"));
            for (int i = 0; i < nodelist.size(); i++) {
                LinkTag tag = (LinkTag) nodelist.elementAt(i);
                moiveDownLoadUrl = tag.getLink();
            }
        } catch (ParserException e) {
            e.printStackTrace();
        }
        return moiveDownLoadUrl;
    }

 

 二、獲取一個分頁裏的全部電影介紹頁面

 

/**
     * 
     * 獲取一個分頁裏的全部電影介紹頁面
     */
    public static List getAllMoiveUrlFromOneList(String pageListUrl) {
        // 將連接地址以集合的形式返回出去
        List<String> allMoiveUrl = new ArrayList<String>();
        try {
            Parser parser = new Parser(pageListUrl);
            // 這裏咱們使用屬性過濾器,能夠幫助咱們過濾一些屬性特殊或者屬性裏面值惟一的標籤
            NodeList nodelist = parser.extractAllNodesThatMatch(new HasAttributeFilter("class", "ulink"));
            for (int i = 0; i < nodelist.size(); i++) {
                LinkTag tag = (LinkTag) nodelist.elementAt(i);
                // 將取出的分頁連接拼接一下,放入到集合中來。
                allMoiveUrl.add("http://www.ygdy8.net" + tag.getLink());
            }
        } catch (ParserException e) {
            e.printStackTrace();
        }
        return allMoiveUrl;
    }

 

 三、獲取電影網裏面的全部分頁

/**
     *獲取電影網裏面的全部的分頁 
     */
    public static List getAllPage() {
        // 將連接地址以集合的形式返回出去
        List<String> allPage = new ArrayList<String>();
        try {
            Parser parser = new Parser("http://www.ygdy8.net/html/gndy/jddy/index.html");
                                      //http://www.ygdy8.net/html/gndy/jddy/index.html
            NodeList nodelist = parser.extractAllNodesThatMatch(new TagNameFilter("option"))
                    .extractAllNodesThatMatch(new HasAttributeFilter("value"));
            for (int i = 0; i < nodelist.size(); i++) {
                OptionTag tag = (OptionTag) nodelist.elementAt(i);
                if (tag.getAttribute("value").contains("list")) {
                    allPage.add("http://www.ygdy8.net/html/gndy/jddy/" + tag.getAttribute("value"));
                }
            }
        } catch (ParserException e) {
            e.printStackTrace();
        }
        return allPage;
    }

 

 

OK。至此,咱們就能夠獲得所有分頁的連接,各個電影介紹頁面的連接,介紹頁面裏的下載連接。接下來咱們要作的就是將這三個方法整合起來,得到所有電影的下載連接。

/**
     * 
     * 功能:保存數據到文件中
     * @param content 要保存的內容
     * @param fileName 目標文件名(路徑)
     * 
     */
    public static boolean writeContentToFileTwo(String content, String fileName) {
        boolean flag = false;
        try {
            PrintWriter pw = new PrintWriter(new OutputStreamWriter(new FileOutputStream(fileName, true)));
            pw.println();
            pw.print(content);
            pw.flush();
            pw.close();
            flag = true;
        } catch (FileNotFoundException e) {
            e.printStackTrace();
            flag = false;
        }
        return flag;
    }

    public static List getAllMoive() {
        List<String> movieList = new ArrayList<String>();
        // 獲得所有的分頁連接
        List<String> allPage = getAllPage();
        for (Iterator iterator = allPage.iterator(); iterator.hasNext();) {
            String pageListUrl = (String) iterator.next();
            List<String> allMoiveUrl = getAllMoiveUrlFromOneList(pageListUrl);
            for (Iterator iterator2 = allMoiveUrl.iterator(); iterator2.hasNext();) {
                String moiveIntroUrl = (String) iterator2.next();
                String moiveDownLoadUrl = getMoiveDownloadUrl(moiveIntroUrl);
                writeContentToFileTwo(moiveDownLoadUrl, "a.txt");
                movieList.add(moiveDownLoadUrl);
            }
        }
        return movieList;
    }
    public static void main(String[] args) {
        getAllMoive();
    }

 

效果以下圖所示:

 

好啦,大功告成啦!是否是很簡答呢。

其實這個工具的使用是不復雜的,流程也很清晰,問題的關鍵在於如何在一個龐大的html頁面中獲取你想要的內容,能夠多一點查看各類的節點過濾器,它能夠幫助咱們選出咱們想要的內容,每次在爬取網頁以前咱們都要花大量時間去分析一個網頁,找到咱們想要的內容,不能多也不能少,這我以爲纔是爬蟲的使用的重點。

若是您對本文有什麼異議或者發現有什麼問題,歡迎留言,發表您的見解和觀點。

附上項目源碼和所有電影下載連接的excelhttps://git.oschina.net/AuSiang/myBug/attach_files

相關文章
相關標籤/搜索