multi-Threaded download can preempt other users of the same priority network resources (broadband), so that the download speed is relatively fast, thunder, fast broadcast are using multi-threaded download.
1. Request the length of the file on the server 2. Create a file of the same size on your phone based on the length of the file on the server 3. Calculate the range of downloads for each thread based on the number of threads and the length of the file the length of the file is: 10 The number of threads is: 3 size of each block: 10/3=3.3333=3
Thread 0:0~2
Thread 1:3~5
Thread 2:6~9
start Position: The size of each chunk of the thread's id*. End Position: Thread (id+1) * Size of each block-1; where the last thread ends is: the length of the file-1;
4. Turn on multiple threads and each thread downloads its own chunk1). Request the server to upload some content.
Range (Request header):bytes= 3-8 Get the contents of server file 3-8
Features: The server return value is no longer 200, is 206.
2). Move the write position to the location where the thread started.
3). The read contents of the loop are written to local.
# # # #断点下载 (not normal off)* Every time you read data, write local data, you should gross position the record to local. * The next time you start the download, check that there are no downloaded Records (archive), if any, take out, continue to download
Code:
public class Downloadutils {//completed thread private int completethread;private int threadcount;/** * Start multi-Threaded download * * @param URL * Access server address * @param dir * Local receive path * @param threadcount * How many threads are open to download */public void Startmultithre Addownload (final string url, final string dir,final int threadcount) {this.threadcount = Threadcount;completethread = 0;ne W Thread (New Runnable () {@Overridepublic void Run () {//1. The length of the file on the requesting server int filelength = getremoteservicefilelength (URL); if (filelength = =-1) {SYSTEM.OUT.PRINTLN ("Request server file length failed, stop download"); return; SYSTEM.OUT.PRINTLN ("Remote server length:" + filelength);//2. Create an exact size file on your phone based on the length of the file on the server string fileName = Url.substring ( Url.lastindexof ("/") + 1); File File = new file (dir, fileName); try {randomaccessfile RAF = new Randomaccessfile (file, "RWD"); Raf.setlength (filelengt h); Raf.close (); SYSTEM.OUT.PRINTLN ("Local file creation succeeded" + File.getpath ());} catch (Exception e) {//TODO auto-generated catch Blocke.printstacktrace ();} 3. Calculate the range that each thread needs to download, based on the number of threads and the length of the file int blockSize = filelength/threadcount;for (int i = 0; i < ThreadCount; i++) {//Start position: The size of each block of id* of the thread. int start = i * blocksize;//End Position: Thread (id+1) * size of each block -1;int end = (i + 1) * blocksize-1;//The last thread end position is: the length of the file -1;if ((i = = threadCount-1) {end = FileLength-1;} 4. Open multiple threads, each of which downloads its own block range, passing parameters:, the path of the stored file//Start position, the end of the location, thread idnew threads (new downloadrunnable (URL, File.getpath (), Start,end, i)). Start ();}}). Start ();} /** * Download Task class * * @author Administrator * */class Downloadrunnable implements Runnable {private String url;private File Lo Calfile; Path of the file private int start; The location where the current thread starts to download the private int end; End download location private int threadid;//thread idpublic downloadrunnable (string url, string path, int start, int end,int i) {This.url = Url;this.localfile = new File (path); This.start = Start;this.end = End;this.threadid = i;} @Overridepublic void Run () {HttpURLConnection conn = null;try {//Add breakpoint download int total = 0;//Overall progress of current thread download//gross position progress value stored locally go to file Cach Efile = new File (Localfile.getparent (), "thread" + ThreadID + ". HM");Randomaccessfile Cacheraf = new Randomaccessfile (Cachefile, "RWD");//Determine if the last cache progress if (cachefile.exists () && Cachefile.length () > 0) {//file exists and has data//progress of last download int progress = integer.valueof (Cacheraf.readline ()); start + = Progress ;//Put the last progress in the beginning of the position Plus, continue to download total = progress;//The last download overall progress assignment}system.out.println ("thread" + ThreadID + ", began to download, the scope of the download is:" + start+ "~ "+ END"; conn = (httpurlconnection) new URL (URL). OpenConnection (); Conn.setrequestmethod ("GET"); Conn.setconnecttimeout, Conn.setreadtimeout (5000);//Set the request header message: Range, requesting part of the contents of the file on the server Conn.setrequestproperty (" Range "," bytes= "+ Start +"-"+ end); int responsecode = Conn.getresponsecode (); if (responsecode = = 206) {int Contentlengt h = conn.getcontentlength (); SYSTEM.OUT.PRINTLN ("thread" + ThreadID + ", request succeeded, content length:" + contentlength);//Get the data returned by the server InputStream is = Conn.getinputstream () ; Randomaccessfile RAF = new Randomaccessfile (LocalFile, "RWD");//move the written position to the position where the thread started Raf.seek (start); byte[] buf = new byte[ 1024];int len = 0;while (len = Is.read (BUF))! = -1) {raf.write (buf, 0, Len), Total + = Len;cacheraf.seek (0);//Every time you move to the beginning of the file, write Cacheraf.write (string.valueof (total). GetBytes ());} Cacheraf.close (); Raf.close (); Is.close (); SYSTEM.OUT.PRINTLN ("thread" + ThreadID + ", download completed."); Completethread++;if (Completethread = = ThreadCount) {System.out.println ("Full download complete, delete temp profile."); for (int i = 0; i < ThreadCount; i++) {File DeleteFile = new File (Localfile.getparent (), "thread" + i + ". HM"); System.out.println (Deletefile.delete ());}}} catch (Exception e) {//TODO auto-generated catch Blocke.printstacktrace ();} finally {if (conn! = null) {Conn.disconnect () ;}}}} /** * Request a remote server for a file size based on a URL connection * * @param URL * Server address * @return */private int getremoteservicefilelength (String ur L) {HttpURLConnection conn = null;try {conn = (httpurlconnection) new URL (URL). OpenConnection ();//Request method, Must be size Conn.setrequestmethod ("GET");//Connection Timeout conn.setconnecttimeout (5000);//Read Timeout conn.setreadtimeout (+); int Reponsecode = Conn.getresponsecode ();//Gets the response code returned by the server if (Reponsecode = = 200) {return conn.getcontentlength ();}} catch (Exception e) {e.printstacktrace ();} finally {if (conn! = null) {Conn.disconnect ();}} return-1;}}
Call:
public class Demo {public static void main (string[] args) {System.out.println ("Turn on multi-threaded download ...");//link, path, Number of threads string url = "Http://192.168.1.109/FeiQ.exe"; String dir = "f:/wdjdownload"; int threadcount = 3;downloadutils du = new Downloadutils ();d u.startmultithreaddownload (url , dir, ThreadCount);}}