使用多线程的Java中的下载管理器

贝扎德·哈萨尼(Behzad Hassani)

正如您在使用Java的下载管理器工作之前所看到的那样,我已经问过这个问题,并且已经阅读了这个问题,但是这些并不能解决我的问题。现在我用Java编写了另一个代码。但有一个问题。当下载完成文件大于其大小并且相关软件无法读取时

这是我的代码执行的图像:

在此处输入图片说明

如您所见,文件大小约为9.43 MB

这是我的项目目录的图像:

在此处输入图片说明

如您所见,我下载的文件大小约为13 MB

那我的问题是什么?

这是我完整的源代码

主类:

package download.manager;

import java.util.Scanner;

/**
 *
 * @author Behzad
 */
public class DownloadManager {

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {        
        Scanner input = new Scanner(System.in);
        System.out.print("Enter url here : ");
        String url = input.nextLine();
        DownloadInfo information = new DownloadInfo(url);

    }
}

DownloadInfo类:

package download.manager;

import java.io.IOException;
import java.io.RandomAccessFile;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
import java.util.logging.Level;
import java.util.logging.Logger;

public class DownloadInfo {         

    private String downloadUrl;

    private String fileName;       

    private String fileExtension;

    private URL nonStringUrl;

    private HttpURLConnection connection;

    private int fileSize;

    private int remainingByte;

    private RandomAccessFile outputFile;

    public DownloadInfo(String downloadUrl) {
        this.downloadUrl = downloadUrl;

        initiateInformation();
    }

    private void initiateInformation(){        
        fileName = downloadUrl.substring(downloadUrl.lastIndexOf('/') + 1, downloadUrl.length());

        fileExtension = fileName.substring(fileName.lastIndexOf('.') + 1, fileName.length());

        try {

            nonStringUrl = new URL(downloadUrl);

            connection = (HttpURLConnection) nonStringUrl.openConnection();

            fileSize = ((connection.getContentLength()));

            System.out.printf("File Size is : %d \n", fileSize);

            System.out.printf("Remain File Size is : %d \n", fileSize % 8);

            remainingByte = fileSize % 8;

            fileSize /= 8;

            outputFile = new RandomAccessFile(fileName, "rw");

        } catch (MalformedURLException ex) {
            Logger.getLogger(DownloadInfo.class.getName()).log(Level.SEVERE, null, ex);
        } catch (IOException ex) {
            Logger.getLogger(DownloadInfo.class.getName()).log(Level.SEVERE, null, ex);
        }



        System.out.printf("File Name is : %s\n", fileName);
        System.out.printf("File Extension is : %s\n", fileExtension);        
        System.out.printf("Partition Size is : %d MB\n", fileSize);

        int first = 0 , last = fileSize - 1;

        ExecutorService thread_pool = Executors.newFixedThreadPool(8);        

        for(int i=0;i<8;i++){            
            if(i != 7){
                thread_pool.submit(new Downloader(nonStringUrl, first, last, (i+1), outputFile));
            }
            else{
                thread_pool.submit(new Downloader(nonStringUrl, first, last + remainingByte, (i+1), outputFile));
            }
            first = last + 1;
            last += fileSize;
        }
        thread_pool.shutdown();

        try {
            thread_pool.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS);
        } catch (InterruptedException ex) {
            Logger.getLogger(DownloadInfo.class.getName()).log(Level.SEVERE, null, ex);
        }

    }

}

这是我的下载程序类:

package download.manager;

import java.io.IOException;
import java.io.InputStream;
import java.io.RandomAccessFile;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
 *
 * @author Behzad
 */
public class Downloader implements Runnable{

    private URL downloadURL;    

    private int startByte;       

    private int endByte;

    private int threadNum;    

    private RandomAccessFile outputFile;

    private InputStream stream;

    public Downloader(URL downloadURL,int startByte, int endByte, int threadNum, RandomAccessFile outputFile) {
        this.downloadURL = downloadURL;
        this.startByte = startByte;
        this.endByte = endByte;
        this.threadNum = threadNum;
        this.outputFile = outputFile;
    }



    @Override
    public void run() {
        download();
    }

    private void download(){
        try {

            System.out.printf("Thread %d is working...\n" , threadNum);

            HttpURLConnection httpURLConnection = (HttpURLConnection) downloadURL.openConnection();

            httpURLConnection.setRequestProperty("Range", "bytes="+startByte+"-"+endByte);

            httpURLConnection.connect();

            outputFile.seek(startByte);

            stream = httpURLConnection.getInputStream();

            while(true){                                                                
                int nextByte = stream.read();
                if(nextByte == -1){
                    break;
                }

                outputFile.write(endByte);

            }

        } catch (IOException ex) {
            Logger.getLogger(Downloader.class.getName()).log(Level.SEVERE, null, ex);
        }   
    }
}

如您所见,该文件是MP4,但Gom无法播放它。请您帮帮我吗?

贝扎德·哈萨尼(Behzad Hassani)

OoOoOopppps终于我找到了问题所在,全部在寻找方法上。因为我有一个文件和8个线程。因此,seek方法会反复更改光标,并生成更大的文件和无法执行的文件:),但是我很抱歉。我无法显示完整的代码:)

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章