From b85819a5c6ac1ff35a367eee9bf21472e87622ee Mon Sep 17 00:00:00 2001 From: Samson Shenglu Cao Date: Mon, 6 Mar 2017 11:53:18 +0800 Subject: [PATCH 1/3] modify --- group19/972815123/src/com/coderising/litestruts/Struts.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/group19/972815123/src/com/coderising/litestruts/Struts.java b/group19/972815123/src/com/coderising/litestruts/Struts.java index 7d908282b6..2aeaffd491 100644 --- a/group19/972815123/src/com/coderising/litestruts/Struts.java +++ b/group19/972815123/src/com/coderising/litestruts/Struts.java @@ -52,7 +52,7 @@ public class Struts { public static View runAction(String actionName, Map parameters) { HashMap> xml = parseStrutsXml(url); - HashMap login = xml.get("login"); + HashMap login = xml.get(actionName); String loginClassName = login.get("class"); System.out.println(loginClassName); From e01ba89120b5c5b347b17d3989d76a3c333c4811 Mon Sep 17 00:00:00 2001 From: Samson Shenglu Cao Date: Sun, 12 Mar 2017 01:41:21 +0800 Subject: [PATCH 2/3] add unit test --- .../src/com/coderising/array/ArrayUtil.java | 128 ++++++++++++------ .../com/coderising/array/ArrayUtilTest.java | 120 ++++++++++++++++ .../src/com/coderising/array/Main.java | 20 +++ 3 files changed, 224 insertions(+), 44 deletions(-) create mode 100644 group19/972815123/src/com/coderising/array/ArrayUtilTest.java create mode 100644 group19/972815123/src/com/coderising/array/Main.java diff --git a/group19/972815123/src/com/coderising/array/ArrayUtil.java b/group19/972815123/src/com/coderising/array/ArrayUtil.java index fca1de56e4..b24534a1f6 100644 --- a/group19/972815123/src/com/coderising/array/ArrayUtil.java +++ b/group19/972815123/src/com/coderising/array/ArrayUtil.java @@ -16,10 +16,10 @@ public void reverseArray(int[] origin){ int tem = 0; for(int i = 0, len = origin.length; i < len/2; i ++){ tem = origin[i]; - origin[i] = origin[len - i + 1]; - origin[len - i + 1] = tem; + origin[i] = origin[len - i - 1]; + origin[len - i - 1] = tem; } - + System.out.println(join(origin, ",")); } /** @@ -33,12 +33,12 @@ public void reverseArray(int[] origin){ public int[] removeZero(int[] oldArray){ int withoutZeroSize = 0; for(int i = 0, len = oldArray.length; i < len; i ++ ){ - if( oldArray[i] == 0){ + if( oldArray[i] != 0){ withoutZeroSize ++; } } int[] newArray = new int[withoutZeroSize]; - int point = 1; + int point = 0; for(int i = 0 ,len = oldArray.length; i < len; i ++ ){ if( oldArray[i] != 0){ newArray[point] = oldArray[i]; @@ -57,19 +57,39 @@ public int[] removeZero(int[] oldArray){ */ public int[] merge(int[] array1, int[] array2){ - int point2 = 0; - int[] result = new int[array1.length + array2.length]; - int point1 = 0, len1 = array1.length; - while(point1 < len1){ - if(array1[point1] < array2[point2]){ - result[point1 + point2] = array1[point1]; - point1 ++; + int point = 0; + int point2 = 0, point1 = 0; + int len1 = array1.length, len2 = array2.length; + + int[] result = new int[len1 + len2]; + while(point1 < len1 || point2 < len2){ + if(point1 < len1 && point2 < len2){ + if(array1[point1] <= array2[point2]){ + result[point] = array1[point1]; + point++; + point1++; + }else{ + if(result[point - 1] == array2[point2]){ + point2++; + }else{ + result[point] = array2[point2]; + point++; + point2++; + } + } }else{ - result[point1 + point2] = array2[point2]; - point2 ++; + if(point1 < len1){ + result[point] = array1[point1]; + point++; + point1++; + }else{ + result[point] = array2[point2]; + point++; + point2++; + } } } - + result = removeZero(result); return result; } /** @@ -97,24 +117,26 @@ public int[] grow(int [] oldArray, int size){ * @return */ public int[] fibonacci(int max){ - int[] result = {1,1,2}; - int a1 = 1, a2 = 2; + int[] result = {1,1}; if(max <= 1){ return null; }else if(max == 2){ return result; }else{ result = grow(result, 10); - int index = 2; - while(result[index] > max){ - if(result.length < index + 2){ + int index = 1; + while(true){ + index ++; + if(result.length < index + 1){ result = grow(result, 10); } - result[index + 1] = result[index -1] + result[index]; - index ++; + result[index] = result[index -1] + result[index - 2]; + if(result[index] > max){ + break; + } } } - return result; + return removeZero(result); } /** @@ -124,32 +146,36 @@ public int[] fibonacci(int max){ * @return */ public int[] getPrimes(int max){ - int[] temArr = null; + int[] temArr = {2}; if(max < 2){ return null; }else if (max == 2){ - int[] re = {2}; - return re; + return temArr; }else{ - temArr = new int[max/2]; - temArr[0] = 2; - int index = 1; - for(int i = 3; i < max ; i= i+2){ + temArr = grow(temArr, 10); + int index = 0; + for(int i = 3;i < max; i ++){ boolean flag = true; - int isql = (int) Math.sqrt(i); - for(int j = 3; j < isql; j++){ - if(i % j == 0){ + int iSqrt = (int) Math.sqrt(i); + for(int j = 0; j < index + 1; j ++){ + if(iSqrt < temArr[j]){ + break; + } + if(i % temArr[j] == 0){ flag = false; + break; } } if(flag){ - temArr[index] = i; index ++; + if(temArr.length < index + 1){ + temArr = grow(temArr, 30); + } + temArr[index] = i; } } } - temArr = this.removeZero(temArr); - return temArr; + return removeZero(temArr); } /** @@ -163,17 +189,17 @@ public int[] getPerfectNumbers(int max){ int index = 0; if(max < 6){ return null; - }else{ - } + } + for (int n = 6; n <= max ; n ++){ - int[] allPrimeFactore = getPrimeFactors(n); + int[] allFactors = getAllFactors(n); int sum = 0; - for(int i = 0, len = allPrimeFactore.length; i < len; i ++){ - sum += allPrimeFactore[i]; + for(int i = 0, len = allFactors.length; i < len; i ++){ + sum += allFactors[i]; } if(sum == n){ if(result.length < index + 1){ - result = this.grow(result, 1); + result = this.grow(result, 3); } result[index] = n; index ++; @@ -183,10 +209,24 @@ public int[] getPerfectNumbers(int max){ return removeZero(result); } - private int[] getPrimeFactors(int n){ + public int[] getAllFactors(int n){ + int[] result = new int[n]; + int index = 0; + for(int i = 1; i < n; i++){ + if(n % i == 0){ + result[index] = i; + index ++; + } + } + return removeZero(result); + } + + //分解因式算法 + public int[] getPrimeFactors(int n){ int[] allPrimes = getPrimes(n); int[] result = new int[allPrimes.length]; - int index = 0; + int index = 1; + result[0] = 1; for(int i = 0, len = allPrimes.length; i < len; i ++){ int devide = n; while(devide % allPrimes[i] == 0){ diff --git a/group19/972815123/src/com/coderising/array/ArrayUtilTest.java b/group19/972815123/src/com/coderising/array/ArrayUtilTest.java new file mode 100644 index 0000000000..2fbd5ead5e --- /dev/null +++ b/group19/972815123/src/com/coderising/array/ArrayUtilTest.java @@ -0,0 +1,120 @@ +package com.coderising.array; + +import static org.junit.Assert.*; + +import org.junit.After; +import org.junit.AfterClass; +import org.junit.Before; +import org.junit.BeforeClass; +import org.junit.Test; + +import junit.framework.Assert; + +public class ArrayUtilTest { + + private ArrayUtil au; + + @BeforeClass + public static void setUpBeforeClass() throws Exception { + } + + @AfterClass + public static void tearDownAfterClass() throws Exception { + } + + @Before + public void setUp() throws Exception { + au = new ArrayUtil(); + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testReverseArray() { + int[] test = {1,2,3}; + au.reverseArray(test); + String result = au.join(test, "-"); + Assert.assertEquals(result, "3-2-1"); + } + + @Test + public void testRemoveZero() { + int[] test = {1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5}; + test = au.removeZero(test); + String result = au.join(test, ","); + Assert.assertEquals(result, "1,3,4,5,6,6,5,4,7,6,7,5"); + } + + @Test + public void testMerge() { + int[] arr1 = {3, 5, 7,8}; + int[] arr2 = {4, 5, 6,7}; + int[] test = au.merge(arr1, arr2); + String result = au.join(test, ","); + System.out.println(result); + Assert.assertEquals(result, "3,4,5,6,7,8"); + } + + @Test + public void testGrow() { + int[] test = {3,5,6}; + test = au.grow(test, 2); + String result = au.join(test, ","); + System.out.println(result); + System.out.println(test.length); + Assert.assertTrue(5 == test.length); + } + + @Test + public void testFibonacci() { + int[] test = au.fibonacci(250); + String result = au.join(test, ","); + System.out.println(result); + Assert.assertEquals(result, "1,1,2,3,5,8,13,21,34,55,89,144,233,377"); + } + + @Test + public void testGetPrimes() { + //2,3,5,7,11,13,17,19 + int[] test = au.getPrimes(23); + String result = au.join(test, ","); + System.out.println(result); + Assert.assertEquals(result, "2,3,5,7,11,13,17,19"); + } + + @Test + public void testGetPerfectNumbers() { + int[] test = au.getPerfectNumbers(10000); + String result = au.join(test, ","); + System.out.println(result); + Assert.assertEquals(result, "6,28,496,8128"); + } + + + @Test + public void testGetAllFactors(){ + int[] test = au.getAllFactors(98); + String result = au.join(test, ","); + System.out.println(result); + Assert.fail(); + } + + @Test + public void testGetPrimeFactors(){ + int[] test = au.getPrimeFactors(98); + String result = au.join(test, ","); + System.out.println(result); + Assert.fail(); + } + + @Test + public void testJoin() { + int[] test = {1,2,3}; + String result = au.join(test, ","); + + Assert.assertEquals(result, "1,2,3"); + } + +} diff --git a/group19/972815123/src/com/coderising/array/Main.java b/group19/972815123/src/com/coderising/array/Main.java new file mode 100644 index 0000000000..5c8a9abcc6 --- /dev/null +++ b/group19/972815123/src/com/coderising/array/Main.java @@ -0,0 +1,20 @@ +package com.coderising.array; + +public class Main { + + public static void main(String[] args) { + ArrayUtil au = new ArrayUtil(); +// int[] test = {1,2}; +// au.reverseArray(test); +// String result = au.join(test, "-"); + + + int[] arr1 = {3, 5, 7,8}; + int[] arr2 = {4, 5, 6,7}; + int[] test = au.merge(arr1, arr2); + String result = au.join(test, ","); + + System.out.println(result); + } + +} From 1d7c36380efd718ca1e7137b7dbd7b58f3f3166e Mon Sep 17 00:00:00 2001 From: Samson Shenglu Cao Date: Mon, 20 Mar 2017 09:32:43 +0800 Subject: [PATCH 3/3] 3rd homework --- .../src/com/coding/basic/LinkedList.java | 234 +++++++++++++++++- .../src/com/coding/basic/LinkedListTest.java | 209 ++++++++++++++++ .../src/com/download/DownloadDemo.java | 34 +++ .../src/com/download/DownloadThread.java | 58 +++++ .../src/com/download/FileDownloader.java | 88 +++++++ .../src/com/download/FileDownloaderTest.java | 52 ++++ .../src/com/download/api/Connection.java | 23 ++ .../com/download/api/ConnectionException.java | 5 + .../com/download/api/ConnectionManager.java | 10 + .../com/download/api/DownloadListener.java | 5 + .../src/com/download/impl/ConnectionImpl.java | 46 ++++ .../download/impl/ConnectionManagerImpl.java | 28 +++ 12 files changed, 786 insertions(+), 6 deletions(-) create mode 100644 group19/972815123/src/com/coding/basic/LinkedListTest.java create mode 100644 group19/972815123/src/com/download/DownloadDemo.java create mode 100644 group19/972815123/src/com/download/DownloadThread.java create mode 100644 group19/972815123/src/com/download/FileDownloader.java create mode 100644 group19/972815123/src/com/download/FileDownloaderTest.java create mode 100644 group19/972815123/src/com/download/api/Connection.java create mode 100644 group19/972815123/src/com/download/api/ConnectionException.java create mode 100644 group19/972815123/src/com/download/api/ConnectionManager.java create mode 100644 group19/972815123/src/com/download/api/DownloadListener.java create mode 100644 group19/972815123/src/com/download/impl/ConnectionImpl.java create mode 100644 group19/972815123/src/com/download/impl/ConnectionManagerImpl.java diff --git a/group19/972815123/src/com/coding/basic/LinkedList.java b/group19/972815123/src/com/coding/basic/LinkedList.java index 04de763349..b001f06305 100644 --- a/group19/972815123/src/com/coding/basic/LinkedList.java +++ b/group19/972815123/src/com/coding/basic/LinkedList.java @@ -12,13 +12,24 @@ public LinkedList() { @Override public void add(Object o) { + + Node newNode = new Node(); - Node last = head; - while(last.next != null){ - last = last.next; + newNode.data = o; + newNode.next = null; + + if(size == 0){ + head = newNode; + size = 1; + return; } - last.next = newNode; - newNode.prev = last; + + Node _last = head; + while(_last.next != null){ + _last = _last.next; + } + _last.next = newNode; + newNode.prev = _last; last = newNode; size++; } @@ -60,7 +71,7 @@ public int size() { public Object remove(int index) { Node indexNode = head ; int i = 0; - while(i == index){ + while(i != index){ indexNode = indexNode.next; i++; @@ -131,4 +142,215 @@ public Object next() { index = index.next; return tem; } + + @Override + public String toString(){ + Node node = head; + StringBuffer sb = new StringBuffer(); + while(node.next != null){ + sb.append(node.data.toString() + ","); + node = node.next; + } + sb.append(node.data.toString()); + return sb.toString(); + } + + /** + * 把该链表逆置 + * 例如链表为 3->7->10 , 逆置后变为 10->7->3 + */ + public void reverse(){ + Node index = head; + Node temPre = null; + while(true){ + Node tem = index.next; + if(index.next == null){ + head = index; + index.next = temPre; + break; + } + index.next = temPre; + temPre = index; + index = tem; + } + } + + /** + * 删除一个单链表的前半部分 + * 例如:list = 2->5->7->8 , 删除以后的值为 7->8 + * 如果list = 2->5->7->8->10 ,删除以后的值为7,8,10 + */ + public void removeFirstHalf(){ + int i = 0; + Node node = head; + while(i < size/2 + 1){ + head = node; + node = node.next; + i++; + } + } + + /** + * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 + * @param i + * @param length + */ + public void remove(int i, int length){ + //省略了数据合法性检查; + Node indexStart = head; + int index = 0; + for(int j = 0; j < i - 1; j++){ + indexStart= indexStart.next; + } + Node indexEnd = indexStart; + Node tem = null; + for(int k = 0 ; k <= length; k++){ + tem = indexEnd; + indexEnd = indexEnd.next; + } + tem.next = null; + indexStart.next = indexEnd; + } + /** + * 假定当前链表和listB均包含已升序排列的整数 + * 从当前链表中取出那些listB所指定的元素 + * 例如当前链表 = 11->101->201->301->401->501->601->701 + * listB = 1->3->4->6 + * 返回的结果应该是[101,301,401,601] + * @param list + */ + public Object[] getElements(LinkedList list){ + //省略了数据合法性检查; + Node pointHead = list.head; + Node node = head; + Object[] result = new Object[list.size]; + int point = 0; + int resultPoint = 0; + while(true){ + int temPoint = (int)pointHead.data; + if(point == temPoint){ + result[resultPoint] = node.data; + if(pointHead.next == null){ + break; + } + resultPoint++; + pointHead = pointHead.next; + } + if(node.next == null ){ + break; + } + node = node.next; + point++; + } + return result; + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 + * 从当前链表中中删除在listB中出现的元素 + + * @param list + */ + //m * n 复杂度的算法,没有利用原链表已排序的特性; + public void subtract(LinkedList list){ + Node indexNode = head; + Node indexPreNode = null; + while(null != indexNode){ + Node pointNode = list.head; + while(null != pointNode){ + if((int)pointNode.data == (int)(indexNode.data)){ + if(indexPreNode == null){ + head = indexNode.next; + }else{ + indexPreNode.next = indexNode.next; + } + } + pointNode = pointNode.next; + } + indexPreNode = indexNode; + indexNode = indexNode.next; + } + } + + /** + * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 + * 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) + */ + public void removeDuplicateValues(){ + Node indexNode = head; + Node indexPreNode = null; + while(null != indexNode){ + if(null == indexPreNode){ + indexPreNode = indexNode; + indexNode = indexNode.next; + continue; + } + if((int)indexPreNode.data == (int)indexNode.data){ + indexPreNode.next = indexNode.next; + }else{ + indexPreNode = indexNode; + } + indexNode = indexNode.next; + } + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 + * 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) + * @param min + * @param max + */ + public void removeRange(int min, int max){ + Node indexNode = head; + Node indexPreNode = null; + Node minNode = null; + Node maxNode = null; + boolean getMin = false, getMax = false; + while(indexNode != null){ + if((int)indexNode.data >= min){ + if(!getMin){ + minNode = indexPreNode; + getMin = true; + } + } + + if((int)indexNode.data > max){ + if(!getMax){ + maxNode = indexNode; + break; + } + } + indexPreNode = indexNode; + indexNode = indexNode.next; + } + if(null == minNode && null == maxNode){ + head.data = null; + head.next = null; + }else if(null != minNode && null != maxNode){ + minNode.next = maxNode; + } + + } + + /** + * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) + * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 + * @param list + */ + public LinkedList intersection( LinkedList list){ + LinkedList result = new LinkedList(); + Node indexNode = head; + while(null != indexNode){ + Node pointNode = list.head; + while(null != pointNode){ + if((int)pointNode.data == (int)(indexNode.data)){ + result.add(indexNode.data); + } + pointNode = pointNode.next; + } + indexNode = indexNode.next; + } + return result; + } + } diff --git a/group19/972815123/src/com/coding/basic/LinkedListTest.java b/group19/972815123/src/com/coding/basic/LinkedListTest.java new file mode 100644 index 0000000000..1bb14396a0 --- /dev/null +++ b/group19/972815123/src/com/coding/basic/LinkedListTest.java @@ -0,0 +1,209 @@ +package com.coding.basic; + +import static org.junit.Assert.*; + +import org.junit.After; +import org.junit.AfterClass; +import org.junit.Before; +import org.junit.BeforeClass; +import org.junit.Test; + +import junit.framework.Assert; + +public class LinkedListTest { + + @BeforeClass + public static void setUpBeforeClass() throws Exception { + } + + @AfterClass + public static void tearDownAfterClass() throws Exception { + } + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testRemove(){ + LinkedList ll = new LinkedList(); + ll.add("1"); + ll.add("2"); + ll.add("3"); + ll.add("4"); + ll.remove(3); + System.out.println(ll.toString()); + Assert.assertEquals("1,2,3,4", ll.toString()); + } + + @Test + public void testToString() { + LinkedList ll = new LinkedList(); + ll.add("1"); + ll.add("2"); + ll.add("3"); + ll.add("4"); + System.out.println(ll.toString()); + Assert.assertEquals("1,2,3,4", ll.toString()); + } + + @Test + public void testReverse() { + LinkedList ll = new LinkedList(); + ll.add("4"); + ll.add("3"); + ll.add("2"); + ll.add("1"); + System.out.println(ll.toString()); + ll.reverse(); + System.out.println(ll.toString()); + Assert.assertEquals("1,2,3,4", ll.toString()); + } + + @Test + public void testRemoveFirstHalf() { + LinkedList ll = new LinkedList(); + ll.add("4"); + ll.add("3"); + ll.add("2"); + ll.add("1"); + ll.add("0"); + System.out.println(ll.toString()); + ll.removeFirstHalf(); + System.out.println(ll.toString()); + Assert.assertEquals("2,1,0", ll.toString()); + } + + @Test + public void testRemoveIntInt() { + LinkedList ll = new LinkedList(); + ll.add("1"); + ll.add("2"); + ll.add("3"); + ll.add("4"); + ll.add("5"); + ll.add("6"); + ll.add("7"); + ll.add("8"); + ll.add("9"); + ll.remove(3,2); + System.out.println(ll.toString()); + Assert.assertEquals("1,2,3,6,7,8,9", ll.toString()); + } + + @Test + public void testGetElements() { + LinkedList ll = new LinkedList(); + ll.add("0"); + ll.add("1"); + ll.add("2"); + ll.add("3"); + ll.add("4"); + ll.add("5"); + ll.add("6"); + ll.add("7"); + ll.add("8"); + ll.add("9"); + LinkedList pointerList = new LinkedList(); + pointerList.add(1); + pointerList.add(3); + pointerList.add(5); + pointerList.add(7); + Object[] result = ll.getElements(pointerList); + for(Object o : result){ + System.out.print((String)o); + System.out.print(","); + } + Assert.assertEquals((String)result[3], "7"); + } + + @Test + public void testSubtract() { + LinkedList ll = new LinkedList(); + ll.add(0); + ll.add(1); + ll.add(2); + ll.add(3); + ll.add(4); + ll.add(5); + ll.add(6); + ll.add(7); + ll.add(8); + LinkedList pointerList = new LinkedList(); + pointerList.add(1); + pointerList.add(3); + pointerList.add(5); + pointerList.add(7); + ll.subtract(pointerList); + System.out.println(ll.toString()); + Assert.assertEquals("0,2,4,6,8", ll.toString()); + } + + @Test + public void testRemoveDuplicateValues() { + LinkedList ll = new LinkedList(); + ll.add(0); + ll.add(1); + ll.add(2); + ll.add(3); + ll.add(3); + ll.add(3); + ll.add(4); + ll.add(5); + ll.add(5); + ll.add(6); + ll.add(7); + ll.add(8); + ll.removeDuplicateValues(); + System.out.println(ll.toString()); + Assert.assertEquals("0,1,2,3,4,5,6,7,8", ll.toString()); + } + + @Test + public void testRemoveRange() { + LinkedList ll = new LinkedList(); + ll.add(0); + ll.add(1); + ll.add(2); + ll.add(3); + ll.add(3); + ll.add(3); + ll.add(4); + ll.add(5); + ll.add(5); + ll.add(6); + ll.add(7); + ll.add(8); + ll.removeRange(3,7); + System.out.println(ll.toString()); + Assert.assertEquals("0,1,2,8", ll.toString()); + } + + @Test + public void testIntersection() { + LinkedList ll = new LinkedList(); + ll.add(0); + ll.add(1); + ll.add(2); + ll.add(3); + ll.add(4); + ll.add(5); + ll.add(6); + ll.add(7); + ll.add(8); + LinkedList pointerList = new LinkedList(); + pointerList.add(1); + pointerList.add(5); + pointerList.add(3); + pointerList.add(11); + pointerList.add(7); + ll = ll.intersection(pointerList); + System.out.println(ll.toString()); + Assert.assertEquals("1,3,5,7", ll.toString()); + } + +} diff --git a/group19/972815123/src/com/download/DownloadDemo.java b/group19/972815123/src/com/download/DownloadDemo.java new file mode 100644 index 0000000000..ceb9f93309 --- /dev/null +++ b/group19/972815123/src/com/download/DownloadDemo.java @@ -0,0 +1,34 @@ +package com.coderising.download; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.InputStream; +import java.io.RandomAccessFile; +import java.net.URL; +import java.net.URLConnection; + +public class DownloadDemo { + + public static void main(String[] args) throws Exception { + URL url = new URL("http://bpic.588ku.com/back_pic/02/66/65/68578b3fca8af67.jpg"); + URLConnection conn = url.openConnection(); + InputStream is = conn.getInputStream(); + + System.out.println("content length:" + conn.getContentLength() /1024 + " * 1024"); + System.out.println("stream avilable:" + is.available()/1024 + " * 1024"); + int length = conn.getContentLength(); + + byte[] buffer = new byte[1024]; + int hasRead = 0; + ByteArrayOutputStream out = new ByteArrayOutputStream(); + while((hasRead = is.read(buffer)) != -1){ + out.write(buffer, 0, hasRead); + } + byte[] result = out.toByteArray(); + + RandomAccessFile file = new RandomAccessFile("demo.jpg", "rw"); + file.write(result); + file.close(); + is.close(); + } +} diff --git a/group19/972815123/src/com/download/DownloadThread.java b/group19/972815123/src/com/download/DownloadThread.java new file mode 100644 index 0000000000..c699e81f5a --- /dev/null +++ b/group19/972815123/src/com/download/DownloadThread.java @@ -0,0 +1,58 @@ +package com.coderising.download; + +import java.io.IOException; +import java.io.RandomAccessFile; + +import com.coderising.download.api.Connection; +import com.coderising.download.api.DownloadListener; + +public class DownloadThread extends Thread{ + + Connection conn; + int startPos; + int endPos; + + String fileName; + + Object obj; + private DownloadListener downLoadThread; + +// public DownloadThread setObj(Object obj){ +// this.obj = obj; +// return this; +// } + + public DownloadThread setOnThreadFinished(DownloadListener downLoadThread){ + this.downLoadThread = downLoadThread; + return this; + } + + + public DownloadThread( Connection conn, int startPos, int endPos, String fileName){ + + this.conn = conn; + this.startPos = startPos; + this.endPos = endPos; + this.fileName = fileName; + } + public void run(){ + try { + double id = Thread.currentThread().getId(); + System.out.println(id); + byte[] byArr = conn.read(startPos, endPos); + int len = byArr.length; + + Thread.sleep(2000); + + RandomAccessFile currenctPart = new RandomAccessFile(fileName, "rw"); + currenctPart.seek(startPos); + System.out.println(len + "readed length"); + currenctPart.write(byArr,0,len); + currenctPart.close(); + System.out.println(id); + downLoadThread.notifyFinished(); + } catch (IOException | InterruptedException e) { + e.printStackTrace(); + } + } +} diff --git a/group19/972815123/src/com/download/FileDownloader.java b/group19/972815123/src/com/download/FileDownloader.java new file mode 100644 index 0000000000..d02b9970b8 --- /dev/null +++ b/group19/972815123/src/com/download/FileDownloader.java @@ -0,0 +1,88 @@ +package com.coderising.download; + + +import com.coderising.download.api.Connection; +import com.coderising.download.api.ConnectionException; +import com.coderising.download.api.ConnectionManager; +import com.coderising.download.api.DownloadListener; +import com.coderising.download.impl.ConnectionManagerImpl; + + +public class FileDownloader { + + String url; + DownloadListener listener; + ConnectionManager cm; + private int threadRun = 0; + + public FileDownloader(String _url) { + this.url = _url; + } + + public void execute(){ + // 在这里实现你的代码, 注意: 需要用多线程实现下载 + // 这个类依赖于其他几个接口, 你需要写这几个接口的实现代码 + // (1) ConnectionManager , 可以打开一个连接,通过Connection可以读取其中的一段(用startPos, endPos来指定) + // (2) DownloadListener, 由于是多线程下载, 调用这个类的客户端不知道什么时候结束,所以你需要实现当所有 + // 线程都执行完以后, 调用listener的notifiedFinished方法, 这样客户端就能收到通知。 + // 具体的实现思路: + // 1. 需要调用ConnectionManager的open方法打开连接, 然后通过Connection.getContentLength方法获得文件的长度 + // 2. 至少启动3个线程下载, 注意每个线程需要先调用ConnectionManager的open方法 + // 然后调用read方法, read方法中有读取文件的开始位置和结束位置的参数, 返回值是byte[]数组 + // 3. 把byte数组写入到文件中 + // 4. 所有的线程都下载完成以后, 需要调用listener的notifiedFinished方法 + + // 下面的代码是示例代码, 也就是说只有一个线程, 你需要改造成多线程的。 + Connection conn = null; + try { + cm = new ConnectionManagerImpl(); + conn = cm.open(this.url); + + int length = conn.getContentLength(); + String fileName = "test.jpg"; + Object obj = new Object(); + int part = 4; + int step = length / part; + for(int i = 0; i < part; i++){ + threadRun++; + new DownloadThread(cm.open(this.url), step * i,step * (i + 1) -1, fileName) + .setOnThreadFinished(new DownloadListener() { + + @Override + public void notifyFinished() { + synchronized (this) { + threadRun--; + if(threadRun==0){ + listener.notifyFinished(); + } + } + + } + }).start(); + } + + + } catch (ConnectionException e ) { + e.printStackTrace(); + }finally{ + if(conn != null){ + conn.close(); + } + } + } + + public void setListener(DownloadListener listener) { + this.listener = listener; + } + + + +// public void setConnectionManager(ConnectionManager ucm){ +// this.cm = ucm; +// } + + public DownloadListener getListener(){ + return this.listener; + } + +} diff --git a/group19/972815123/src/com/download/FileDownloaderTest.java b/group19/972815123/src/com/download/FileDownloaderTest.java new file mode 100644 index 0000000000..de22d5765e --- /dev/null +++ b/group19/972815123/src/com/download/FileDownloaderTest.java @@ -0,0 +1,52 @@ +package com.coderising.download; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import com.coderising.download.api.ConnectionManager; +import com.coderising.download.api.DownloadListener; +import com.coderising.download.impl.ConnectionManagerImpl; + +public class FileDownloaderTest { + boolean downloadFinished = false; + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testDownload() { + + String url = "http://img.sc115.com/uploads1/sc/jpgs/1504/fpic780_sc115.com.jpg"; + FileDownloader downloader = new FileDownloader(url); + +// ConnectionManager cm = new ConnectionManagerImpl(); +// downloader.setConnectionManager(cm); + + downloader.setListener(new DownloadListener() { + @Override + public void notifyFinished() { + downloadFinished = true; + } + }); + + downloader.execute(); + + // 等待多线程下载程序执行完毕 + while (!downloadFinished) { + try { + System.out.println("还没有下载完成,休眠五秒"); + //休眠5秒 + Thread.sleep(5000); + } catch (InterruptedException e) { + e.printStackTrace(); + } + } + System.out.println("下载完成!"); + } + +} diff --git a/group19/972815123/src/com/download/api/Connection.java b/group19/972815123/src/com/download/api/Connection.java new file mode 100644 index 0000000000..0957eaf7f4 --- /dev/null +++ b/group19/972815123/src/com/download/api/Connection.java @@ -0,0 +1,23 @@ +package com.coderising.download.api; + +import java.io.IOException; + +public interface Connection { + /** + * 给定开始和结束位置, 读取数据, 返回值是字节数组 + * @param startPos 开始位置, 从0开始 + * @param endPos 结束位置 + * @return + */ + public byte[] read(int startPos,int endPos) throws IOException; + /** + * 得到数据内容的长度 + * @return + */ + public int getContentLength(); + + /** + * 关闭连接 + */ + public void close(); +} diff --git a/group19/972815123/src/com/download/api/ConnectionException.java b/group19/972815123/src/com/download/api/ConnectionException.java new file mode 100644 index 0000000000..1551a80b3d --- /dev/null +++ b/group19/972815123/src/com/download/api/ConnectionException.java @@ -0,0 +1,5 @@ +package com.coderising.download.api; + +public class ConnectionException extends Exception { + +} diff --git a/group19/972815123/src/com/download/api/ConnectionManager.java b/group19/972815123/src/com/download/api/ConnectionManager.java new file mode 100644 index 0000000000..ce045393b1 --- /dev/null +++ b/group19/972815123/src/com/download/api/ConnectionManager.java @@ -0,0 +1,10 @@ +package com.coderising.download.api; + +public interface ConnectionManager { + /** + * 给定一个url , 打开一个连接 + * @param url + * @return + */ + public Connection open(String url) throws ConnectionException; +} diff --git a/group19/972815123/src/com/download/api/DownloadListener.java b/group19/972815123/src/com/download/api/DownloadListener.java new file mode 100644 index 0000000000..bf9807b307 --- /dev/null +++ b/group19/972815123/src/com/download/api/DownloadListener.java @@ -0,0 +1,5 @@ +package com.coderising.download.api; + +public interface DownloadListener { + public void notifyFinished(); +} diff --git a/group19/972815123/src/com/download/impl/ConnectionImpl.java b/group19/972815123/src/com/download/impl/ConnectionImpl.java new file mode 100644 index 0000000000..46c5aaf387 --- /dev/null +++ b/group19/972815123/src/com/download/impl/ConnectionImpl.java @@ -0,0 +1,46 @@ +package com.coderising.download.impl; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.net.HttpURLConnection; +import java.net.URLConnection; + +import com.coderising.download.api.Connection; + +public class ConnectionImpl implements Connection{ + + private URLConnection connect; + public void setHttpURLConnection(URLConnection conn){ + this.connect = conn; + this.connect.setRequestProperty("Connection", "Keep-Alive"); + } + + @Override + public byte[] read(int startPos, int endPos) throws IOException { + + InputStream is = connect.getInputStream(); + is.skip(startPos); + + byte[] buffer = new byte[1024]; + int hasRead = 0; + ByteArrayOutputStream out = new ByteArrayOutputStream(); + while(startPos < endPos && (hasRead = is.read(buffer, 0, 1024)) != -1){ + out.write(buffer, 0, hasRead); + startPos += hasRead; + } + + byte[] result = out.toByteArray(); + return result; + } + + @Override + public int getContentLength() { + return connect.getContentLength(); + } + + @Override + public void close() { + } + +} diff --git a/group19/972815123/src/com/download/impl/ConnectionManagerImpl.java b/group19/972815123/src/com/download/impl/ConnectionManagerImpl.java new file mode 100644 index 0000000000..7f16a4d1cd --- /dev/null +++ b/group19/972815123/src/com/download/impl/ConnectionManagerImpl.java @@ -0,0 +1,28 @@ +package com.coderising.download.impl; + +import java.io.IOException; +import java.net.HttpURLConnection; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.URLConnection; + +import com.coderising.download.api.Connection; +import com.coderising.download.api.ConnectionException; +import com.coderising.download.api.ConnectionManager; + +public class ConnectionManagerImpl implements ConnectionManager { + + @Override + public Connection open(String url) throws ConnectionException { + try { + URL u = new URL(url); + URLConnection conn = u.openConnection(); + ConnectionImpl connection = new ConnectionImpl(); + connection.setHttpURLConnection(conn); + return connection; + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } +}