多线程下载

<span style="font-size:18px;">
</span>
<span style="font-size:18px;">
</span>
<span style="font-size:18px;">下载:</span>
<span style="font-size:18px;">1、用Http去请求服务器</span>
<span style="font-size:18px;">2、获取文件的大小</span>
<span style="font-size:18px;">3、创建一个空的文件夹与服务器三文件等大小</span>
<span style="font-size:18px;">4、根据线程的总数,计算每一个线程需要下载的区间段</span>
<span style="font-size:18px;">5、每个线程下载以后写入到本地文件的指定单位位置</span>
<span style="font-size:18px;">
</span>
<span style="font-size:18px;">
</span>
<span style="font-size:18px;">package com.hx.zy.download;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.RandomAccessFile;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;

import javax.tools.FileObject;

import com.hx.zy.constant.Contant;

public class TestDownload 
{
	//public static int threadCount = 3;
	public static int blockSize = 0;

	public static void main(String[] args) throws Exception 
	{
		URL url = new URL("http://localhost:8080/download/cc.zip");
		
		HttpURLConnection conn = (HttpURLConnection) url.openConnection();
		conn.setRequestMethod("GET");
		conn.setReadTimeout(10000);
		
		long length = conn.getContentLength();
		
		conn.connect(); //连接
		File file = new File("cc.zip");
		
		RandomAccessFile randomFile = new RandomAccessFile(file,"rwd");
		randomFile.setLength(length);
		
		//每一个线程他需要下载的大小
		System.out.println("总大小:" + length);
		blockSize = (int) (length / Contant.threadCount);
		System.out.println("每一个线程下载的大小:" + blockSize);
		long start = 1;
		long end = 0;
		for(int i=1; i < (Contant.threadCount+1); i++)
		{
			
			//1 》》 0 - 46354938 123456
			// 2 >> 46354939 -(46354939 + 46354938)
			//3 》》 
			start = blockSize * (i -1);
			end = blockSize*i -1;
			if(i == Contant.threadCount)
			{
				end = length;
			}
			System.out.println("第" + i + "个线程下载的区间:" + start + " - " + end);
			new downloadThread(file, i, start, end).start();
		}
		
		conn.disconnect();
	}
}

class downloadThread extends Thread
{
	private File path; //本地磁盘的地址
	private String url = "http://localhost:8080/download/cc.zip" ; //HTTP请求的地址
	private Integer threadID; //当前是第几个线程
	private long start; //该线程下载的起始位置
	private long end; //该线程的结束位置
	
	public downloadThread(File path, Integer threadID, long start,
			long end) {
		this.path = path;
		this.threadID = threadID;
		this.start = start;
		this.end = end;
		
	}

	@Override
	public void run() 
	{
		try {
			System.out.println(threadID + "开启读取");
			File contextFile = new File(threadID +".txt");
			if(!contextFile.exists())
			{
				contextFile.createNewFile();
			}
			
			//读取断线信息里面的数据来重新的指定从哪里开始写
			BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream(contextFile)));
			String info = reader.readLine();
			if(null != info && info.length() > 0)
			{
				start = start + Integer.parseInt(info);
			}
			
			System.out.println("start........=" + start);
			URL uri = new URL(url);
			HttpURLConnection conn = (HttpURLConnection) uri.openConnection();
			conn.setRequestProperty("Range", "bytes="+start +"-" + end);
			conn.setReadTimeout(50000);
			conn.setConnectTimeout(50000);
			
			conn.connect();
			
			//让http请求只请求一个片段
			System.out.println("bytes="+start +"-" + end);
			
			//判断一下是否为200?
			int status = conn.getResponseCode();
			
			if(status / 100 == 2)
			{
				int total = 0; //总共下载的字节数
				//FileOutputStream out = new FileOutputStream(new File(threadID +".txt")); 不靠谱了
				RandomAccessFile random = new RandomAccessFile(path, "rw");
				
				random.seek(start);
				InputStream in = conn.getInputStream();
				byte[] buffer = new byte[1024];
				int len = 0;
				
				while((len = in.read(buffer)) != -1)
				{
					RandomAccessFile duandian = new RandomAccessFile(contextFile, "rwd");
					random.write(buffer, 0, len);
					total += len;
					duandian.write(String.valueOf(total).getBytes());
					duandian.close();
				}
				in.close();
				random.close();
			}
			conn.disconnect();
			System.out.println(threadID + "读取完成");
		} catch (MalformedURLException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}finally
		{
			synchronized (TestDownload.class)
			{
				Contant.threadCount --;
				System.out.println("Contant.threadCount = " + Contant.threadCount);
				if(Contant.threadCount == 0)
				{
					for(int i=1; i < 4; i++)
					{
						File contextFile = new File(i +".txt");
						System.out.println(contextFile.delete() +"   ccc");
					}
				}
			}
		}
		
	}
}</span>

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值