日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

多线程系列之学习多线程下载的基本原理和基本用法(1)

發(fā)布時間:2025/3/20 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 多线程系列之学习多线程下载的基本原理和基本用法(1) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

多線程下載在我們生活中非常常見,比如迅雷就是我們常用的多線程的下載工具,當然還有斷點續(xù)傳,斷點續(xù)傳我們在下一節(jié)來講,android手機端下載文件時也可以用多線程下載,我們這里是在java中寫一個測試,其實android中的實現(xiàn)和java是一樣的,學(xué)會了java就知道怎么在android中實現(xiàn)了,廢話不多說了,怎么實現(xiàn)多線程和多線程的原理是什么樣的,現(xiàn)在我們來學(xué)習(xí)一下。
<!--more-->

多線程下載原理及步驟:

  • 在本地創(chuàng)建一個大小跟服務(wù)器文件相同大小的臨時文件。

  • 計算分配幾個線程去下載服務(wù)器上的資源,知道每個線程下載文件的位置。

  • 步驟二的具體方法和操作:

    文件的長度/3(線程的個數(shù))=每個線程下載文件的大小

    假設(shè)文件長度為10,則

    線程1:0-2

    線程2:3-5

    線程3:6-文件末尾

    每個線程下載的位置的計算方式:

    開始位置:

    (線程id - 1)* 每一塊的大小

    結(jié)束位置:

    (線程id * 每一塊大小)-1

  • 開啟多(3)個線程,每一個線程下載對應(yīng)位置的文件

  • 如果所有的線程都把自己的數(shù)據(jù)下載完畢了,服務(wù)器上的資源就被下載到本地了。

  • 在這里在介紹一個有關(guān)多線程下載的java中的相關(guān)類RandomAccessFile

    RandomAccessFile 隨機文件訪問類

    只有RandomAccessFile才有seek搜尋方法,而這個方法也只適用于文件。通過seek()方法指定位置,定位文件,即可以指定隨機寫文件的時候從哪個位置開始寫。利用這個類才能實現(xiàn)文件的多線程下載。

    基本原理和相關(guān)介紹如上,就這些,現(xiàn)在我們看看代碼:

    package net.loonggg.test;import java.io.InputStream; import java.io.RandomAccessFile; import java.net.HttpURLConnection; import java.net.URL;/**** 多線程下載* * @author loonggg* */ public class MutilDownloader {// 開啟的線程的個數(shù)public static final int THREAD_COUNT = 3;public static void main(String[] args) throws Exception {String path = "http://down.360safe.com/yunpan/360wangpan_setup.exe";// 連接服務(wù)器,獲取一個文件,獲取文件的長度,在本地創(chuàng)建一個大小跟服務(wù)器文件大小一樣的臨時文件URL url = new URL(path);HttpURLConnection conn = (HttpURLConnection) url.openConnection();// 設(shè)置網(wǎng)絡(luò)請求超時時間conn.setConnectTimeout(5000);// 設(shè)置請求方式conn.setRequestMethod("GET");int code = conn.getResponseCode();if (code == 200) {// 服務(wù)器返回的數(shù)據(jù)的長度,實際就是文件的長度int length = conn.getContentLength();System.out.println("----文件總長度----" + length);// 在客戶端本地創(chuàng)建出來一個大小跟服務(wù)器端文件一樣大小的臨時文件RandomAccessFile raf = new RandomAccessFile("yunpan.exe", "rwd");// 指定創(chuàng)建的這個文件的長度raf.setLength(length);// 關(guān)閉rafraf.close();// 假設(shè)是3個線程去下載資源// 平均每一個線程下載的文件的大小int blockSize = length / THREAD_COUNT;for (int threadId = 1; threadId <= THREAD_COUNT; threadId++) {// 計算每個線程下載的開始位置和結(jié)束位置int startIndex = (threadId - 1) * blockSize;int endIndex = threadId * blockSize - 1;if (threadId == THREAD_COUNT) {endIndex = length;}System.out.println("----threadId---" + threadId+ "--startIndex--" + startIndex + "--endIndex--"+ endIndex);// 開啟每一個線程new DownloadThread(path, threadId, startIndex, endIndex).start();}}}/*** 下載文件的子線程,每一個線程下載對應(yīng)位置的文件* * @author loonggg* */public static class DownloadThread extends Thread {private int threadId;private int startIndex;private int endIndex;private String path;/*** @param path* 下載文件在服務(wù)器上的路徑* @param threadId* 線程id* @param startIndex* 線程下載的開始位置* @param endIndex* 線程下載的結(jié)束位置*/public DownloadThread(String path, int threadId, int startIndex,int endIndex) {this.path = path;this.threadId = threadId;this.startIndex = startIndex;this.endIndex = endIndex;}@Overridepublic void run() {try {URL url = new URL(path);HttpURLConnection conn = (HttpURLConnection) url.openConnection();conn.setRequestMethod("GET");// 重要:請求服務(wù)器下載部分的文件 指定文件的位置conn.setRequestProperty("Range", "bytes=" + startIndex + "-"+ endIndex);conn.setConnectTimeout(5000);// 從服務(wù)器請求全部資源的狀態(tài)碼200 ok 如果從服務(wù)器請求部分資源的狀態(tài)碼206 okint code = conn.getResponseCode();System.out.println("---code---" + code);InputStream is = conn.getInputStream();// 已經(jīng)設(shè)置了請求的位置,返回的是當前位置對應(yīng)的文件的輸入流RandomAccessFile raf = new RandomAccessFile("yunpan.exe", "rwd");// 隨機寫文件的時候從哪個位置開始寫raf.seek(startIndex);// 定位文件int len = 0;byte[] buffer = new byte[1024];while ((len = is.read(buffer)) != -1) {raf.write(buffer, 0, len);}is.close();raf.close();System.out.println("線程" + threadId + ":下載完畢了!");} catch (Exception e) {e.printStackTrace();}}}}

    公眾號:非著名程序員(smart_android) 歡迎大家關(guān)注,每天一篇原創(chuàng)技術(shù)文章。

    總結(jié)

    以上是生活随笔為你收集整理的多线程系列之学习多线程下载的基本原理和基本用法(1)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。