java爬蟲-妹子圖


一,分析

1.選擇入口

​ 打開 https://www.mzitu.com/ 主頁,我們發現主頁有200+頁圖片,我們如果從首頁入手,這里可能不是全部圖片。這里我們打開每日更新 https://www.mzitu.com/all/ ,從url上看這應該是所有的圖片了,但是從網頁上有個早期圖片 的超鏈接 https://www.mzitu.com/old/ ,我們得知這兩個url包含了所有的圖片了。

2. 技術選型

​ 作為爬蟲學習階段,我們的目標應該是不顧一切把想要的資源爬到手,至於使用java或者使用python,使用Linux還是Windows就有些無關緊要。

​ 技術選型:HttpClient+Jsoup

3.深入分析

思路:

  1. 根據 https://www.mzitu.com/all/ 獲取所有的album
    • 使用HttpClient獲取當前頁面的html(字符串格式)
    • 使用Jsoup解析html,獲取每個album的url
  2. 獲取每個album里的圖片
    • 根據每個album的url,獲取每頁的html
    • 使用Jsoup解析html,獲取圖片src屬性值
    • 下載

第一步

​ 獲取所有的album的url

​ 獲取圖片里的src,這里我們不禁想到怎么實現下一頁呢?我們點擊下一頁按鈕發現了規律

下一頁

​ 至此,我們就可以獲取所有的圖片src了,但是還有個問題,如果一個album只有51張圖片,那我什么時候判斷結束?也就是https://www.mzitu.com/224497/52 會出現什么?

判斷終止條件

​ 會出現404,找不到頁面,這里就應該跳出去遍歷別的相冊了,此時,大致思路和問題就解決了,現在就是coding時間了。

二、代碼

package com.my.crawler.util;


import org.apache.http.HttpEntity;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.apache.http.util.EntityUtils;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.util.UUID;



public class HttpUtils {

    public static PoolingHttpClientConnectionManager cm = null;

    static{
        cm = new PoolingHttpClientConnectionManager();
        cm.setMaxTotal(100); // 設置最大連接數
        cm.setDefaultMaxPerRoute(10); // 設置主機的最大連接數
    }

    // 目的:傳遞一個url(http的地址),返回對應地址下的HTML的文檔
    public static String getHtml(String url){
        CloseableHttpClient client = HttpClients.custom().setConnectionManager(cm).build();
        HttpGet httpGet = new HttpGet(url);
        /**設置參數*/
        httpGet.setConfig(setConfig());
        /*************************添加代碼*********************************/
        httpGet.setHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.104 Safari/537.36 Core/1.53.2595.400 QQBrowser/9.6.10872.400");
        httpGet.setHeader("Referer","https://www.mzitu.com/");
        /*************************添加代碼*********************************/
        CloseableHttpResponse response = null;
        // 封裝網站中的內容
        String html = "";
        try {
            response = client.execute(httpGet);
            // 響應成功(200)
            if(response.getStatusLine().getStatusCode()==200){
                HttpEntity httpEntity = response.getEntity();
                html = EntityUtils.toString(httpEntity,"UTF-8");
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if(response!=null){
                try {
                    response.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            // 使用連接池不需要關閉
        }
        return html;
    }

    public static String getImg(String url){
        CloseableHttpClient client = HttpClients.custom().setConnectionManager(cm).build();
        HttpGet httpGet = new HttpGet(url);
        /**設置參數*/
        httpGet.setConfig(setConfig());
        /*************************添加代碼*********************************/

        httpGet.setHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.104 Safari/537.36 Core/1.53.2595.400 QQBrowser/9.6.10872.400");
        httpGet.setHeader("Referer","https://www.mzitu.com/");
        /*************************添加代碼*********************************/
        CloseableHttpResponse response = null;
        // 圖片名稱
        String img = "";
        try {
            response = client.execute(httpGet);
            // 響應成功(200)
            if(response.getStatusLine().getStatusCode()==200){
                HttpEntity httpEntity = response.getEntity();
                String ext = url.substring(url.lastIndexOf("."));
                img = UUID.randomUUID().toString()+ext;
                OutputStream outputStream = new FileOutputStream(new File("D:\\images\\"+img));
                httpEntity.writeTo(outputStream);
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if(response!=null){
                try {
                    response.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            // 使用連接池不需要關閉
        }
        return img;
    }

    public static String getImg(String url,String dir){
        CloseableHttpClient client = HttpClients.custom().setConnectionManager(cm).build();
        HttpGet httpGet = new HttpGet(url);
        /**設置參數*/
        httpGet.setConfig(setConfig());
        /*************************添加代碼*********************************/

        httpGet.setHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.104 Safari/537.36 Core/1.53.2595.400 QQBrowser/9.6.10872.400");
        httpGet.setHeader("Referer","https://www.mzitu.com/");
        /*************************添加代碼*********************************/
        CloseableHttpResponse response = null;
        // 圖片名稱
        String img = "";
        try {
            response = client.execute(httpGet);
            // 響應成功(200)
            if(response.getStatusLine().getStatusCode()==200){
                HttpEntity httpEntity = response.getEntity();
                String ext = url.substring(url.lastIndexOf("."));
                img = UUID.randomUUID().toString()+ext;
                // 先建文件夾
                File file = new File("D:\\images\\" + dir+"\\");
                if (!file.exists()){
                    file.mkdirs();
                }
                OutputStream outputStream = new FileOutputStream(new File("D:\\images\\"+dir+"\\"+img));
                httpEntity.writeTo(outputStream);
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if(response!=null){
                try {
                    response.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
            // 使用連接池不需要關閉
        }
        return img;
    }

    // 用來設置HttpClient的參數
    private static RequestConfig setConfig() {
        RequestConfig config = RequestConfig.custom()
                .setConnectTimeout(1000) // 創建連接的超時時間,單位毫秒
                .setConnectionRequestTimeout(1000) // 從連接池中創建連接的超時時間,單位毫秒
                .setSocketTimeout(10*1000) // 數據傳輸的超時時間,單位毫秒;啟動如果你的網絡慢或者你訪問的是國外的url,有可能出現超時異常
                .build();
        return config;
    }

    // 測試
    public static void main(String[] args) {
        // 測試getHtml
        String html = getHtml("https://www.mzitu.com/224497/52");
        System.out.println(html.equals(""));
    }
}

public class MzituTask {

    public static void main(String[] args) {
        // 初始化url
        String url = "https://www.mzitu.com/all/";
        // 獲取所有頁面
        String html = HttpUtils.getHtml(url);
        // 解析url
        Document document = Jsoup.parse(html);
        Elements elements = document.select("[target=_blank]");
        //System.out.println(elements.text());
        for (Element element : elements) {
            String albumUrl = element.attr("href");
            // 遍歷解析每一個URL,得到每一個相冊的html
            String eachAlblumHtml = HttpUtils.getHtml(albumUrl);   
            // 根據第一頁找剩下的URL
            int page = 1;
            while (true) {
                try {
                    String singleUrl = albumUrl+"/"+page;
                    String singleHtml = HttpUtils.getHtml(singleUrl);
                    System.out.println(singleHtml);
                    if (singleHtml.equals("")) {
                        break;
                    }
                    Document singleDoc = Jsoup.parse(singleHtml);
                    // 找到想要的照片信息
                    Elements imgElements = singleDoc.select(".main-image img");
                    if (imgElements.size() > 0) {
                        String imgSrc = imgElements.get(0).attr("src");
                        HttpUtils.getImg(imgSrc,element.text());
                        // 睡1s
                        Thread.sleep(1000);
                    }
                    page++;
                } catch (Exception e) {
                    e.printStackTrace();
                    continue;
                }
            }
        }
    }
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM