package com.java.net;
import java.io.IOException;
import java.io.InputStream;
import java.io.RandomAccessFile;
import java.net.URL;
import java.net.URLConnection;
class Download extends Thread{
//定義字節數組(取水的竹筒)的長度
private final int BUFF_LEN = 32;
//定義下載的起始點
private long start;
//定義下載的結束點
private long end;
//下載資源對應的輸入流
private InputStream is;
//將下載的字節輸出到raf中
private RandomAccessFile raf;
public Download() {
}
public Download(long start, long end, InputStream is, RandomAccessFile raf) {
System.out.println(start + "---------->" + end);
this.start = start;
this.end = end;
this.is = is;
this.raf = raf;
}
@Override
public void run() {
try {
is.skip(start);
raf.seek(start);
//定義讀取輸入流內容的緩存數組(竹筒)
byte[] buff = new byte[BUFF_LEN];
//本線程負責下載資源的大小
long contentLen = end - start;
//定義最多需要讀取幾次就可以完成本線程下載
long times = contentLen / BUFF_LEN + 4;
//實際讀取的字節
int hasRead = 0;
for(int i=0; i<times; i++){
hasRead = is.read(buff);
if(hasRead < 0){
break;
}
raf.write(buff, 0, hasRead);
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if(is != null) is.close();
if(raf != null) raf.close();
} catch (Exception e2) {
e2.printStackTrace();
}
}
}
}
public class MutilDown {
public static void main(String[] args) {
final int DOWN_THREAD_NUM = 4;
final String OUT_FILE_NAME = "e:/down.jpg";
InputStream[] isArr = new InputStream[DOWN_THREAD_NUM];
RandomAccessFile[] outArr = new RandomAccessFile[DOWN_THREAD_NUM];
try {
URL url = new URL("http://www.blueidea.com/articleimg/2006/08/3912/images/plant4.jpg");
//依次URL打開一個輸入流
isArr[0] = url.openStream();
long fileLen = getFileLength(url);
System.out.println("網絡資源的大小:" + fileLen);
outArr[0] = new RandomAccessFile(OUT_FILE_NAME, "rw");
for(int i=0; i<fileLen; i++){
outArr[0].write(0);
}
long numPerThred = fileLen / DOWN_THREAD_NUM;
//整個下載資源整除後剩下的餘數
long left = fileLen % DOWN_THREAD_NUM;
for(int i=0; i<DOWN_THREAD_NUM; i++){
//爲每條線程打開一條輸入流,一個RandomAccessFile對象
//讓每個線程分別下載文件的不同部分
if(i != 0){
//以URL打開多個輸入流
isArr[i] = url.openStream();
outArr[i] = new RandomAccessFile(OUT_FILE_NAME, "rw");
}
//分別啓動多個線程來下載網絡資源
if( i == DOWN_THREAD_NUM - 1){
//最後一個線程下載指定numPerThred + left個字節
new Download(i * numPerThred, (i + 1) * numPerThred + left, isArr[i],
outArr[i]).start();
}else{
//每個線程負責下載一定的numPerThred個字節
new Download(i * numPerThred, (i + 1) * numPerThred, isArr[i], outArr[i]).start();
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
//定義獲取指定網絡資源的方法
public static long getFileLength(URL url) throws IOException{
long length = 0;
//打開URL對應的URLConnection
URLConnection con = url.openConnection();
long size = con.getContentLength();
length = size;
return length;
}
}
Java多線程下載代碼
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.