黑马程序员技术交流社区

标题: Android实现多线程断点下载 [打印本页]

作者: linxy06    时间: 2015-11-27 01:48
标题: Android实现多线程断点下载
  class DownLoadThread extends Thread {  
  
        private int threadId;  
        private int startIndex;  
        private int endIndex;  
        private String path;  
  
        /**
         * 构造函数
         *  
         * @param threadId
         *            线程的序号
         * @param startIndex
         *            线程开始位置
         * @param endIndex
         * @param path
         */  
        public DownLoadThread(int threadId, int startIndex, int endIndex,  
                String path) {  
            super();  
            this.threadId = threadId;  
            this.startIndex = startIndex;  
            this.endIndex = endIndex;  
            this.path = path;  
        }  
  
        @Override  
        public void run() {  
            try {  
                File sdFile = Environment.getExternalStorageDirectory();  
                //获取每个线程下载的记录文件  
                File recordFile = new File(sdFile, threadId + ".txt");  
                if (recordFile.exists()) {  
                    // 读取文件的内容  
                    InputStream is = new FileInputStream(recordFile);  
                    // 利用工具类转换  
                    String value = StreamTools.streamToStr(is);  
                    // 获取记录的位置  
                    int recordIndex = Integer.parseInt(value);  
                    // 将记录的位置赋给开始位置  
                    startIndex = recordIndex;  
                }  
  
                // 通过path路径构建URL对象  
                URL url = new URL(path);  
                // 通过URL对象的openConnection()方法打开连接,返回一个连接对象  
                HttpURLConnection httpURLConnection = (HttpURLConnection) url  
                        .openConnection();  
                // 设置请求的头  
                httpURLConnection.setRequestMethod("GET");  
                httpURLConnection.setReadTimeout(5000);  
                // 设置下载文件的开始位置结束位置  
                httpURLConnection.setRequestProperty("Range", "bytes="  
                        + startIndex + "-" + endIndex);  
                // 获取的状态码  
                int code = httpURLConnection.getResponseCode();  
                // 判断是否成功  
                if (code == 206) {  
                    // 获取每个线程返回的流对象  
                    InputStream is = httpURLConnection.getInputStream();  
                    //获取文件的名称  
                    String fileName = path.substring(path.lastIndexOf("/")+1);  
                    // 根据路径创建文件  
                    File file = new File(sdFile, fileName);  
                    // 根据文件创建RandomAccessFile对象  
                    RandomAccessFile raf = new RandomAccessFile(file, "rwd");  
                    raf.seek(startIndex);  
                    // 定义读取的长度  
                    int len = 0;  
                    // 定义缓冲区  
                    byte b[] = new byte[1024 * 1024];  
                    int total = 0;  
                    // 循环读取  
                    while ((len = is.read(b)) != -1) {  
                        RandomAccessFile threadFile = new RandomAccessFile(  
                                new File(sdFile, threadId + ".txt"), "rwd");  
                        threadFile.writeBytes((startIndex + total) + "");  
                        threadFile.close();  
                        raf.write(b, 0, len);  
                        // 已经下载的大小  
                        total += len;  
                        //解决同步问题  
                        synchronized (DownloadActivity.this) {  
                            currentProgress += len;  
                            progressBar.setProgress(currentProgress);  
                            //计算百分比的操作 l表示long型  
                            final String percent = currentProgress*100l/progressBar.getMax()+"%";  
                            DownloadActivity.this.runOnUiThread(new Runnable() {  
                                public void run() {  
                                    tv_pb.setText("当前的进度是:"+percent);  
                                }  
                            });  
                            //创建保存当前进度和百分比的操作  
                            RandomAccessFile pbFile = new RandomAccessFile(  
                                    new File(sdFile, "pb.txt"), "rwd");  
                            pbFile.writeBytes(progressBar.getMax()+";"+currentProgress+";"+percent);  
                            pbFile.close();  
                        }  
                    }  
                    raf.close();  
                    is.close();  
                    runOnUiThread(new Runnable() {  
                        public void run() {  
                            Toast.makeText(DownloadActivity.this, "当前线程--" + threadId + "--下载完毕", Toast.LENGTH_LONG).show();  
                        }  
                    });  
                    deleteRecordFiles();  
                } else {  
                    runOnUiThread(new Runnable() {  
                        public void run() {  
                            Toast.makeText(DownloadActivity.this, "服务器端下载错误", Toast.LENGTH_LONG).show();  
                        }  
                    });  
                }  
            } catch (Exception e) {  
                // TODO Auto-generated catch block  
                e.printStackTrace();  
            }  
  
        }  
  
    }  
  
    // synchronized避免线程同步  
    public synchronized void deleteRecordFiles() {  
        File sdFile = Environment.getExternalStorageDirectory();  
        threadRunning--;  
        if (threadRunning == 0) {  
            for (int i = 1; i <= 3; i++) {  
                File recordFile = new File(sdFile, i + ".txt");  
                if (recordFile.exists()) {  
                    // 删除文件  
                    recordFile.delete();  
                }  
                File pbFile = new File(sdFile,"pb.txt");  
                if (pbFile.exists()) {  
                    pbFile.delete();  
                }  
            }  
        }  
    }  
作者: qinxiaodong    时间: 2015-11-27 15:46
安卓的啊




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2