说明:
SiteFileFetch.java 负责整个文件的抓取,控制内部线程(FileSplitterFetch类)。
FileSplitterFetch.java 负责部分文件的抓取。
FileAccess.java 负责文件的存储。
SiteInfoBean.java 要抓取的文件的信息,如文件保存的目录,名字,抓取文件的URL等。
Utility.java 工具类,放一些简单的方法。
*
**SiteFileFetch.java
*/
package NetFox;
import java.io.*;
import java.net.*;
public class SiteFileFetch extends Thread {
SiteInfoBean siteInfoBean = null; // 文件信息Bean
long[] nStartPos; // 开始位置
long[] nEndPos; // 结束位置
FileSplitterFetch[] fileSplitterFetch; // 子线程对象
long nFileLength; // 文件长度
boolean bFirst = true; // 是否第一次取文件
boolean bStop = false; // 停止标志
File tmpFile; // 文件下载的临时信息
DataOutputStream output; // 输出到文件的输出流
public SiteFileFetch(SiteInfoBean bean) throws IOException {
siteInfoBean = bean;
// tmpFile = File.createTempFile ("zhong","1111",new
// File(bean.getSFilePath()));
tmpFile = new File(bean.getSFilePath() + File.separator
+ bean.getSFileName() + ".info");
if (tmpFile.exists()) {
bFirst = false;
read_nPos();
} else {
nStartPos = new long[bean.getNSplitter()];
nEndPos = new long[bean.getNSplitter()];
}
}
public void run() {
// 获得文件长度
// 分割文件
// 实例FileSplitterFetch
// 启动FileSplitterFetch线程
// 等待子线程返回
try {
if (bFirst) {
nFileLength = getFileSize();
if (nFileLength == -1) {
System.err.println("File Length is not known!");
} else if (nFileLength == -2) {
System.err.println("File is not access!");
} else {
for (int i = 0; i < nStartPos.length; i++) {
nStartPos[i] = (long) (i * (nFileLength / nStartPos.length));
}
for (int i = 0; i < nEndPos.length - 1; i++) {
nEndPos[i] = nStartPos[i + 1];
}
nEndPos[nEndPos.length - 1] = nFileLength;
}
}
// 启动子线程
fileSplitterFetch = new FileSplitterFetch[nStartPos.length];
for (int i = 0; i < nStartPos.length; i++) {
fileSplitterFetch[i] = new FileSplitterFetch(siteInfoBean
.getSSiteURL(), siteInfoBean.getSFilePath()
+ File.separator + siteInfoBean.getSFileName(),
nStartPos[i], nEndPos[i], i);
Utility.log("Thread " + i + " , nStartPos = " + nStartPos[i]
+ ", nEndPos = " + nEndPos[i]);
fileSplitterFetch[i].start();
}
// fileSplitterFetch[nPos.length-1] = new
// FileSplitterFetch(siteInfoBean.getSSiteURL(),siteInfoBean.getSFilePath()
// + File.separator +
// siteInfoBean.getSFileName(),nPos[nPos.length-1],nFileLength,nPos.length-1);
// Utility.log("Thread " + (nPos.length-1) + " , nStartPos = " +
// nPos[nPos.length-1] + ",nEndPos = " + nFileLength);
// fileSplitterFetch[nPos.length-1].start();
// 等待子线程结束
// int count = 0;
// 是否结束while循环
boolean breakWhile = false;
while (!bStop) {
write_nPos();
Utility.sleep(500);
breakWhile = true;
for (int i = 0; i < nStartPos.length; i++) {
if (!fileSplitterFetch[i].bDownOver) {
breakWhile = false;
break;
}
}
if (breakWhile)
break;
// count++;
// if(count>4)
// siteStop();
}
System.err.println("文件下载结束!");
} catch (Exception e) {
e.printStackTrace();
}
} // 获得文件长度
public long getFileSize() {
int nFileLength = -1;
try {
URL url = new URL(siteInfoBean.getSSiteURL());
HttpURLConnection httpConnection = (HttpURLConnection) url
.openConnection();
httpConnection.setRequestProperty("User-Agent", "NetFox");
int responseCode = httpConnection.getResponseCode();
if (responseCode >= 400) {
processErrorCode(responseCode);
return -2; // -2 represent access is error
}
String sHeader;
for (int i = 1;; i++) {
// DataInputStream in = new
// DataInputStream(httpConnection.getInputStream ());
// Utility.log(in.readLine());
sHeader = httpConnection.getHeaderFieldKey(i);
if (sHeader != null) {
if (sHeader.equals("Content-Length")) {
nFileLength = Integer.parseInt(httpConnection
.getHeaderField(sHeader));
break;
}
} else
break;
}
} catch (IOException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
Utility.log(nFileLength);
return nFileLength;
}
// 保存下载信息(文件指针位置)
private void write_nPos() {
try {
output = new DataOutputStream(new FileOutputStream(tmpFile));
output.writeInt(nStartPos.length);
for (int i = 0; i < nStartPos.length; i++) {
// output.writeLong(nPos[i]);
output.writeLong(fileSplitterFetch[i].nStartPos);
output.writeLong(fileSplitterFetch[i].nEndPos);
}
output.close();
} catch (IOException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}
// 读取保存的下载信息(文件指针位置)
private void read_nPos() {
try {
DataInputStream input = new DataInputStream(new FileInputStream(
tmpFile));
int nCount = input.readInt();
nStartPos = new long[nCount];
nEndPos = new long[nCount];
for (int i = 0; i < nStartPos.length; i++) {
nStartPos[i] = input.readLong();
nEndPos[i] = input.readLong();
}
input.close();
} catch (IOException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}
private void processErrorCode(int nErrorCode) {
System.err.println("Error Code : " + nErrorCode);
}
// 停止文件下载
public void siteStop() {
bStop = true;
for (int i = 0; i < nStartPos.length; i++)
fileSplitterFetch[i].splitterStop();
}
}
分享到:
相关推荐
1.版本:matlab2014/2019a/2024a 2.附赠案例数据可直接运行matlab程序。 3.代码特点:参数化编程、参数可方便更改、代码编程思路清晰、注释明细。 4.适用对象:计算机,电子信息工程、数学等专业的大学生课程设计、期末大作业和毕业设计。
铅酸电池失效仿真comsol
Java小程序项目源码,该项目包含完整的前后端代码、数据库脚本和相关工具,简单部署即可运行。功能完善、界面美观、操作简单,具有很高的实际应用价值,非常适合作为Java毕业设计或Java课程设计使用。 所有项目均经过严格调试,确保可运行!下载后即可快速部署和使用。 1 适用场景: 毕业设计 期末大作业 课程设计 2 项目特点: 代码完整:详细代码注释,适合新手学习和使用 功能强大:涵盖常见的核心功能,满足大部分课程设计需求 部署简单:有基础的人,只需按照教程操作,轻松完成本地或服务器部署 高质量代码:经过严格测试,确保无错误,稳定运行 3 技术栈和工具 前端:小程序 后端框架:SSM/SpringBoot 开发环境:IntelliJ IDEA 数据库:MySQL(建议使用 5.7 版本,更稳定) 数据库可视化工具:Navicat 部署环境:Tomcat(推荐 7.x 或 8.x 版本),Maven
Java小程序项目源码,该项目包含完整的前后端代码、数据库脚本和相关工具,简单部署即可运行。功能完善、界面美观、操作简单,具有很高的实际应用价值,非常适合作为Java毕业设计或Java课程设计使用。 所有项目均经过严格调试,确保可运行!下载后即可快速部署和使用。 1 适用场景: 毕业设计 期末大作业 课程设计 2 项目特点: 代码完整:详细代码注释,适合新手学习和使用 功能强大:涵盖常见的核心功能,满足大部分课程设计需求 部署简单:有基础的人,只需按照教程操作,轻松完成本地或服务器部署 高质量代码:经过严格测试,确保无错误,稳定运行 3 技术栈和工具 前端:小程序 后端框架:SSM/SpringBoot 开发环境:IntelliJ IDEA 数据库:MySQL(建议使用 5.7 版本,更稳定) 数据库可视化工具:Navicat 部署环境:Tomcat(推荐 7.x 或 8.x 版本),Maven
springboot124中药实验管理系统设计与实现,含有完整的源码和报告文档
解除劳动合同协议书
快速过滤图像融合Matlab代码.rar
强调图像中内核形状(例如直线)的过滤器Matlab代码.rar
在内网linux服务器安装redis 在Linux环境中离线安装Redis是常见的需求,尤其是在内网服务器上,由于无法直接访问公网,我们需要提前下载Redis的源码包并手动安装。下面将详细解释如何进行这一过程。
1.版本:matlab2014/2019a/2024a 2.附赠案例数据可直接运行matlab程序。 3.代码特点:参数化编程、参数可方便更改、代码编程思路清晰、注释明细。 4.适用对象:计算机,电子信息工程、数学等专业的大学生课程设计、期末大作业和毕业设计。
微信小程序StartKitw_xapp-startkit
座位选择微信小程序版本
机械臂代码_Mechanical_arm
图像分割测试视频river-light.mp4
前端分析-2023071100789
labview源码参考示例,可供参考学习使用
MPC跟踪轨迹圆形(以后轴为基准)
MATLAB代码:基于主从博弈的智能小区代理商定价策略及电动汽车充电管理 关键词:电动汽车 主从博弈 动态定价 智能小区 充放电优化 参考文档:《基于主从博弈的智能小区代理商定价策略及电动汽车充电管理》基本复现 仿真平台:MATLAB+CPLEX gurobi平台 优势:代码具有一定的深度和创新性,注释清晰,非烂大街的代码,非常精品 主要内容:代码主要做的是一个电动汽车充电管理和智能小区代理商动态定价的问题,将代理商和车主各自追求利益最大化建模为主从博弈,上层以代理商的充电电价作为优化变量,下层以电动汽车的充电策略作为优化变量,通过优化得出最优电价策略以及动态充电策略,代码出图效果非常好,店主已经对代码进行了深入的加工和处理,出图效果非常好,代码质量非常高,保姆级的注释以及人性化的模块子程序,所有数据均有可靠来源,联系后会直接发您资料,保证您学得会,用的起来,简直是萌新福利
springboot154基于Spring Boot智能无人仓库管理,含有完整的源码和报告文档
Matlab领域上传的视频是由对应的完整代码运行得来的,完整代码皆可运行,亲测可用,适合小白; 1、从视频里可见完整代码的内容 主函数:main.m; 调用函数:其他m文件;无需运行 运行结果效果图; 2、代码运行版本 Matlab 2019b;若运行有误,根据提示修改;若不会,私信博主; 3、运行操作步骤 步骤一:将所有文件放到Matlab的当前文件夹中; 步骤二:双击打开main.m文件; 步骤三:点击运行,等程序运行完得到结果; 4、仿真咨询 如需其他服务,可私信博主; 4.1 博客或资源的完整代码提供 4.2 期刊或参考文献复现 4.3 Matlab程序定制 4.4 科研合作