欧美性猛交xxxx免费看_牛牛在线视频国产免费_天堂草原电视剧在线观看免费_国产粉嫩高清在线观看_国产欧美日本亚洲精品一5区

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

汽車玩家 ? 來源: 黑馬程序員 ? 作者: 黑馬程序員 ? 2020-05-05 21:25 ? 次閱讀

在我們調(diào)試爬蟲程序的時(shí)候,單線程爬蟲沒什么問題,但是當(dāng)我們?cè)诰€上環(huán)境使用單線程爬蟲程序去采集網(wǎng)頁時(shí),單線程就暴露出了兩個(gè)致命的問題:

采集效率特別慢,單線程之間都是串行的,下一個(gè)執(zhí)行動(dòng)作需要等上一個(gè)執(zhí)行完才能執(zhí)行

對(duì)服務(wù)器的CUP等利用率不高,想想我們的服務(wù)器都是 8核16G,32G 的只跑一個(gè)線程會(huì)不會(huì)太浪費(fèi)啦

線上環(huán)境不可能像我們本地測(cè)試一樣,不在乎采集效率,只要能正確提取結(jié)果就行。在這個(gè)時(shí)間就是金錢的年代,不可能給你時(shí)間去慢慢的采集,所以單線程爬蟲程序是行不通的,我們需要將單線程改成多線程的模式,來提升采集效率和提高計(jì)算機(jī)利用率。

多線程的爬蟲程序設(shè)計(jì)比單線程就要復(fù)雜很多,但是與其他業(yè)務(wù)在高并發(fā)下要保證數(shù)據(jù)安全又不同,多線程爬蟲在數(shù)據(jù)安全上到要求不是那么的高,因?yàn)槊總€(gè)頁面都可以被看作是一個(gè)獨(dú)立體。要做好多線程爬蟲就必須做好兩點(diǎn):第一點(diǎn)就是統(tǒng)一的待采集 URL 維護(hù),第二點(diǎn)就是 URL 的去重,下面我們簡(jiǎn)單的來聊一聊這兩點(diǎn)。

維護(hù)待采集的 URL

多線程爬蟲程序就不能像單線程那樣,每個(gè)線程獨(dú)自維護(hù)這自己的待采集 URL,如果這樣的話,那么每個(gè)線程采集的網(wǎng)頁將是一樣的,你這就不是多線程采集啦,你這是將一個(gè)頁面采集的多次。基于這個(gè)原因我們就需要將待采集的 URL 統(tǒng)一維護(hù),每個(gè)線程從統(tǒng)一 URL 維護(hù)處領(lǐng)取采集 URL ,完成采集任務(wù),如果在頁面上發(fā)現(xiàn)新的 URL 鏈接則添加到 統(tǒng)一 URL 維護(hù)的容器中。下面是幾種適合用作統(tǒng)一 URL 維護(hù)的容器:

JDK 的安全隊(duì)列,例如 LinkedBlockingQueue

高性能的 NoSQL,比如 Redis、Mongodb

MQ 消息中間件

URL 的去重

URL 的去重也是多線程采集的關(guān)鍵一步,因?yàn)槿绻蝗ブ氐脑挘敲次覀儗⒉杉酱罅恐貜?fù)的 URL,這樣并沒有提升我們的采集效率,比如一個(gè)分頁的新聞列表,我們?cè)诓杉谝豁摰臅r(shí)候可以得到 2、3、4、5 頁的鏈接,在采集第二頁的時(shí)候又會(huì)得到 1、3、4、5 頁的鏈接,待采集的 URL 隊(duì)列中將存在大量的列表頁鏈接,這樣就會(huì)重復(fù)采集甚至進(jìn)入到一個(gè)死循環(huán)當(dāng)中,所以就需要 URL 去重。URL 去重的方法就非常多啦,下面是幾種常用的 URL 去重方式:

將 URL 保存到數(shù)據(jù)庫進(jìn)行去重,比如 redis、MongoDB

將 URL 放到哈希表中去重,例如 hashset

將 URL 經(jīng)過 MD5 之后保存到哈希表中去重,相比于上面一種,能夠節(jié)約空間

使用 布隆過濾器(Bloom Filter)去重,這種方式能夠節(jié)約大量的空間,就是不那么準(zhǔn)確。

關(guān)于多線程爬蟲的兩個(gè)核心知識(shí)點(diǎn)我們都知道啦,下面我畫了一個(gè)簡(jiǎn)單的多線程爬蟲架構(gòu)圖,如下圖所示:

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

多線程爬蟲架構(gòu)圖

上面我們主要了解了多線程爬蟲的架構(gòu)設(shè)計(jì),接下來我們不妨來試試 Java 多線程爬蟲,我們以采集虎撲新聞為例來實(shí)戰(zhàn)一下 Java 多線程爬蟲,Java 多線程爬蟲中設(shè)計(jì)到了 待采集 URL 的維護(hù)和 URL 去重,由于我們這里只是演示,所以我們就使用 JDK 內(nèi)置的容器來完成,我們使用 LinkedBlockingQueue 作為待采集 URL 維護(hù)容器,HashSet 作為 URL 去重容器。下面是 Java 多線程爬蟲核心代碼,詳細(xì)代碼以上傳 GitHub,地址在文末:

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

我們用 5 個(gè)線程去采集虎撲新聞列表頁看看效果如果?運(yùn)行該程序,得到如下結(jié)果:

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

多線程采集結(jié)果

結(jié)果中可以看出,我們啟動(dòng)了 5 個(gè)線程采集了 61 頁頁面,一共耗時(shí) 2 秒鐘,可以說效果還是不錯(cuò)的,我們來跟單線程對(duì)比一下,看看差距有多大?我們將線程數(shù)設(shè)置為 1 ,再次啟動(dòng)程序,得到如下結(jié)果:

實(shí)現(xiàn)Java多線程爬蟲的兩點(diǎn)

單線程運(yùn)行結(jié)果

可以看出單線程采集虎撲 61 條新聞花費(fèi)了 7 秒鐘,耗時(shí)差不多是多線程的 4 倍,你想想這可只是 61 個(gè)頁面,頁面更多的話,差距會(huì)越來越大,所以多線程爬蟲效率還是非常高的。

分布式爬蟲架構(gòu)

分布式爬蟲架構(gòu)是一個(gè)大型采集程序才需要使用的架構(gòu),一般情況下使用單機(jī)多線程就可以解決業(yè)務(wù)需求,反正我是沒有分布式爬蟲項(xiàng)目的經(jīng)驗(yàn),所以這一塊我也沒什么可以講的,但是我們作為技術(shù)人員,我們需要對(duì)技術(shù)保存熱度,雖然不用,但是了解了解也無妨,我查閱了不少資料得出了如下結(jié)論:

分布式爬蟲架構(gòu)跟我們多線程爬蟲架構(gòu)在思路上來說是一樣的,我們只需要在多線程的基礎(chǔ)上稍加改進(jìn)就可以變成一個(gè)簡(jiǎn)單的分布式爬蟲架構(gòu)。因?yàn)榉植际脚老x架構(gòu)中爬蟲程序部署在不同的機(jī)器上,所以我們待采集的 URL 和 采集過的 URL 就不能存放在爬蟲程序機(jī)器的內(nèi)存中啦,我們需要將它統(tǒng)一在某臺(tái)機(jī)器上維護(hù)啦,比如存放在 Redis 或者 MongoDB 中,每臺(tái)機(jī)器都從這上面獲取采集鏈接,而不是從 LinkedBlockingQueue 這樣的內(nèi)存隊(duì)列中取鏈接啦,這樣一個(gè)簡(jiǎn)單的分布式爬蟲架構(gòu)就出現(xiàn)了,當(dāng)然這里面還會(huì)有很多細(xì)節(jié)問題,因?yàn)槲覜]有分布式架構(gòu)的經(jīng)驗(yàn)

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • JAVA
    +關(guān)注

    關(guān)注

    19

    文章

    2977

    瀏覽量

    105231
  • 多線程
    +關(guān)注

    關(guān)注

    0

    文章

    278

    瀏覽量

    20077
收藏 人收藏

    評(píng)論

    相關(guān)推薦

    socket 多線程編程實(shí)現(xiàn)方法

    在現(xiàn)代網(wǎng)絡(luò)編程中,多線程技術(shù)被廣泛應(yīng)用于提高服務(wù)器的并發(fā)處理能力。Socket編程是網(wǎng)絡(luò)通信的基礎(chǔ),而將多線程技術(shù)應(yīng)用于Socket編程,可以顯著提升服務(wù)器的性能。 多線程編程的基本概念 多線
    的頭像 發(fā)表于 11-12 14:16 ?495次閱讀

    Python中多線程和多進(jìn)程的區(qū)別

    Python作為一種高級(jí)編程語言,提供了多種并發(fā)編程的方式,其中多線程與多進(jìn)程是最常見的種方式之一。在本文中,我們將探討Python中多線程與多進(jìn)程的概念、區(qū)別以及如何使用線程池與進(jìn)
    的頭像 發(fā)表于 10-23 11:48 ?513次閱讀
    Python中<b class='flag-5'>多線程</b>和多進(jìn)程的區(qū)別

    INA818輸入直接取電阻R2兩點(diǎn)電壓,兩點(diǎn)壓差范圍約為2mV~200mV,是否可以直接作為INA818的輸入呢?

    : 1.INA818采用5V單電源供電,REF引腳由DAC芯片給出2.5V的參考電壓。 2.INA818的輸入直接取電阻R2兩點(diǎn)電壓,兩點(diǎn)壓差范圍約為2mV~200mV,這是否可以直接作為INA818的輸入呢
    發(fā)表于 08-09 06:29

    ESP32會(huì)不會(huì)有多線程問題,需要加鎖嗎?

    ESP32會(huì)不會(huì)有多線程問題,需要加鎖嗎
    發(fā)表于 07-19 08:05

    多線程設(shè)計(jì)模式到對(duì) CompletableFuture 的應(yīng)用

    最近在開發(fā) 延保服務(wù) 頻道頁時(shí),為了提高查詢效率,使用到了多線程技術(shù)。為了對(duì)多線程方案設(shè)計(jì)有更加充分的了解,在業(yè)余時(shí)間讀完了《圖解 Java 多線程設(shè)計(jì)模式》這本書,覺得收獲良多。本篇
    的頭像 發(fā)表于 06-26 14:18 ?445次閱讀
    從<b class='flag-5'>多線程</b>設(shè)計(jì)模式到對(duì) CompletableFuture 的應(yīng)用

    探索虛擬線程:原理與實(shí)現(xiàn)

    虛擬線程的引入與優(yōu)勢(shì) 在Loom項(xiàng)目之前,Java虛擬機(jī)(JVM)中的線程是通過java.lang.Thread類型來實(shí)現(xiàn)的,這些
    的頭像 發(fā)表于 06-24 11:35 ?375次閱讀
    探索虛擬<b class='flag-5'>線程</b>:原理與<b class='flag-5'>實(shí)現(xiàn)</b>

    動(dòng)態(tài)線程池思想學(xué)習(xí)及實(shí)踐

    ://www.javadoop.com/post/java-thread-pool? 引言 在后臺(tái)項(xiàng)目開發(fā)過程中,我們常常借助線程池來實(shí)現(xiàn)多線程任務(wù),以此提升系統(tǒng)的吞吐率和響應(yīng)性;而
    的頭像 發(fā)表于 06-13 15:43 ?1256次閱讀
    動(dòng)態(tài)<b class='flag-5'>線程</b>池思想學(xué)習(xí)及實(shí)踐

    bootloader開多線程做引導(dǎo)程序,跳app初始化后直接進(jìn)hardfualt,為什么?

    如標(biāo)題,想做一個(gè)遠(yuǎn)程升級(jí)的項(xiàng)目,bootloader引導(dǎo)區(qū)域和app都是開多線程跑的,就是自己寫了個(gè)小的任務(wù)調(diào)度器,沒什么功能主要是想讓程序快速的響應(yīng),延時(shí)不會(huì)對(duì)其他程序造成堵塞,程序測(cè)試
    發(fā)表于 04-18 06:07

    鴻蒙OS開發(fā)實(shí)例:【ArkTS類庫多線程CPU密集型任務(wù)TaskPool】

    CPU密集型任務(wù)是指需要占用系統(tǒng)資源處理大量計(jì)算能力的任務(wù),需要長(zhǎng)時(shí)間運(yùn)行,這段時(shí)間會(huì)阻塞線程其它事件的處理,不適宜放在主線程進(jìn)行。例如圖像處理、視頻編碼、數(shù)據(jù)分析等。 基于多線程并發(fā)機(jī)制處理CPU密集型任務(wù)可以提高CPU
    的頭像 發(fā)表于 04-01 22:25 ?917次閱讀
    鴻蒙OS開發(fā)實(shí)例:【ArkTS類庫<b class='flag-5'>多線程</b>CPU密集型任務(wù)TaskPool】

    鴻蒙APP開發(fā):【ArkTS類庫多線程】TaskPool和Worker的對(duì)比

    TaskPool(任務(wù)池)和Worker的作用是為應(yīng)用程序提供一個(gè)多線程的運(yùn)行環(huán)境,用于處理耗時(shí)的計(jì)算任務(wù)或其他密集型任務(wù)??梢杂行У乇苊膺@些任務(wù)阻塞主線程,從而最大化系統(tǒng)的利用率,降低整體資源消耗,并提高系統(tǒng)的整體性能。
    的頭像 發(fā)表于 03-26 22:09 ?722次閱讀
    鴻蒙APP開發(fā):【ArkTS類庫<b class='flag-5'>多線程</b>】TaskPool和Worker的對(duì)比

    鴻蒙原生應(yīng)用開發(fā)-ArkTS語言基礎(chǔ)類庫多線程TaskPool和Worker的對(duì)比(一)

    TaskPool(任務(wù)池)和Worker的作用是為應(yīng)用程序提供一個(gè)多線程的運(yùn)行環(huán)境,用于處理耗時(shí)的計(jì)算任務(wù)或其他密集型任務(wù)??梢杂行У乇苊膺@些任務(wù)阻塞主線程,從而最大化系統(tǒng)的利用率,降低整體資源消耗
    發(fā)表于 03-25 14:11

    鴻蒙原生應(yīng)用開發(fā)-ArkTS語言基礎(chǔ)類庫多線程I/O密集型任務(wù)開發(fā)

    使用異步并發(fā)可以解決單次I/O任務(wù)阻塞的問題,但是如果遇到I/O密集型任務(wù),同樣會(huì)阻塞線程中其它任務(wù)的執(zhí)行,這時(shí)需要使用多線程并發(fā)能力來進(jìn)行解決。 I/O密集型任務(wù)的性能重點(diǎn)通常不在于CPU的處理
    發(fā)表于 03-21 14:57

    java實(shí)現(xiàn)多線程的幾種方式

    Java實(shí)現(xiàn)多線程的幾種方式 多線程是指程序中包含了個(gè)或以上的線程,每個(gè)
    的頭像 發(fā)表于 03-14 16:55 ?793次閱讀

    AT socket可以多線程調(diào)用嗎?

    請(qǐng)問AT socket 可以多線程調(diào)用嗎? 有互鎖機(jī)制嗎,還是要自己做互鎖。
    發(fā)表于 03-01 08:22

    linux多線程編程實(shí)例

    linux線程
    的頭像 發(fā)表于 02-15 21:16 ?536次閱讀
    linux<b class='flag-5'>多線程</b>編程實(shí)例