/**
- 多线程下载实现类
- 1.建立成员变量,描述多线程下载需要的参数
- 2.通过统一资源管理器URL,和要下载的资源建立连接
-
设置参数信息
- 3.获取网络资源的输入流,得到数据
- 4.创建文件存放的file对象,
- 5.具体文件下载的实现
- 6.关闭流
*/
public class DownLoad extends Thread{
private int startIndex;//开始位置
private int endIndex;//结束位置
private int threadId;//线程编号
public DownLoad(int startIndex, int endIndex, int threadId) {
super();
this.startIndex = startIndex;
this.endIndex = endIndex;
this.threadId = threadId;
}
@Override
public void run() {
long start = System.currentTimeMillis();
try {
// 2.通过统一资源管理器URL,和要下载的资源建立连接
URL url = new URL(DownLoadTest.path);
//获取联系
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
// 设置参数信息
conn.setRequestMethod(“GET”);//get方式请求
conn.setConnectTimeout(5000);//连接超时
conn.setReadTimeout(5000);//读取超时
conn.addRequestProperty(“Range”, “bytes=”+startIndex+"-"+endIndex);//设置读取的范围,固定格式的
System.out.println(this.currentThread().getName()+" “+threadId+”:下载的文件范围:"+startIndex+"-"+endIndex);
if(conn.getResponseCode()206) {//部分数据ok
// 3.获取网络资源的输入流,得到数据
InputStream is = conn.getInputStream();
// 4.创建文件存放的file对象,
File distFile = new File(“D:\upload\xxx.zip”);
//创建读写随机流
RandomAccessFile raf = new RandomAccessFile(distFile, “rwd”);
raf.seek(startIndex);//指定写入的开始位置
// 5.具体文件下载的实现
byte[] buf =new byte[8192];
int len = 0;
while((len= is.read(buf))!=-1) {
raf.write(buf, 0, len);
}
// 6.关闭流
raf.close();
is.close();
//线程完成次数加1
DownLoadTest.okThread++;
//加锁
synchronized (DownLoadTest.path) {
System.out.println(this.currentThread().getName()+" “+threadId+”:线程下载完成!"+DownLoadTest.okThread);
//判断如果线程完成数量达到了线程数,重置成0
if(DownLoadTest.okThreadDownLoadTest.threadCount) {
DownLoadTest.okThread=0;
}
}
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
long end = System.currentTimeMillis();
System.out.println(this.currentThread().getName()+“下载子线程运行的时间:”+(end-start));
}
}
/**
- 下载测试类
- @author wyl
*通过统一资源管理器,连接网络资源,获取文件的大小
*调用多线程实现具体 的下载
*
*/
public class DownLoadTest {
static String path = "https://cdn.mysql.com//Downloads/MySQL-8.0/mysql-8.0.25-winx64.zip";
static int threadCount=3;//线程的数量
static int okThread=0;//已经下载完成的线程数量
public static void main(String[] args) throws Exception {
long start = System.currentTimeMillis();
// 通过统一资源管理器URL,和要下载的资源建立连接
URL url = new URL(DownLoadTest.path);
//获取联系
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
// 设置参数信息
conn.setRequestMethod(“GET”);//get方式请求
conn.setConnectTimeout(5000);//连接超时
conn.setReadTimeout(5000);//读取超时
if(conn.getResponseCode()==200) {
int count = conn.getContentLength();//文件的长度
int size = count / threadCount;//每个线程需要下载的文件长度
System.out.println(count);
System.out.println(size);
for (int i = 0; i < threadCount; i++) {
int startIndex = size*i;
int endIndex = size*(i+1);
DownLoad thread= new DownLoad(startIndex, endIndex, i);
thread.start();
}
}
long end = System.currentTimeMillis();
System.out.println("主线的时间:"+(end-start));
}
}