From d70f309e4c60e9e58725e8f9baa72d1748256aae Mon Sep 17 00:00:00 2001 From: eulerlcs Date: Sun, 18 Jun 2017 22:01:26 +0900 Subject: [PATCH 01/73] season 01 commit --- students/41689722.eulerlcs/1.article/.gitkeep | 0 students/41689722.eulerlcs/2.code/.gitignore | 6 + .../2.code/jmr-01-aggregator/pom.xml | 20 + .../jmr-01-aggregator/src/site/.gitkeep | 0 .../2.code/jmr-02-parent/pom.xml | 148 ++++++ .../2.code/jmr-02-parent/src/site/.gitkeep | 0 .../data/shoppingcart/shoppingcart.data | Bin 0 -> 131 bytes .../data/xmlparser/app-config.xml | 12 + .../jmr-11-challenge/data/xmlparser/hello.xml | 5 + .../2.code/jmr-11-challenge/pom.xml | 48 ++ .../core/FileSystemClassLoader.java | 58 +++ .../classloader/core/ICalculator.java | 5 + .../classloader/core/NetworkClassLoader.java | 46 ++ .../challenge/classloader/core/Versioned.java | 5 + .../classloader/driver/CalculatorTest.java | 24 + .../classloader/driver/ClassIdentity.java | 36 ++ .../classloader/driver/ClassLoaderTree.java | 12 + .../challenge/classloader/package-info.java | 7 + .../sampleRename/CalculatorAdvanced.java | 15 + .../sampleRename/CalculatorBasic.java | 15 + .../classloader/sampleRename/Sample.java | 10 + .../challenge/systemrules/AppWithExit.java | 13 + .../challenge/systemrules/package-info.java | 5 + .../digester/core/HelloDigester.java | 17 + .../digester/core/HelloFileRulerSet.java | 28 ++ .../xmlparser/digester/driver/Driver.java | 28 ++ .../xmlparser/digester/entity/Hello.java | 19 + .../xmlparser/digester/entity/HelloFile.java | 11 + .../challenge/xmlparser/jaxb/AppConfig.java | 29 ++ .../jmr/challenge/xmlparser/jaxb/Driver.java | 20 + .../jmr/challenge/xmlparser/jaxb/Hello.java | 22 + .../challenge/xmlparser/jaxb/HelloFile.java | 14 + .../challenge/xmlparser/jaxb/JaxbParser.java | 22 + .../jmr/challenge/xmlparser/package-info.java | 13 + .../jmr/challenge/xmlparser/sax/Driver.java | 19 + .../xmlparser/sax/HelloSaxParser.java | 42 ++ .../challenge/zzz/master170219/Try170205.java | 132 ++++++ .../challenge/zzz/master170219/Try170212.java | 34 ++ .../challenge/zzz/master170219/Try170219.java | 47 ++ .../com/hoo/download/BatchDownloadFile.java | 227 +++++++++ .../java/com/hoo/download/DownloadFile.java | 176 +++++++ .../java/com/hoo/download/SaveItemFile.java | 68 +++ .../java/com/hoo/entity/DownloadInfo.java | 125 +++++ .../main/java/com/hoo/util/DownloadUtils.java | 40 ++ .../java/com/hoo/util/DownloadUtilsTest.java | 39 ++ .../src/main/java/com/hoo/util/LogUtils.java | 40 ++ .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 + .../jmr-11-challenge/src/test/java/.gitkeep | 0 .../systemrules/AppWithExitTest.java | 51 ++ .../src/test/resources/.gitkeep | 0 .../2.code/jmr-51-liuxin-question/pom.xml | 35 ++ .../coderising/download/api/Connection.java | 28 ++ .../download/api/ConnectionException.java | 5 + .../download/api/ConnectionManager.java | 11 + .../download/api/DownloadListener.java | 5 + .../download/core/DownloadThread.java | 21 + .../download/core/FileDownloader.java | 68 +++ .../download/impl/ConnectionImpl.java | 26 ++ .../download/impl/ConnectionManagerImpl.java | 15 + .../coderising/jvm/attr/AttributeInfo.java | 19 + .../com/coderising/jvm/attr/CodeAttr.java | 52 +++ .../coderising/jvm/attr/LineNumberTable.java | 46 ++ .../jvm/attr/LocalVariableItem.java | 49 ++ .../jvm/attr/LocalVariableTable.java | 25 + .../coderising/jvm/attr/StackMapTable.java | 29 ++ .../com/coderising/jvm/clz/AccessFlag.java | 26 ++ .../com/coderising/jvm/clz/ClassFile.java | 100 ++++ .../com/coderising/jvm/clz/ClassIndex.java | 22 + .../coderising/jvm/constant/ClassInfo.java | 28 ++ .../coderising/jvm/constant/ConstantInfo.java | 29 ++ .../coderising/jvm/constant/ConstantPool.java | 28 ++ .../coderising/jvm/constant/FieldRefInfo.java | 54 +++ .../jvm/constant/MethodRefInfo.java | 56 +++ .../jvm/constant/NameAndTypeInfo.java | 48 ++ .../jvm/constant/NullConstantInfo.java | 11 + .../coderising/jvm/constant/StringInfo.java | 28 ++ .../com/coderising/jvm/constant/UTF8Info.java | 37 ++ .../java/com/coderising/jvm/field/Field.java | 26 ++ .../jvm/loader/ByteCodeIterator.java | 55 +++ .../jvm/loader/ClassFileLoader.java | 122 +++++ .../jvm/loader/ClassFileParser.java | 146 ++++++ .../com/coderising/jvm/method/Method.java | 48 ++ .../java/com/coderising/jvm/util/Util.java | 22 + .../coderising/litestruts/LoginAction.java | 42 ++ .../com/coderising/litestruts/Struts.java | 30 ++ .../java/com/coderising/litestruts/View.java | 26 ++ .../main/java/com/coding/basic/ArrayList.java | 33 ++ .../main/java/com/coding/basic/ArrayUtil.java | 96 ++++ .../java/com/coding/basic/BinaryTreeNode.java | 37 ++ .../main/java/com/coding/basic/Iterator.java | 8 + .../java/com/coding/basic/LRUPageFrame.java | 50 ++ .../java/com/coding/basic/LinkedList.java | 126 +++++ .../src/main/java/com/coding/basic/List.java | 13 + .../src/main/java/com/coding/basic/Queue.java | 19 + .../java/com/coding/basic/stack/Stack.java | 26 ++ .../com/coding/basic/stack/StackUtil.java | 54 +++ .../coding/basic/stack/expr/InfixExpr.java | 13 + .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 + .../src/main/resources/struts.xml | 11 + .../download/core/FileDownloaderTest.java | 56 +++ .../jvm/loader/ClassFileloaderTest.java | 248 ++++++++++ .../com/coderising/jvm/loader/EmployeeV1.java | 30 ++ .../com/coderising/litestruts/StrutsTest.java | 38 ++ .../com/coding/basic/LRUPageFrameTest.java | 27 ++ .../com/coding/basic/stack/StackUtilTest.java | 78 ++++ .../basic/stack/expr/InfixExprTest.java | 45 ++ .../src/test/resources/.gitkeep | 0 .../2.code/jmr-52-liuxin-answer/pom.xml | 31 ++ .../coderising/download/api/Connection.java | 28 ++ .../download/api/ConnectionException.java | 8 + .../download/api/ConnectionManager.java | 11 + .../download/api/DownloadListener.java | 5 + .../download/core/DownloadThread.java | 50 ++ .../download/core/FileDownloader.java | 126 +++++ .../download/impl/ConnectionImpl.java | 84 ++++ .../download/impl/ConnectionManagerImpl.java | 15 + .../coderising/litestruts/Configuration.java | 113 +++++ .../litestruts/ConfigurationException.java | 21 + .../coderising/litestruts/LoginAction.java | 42 ++ .../coderising/litestruts/ReflectionUtil.java | 120 +++++ .../com/coderising/litestruts/Struts.java | 56 +++ .../java/com/coderising/litestruts/View.java | 26 ++ .../java/com/coding/basic/BinaryTreeNode.java | 37 ++ .../main/java/com/coding/basic/Iterator.java | 8 + .../src/main/java/com/coding/basic/List.java | 13 + .../src/main/java/com/coding/basic/Queue.java | 19 + .../com/coding/basic/array/ArrayList.java | 36 ++ .../com/coding/basic/array/ArrayUtil.java | 96 ++++ .../coding/basic/linklist/LRUPageFrame.java | 151 ++++++ .../com/coding/basic/linklist/LinkedList.java | 129 ++++++ .../java/com/coding/basic/stack/Stack.java | 26 ++ .../com/coding/basic/stack/StackUtil.java | 140 ++++++ .../coding/basic/stack/expr/InfixExpr.java | 15 + .../basic/stack/expr/InfixExprTest.java | 47 ++ .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 + .../src/main/resources/struts.xml | 11 + .../download/api/ConnectionTest.java | 42 ++ .../download/core/FileDownloaderTest.java | 56 +++ .../litestruts/ConfigurationTest.java | 46 ++ .../litestruts/ReflectionUtilTest.java | 104 +++++ .../com/coderising/litestruts/StrutsTest.java | 37 ++ .../basic/linklist/LRUPageFrameTest.java | 32 ++ .../coding/basic/linklist/LinkedListTest.java | 197 ++++++++ .../com/coding/basic/stack/StackUtilTest.java | 78 ++++ .../src/test/resources/.gitkeep | 0 .../2.code/jmr-61-collection/pom.xml | 27 ++ .../eulerlcs/jmr/algorithm/ArrayList.java | 438 ++++++++++++++++++ .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 + .../eulerlcs/jmr/algorithm/TestArrayList.java | 44 ++ .../src/test/resources/.gitkeep | 0 .../2.code/jmr-62-litestruts/data/struts.xml | 11 + .../2.code/jmr-62-litestruts/pom.xml | 39 ++ .../jmr-62-litestruts/src/main/java/.gitkeep | 0 .../eulerlcs/jmr/algorithm/ArrayUtil.java | 279 +++++++++++ .../jmr/litestruts/action/LoginAction.java | 30 ++ .../jmr/litestruts/action/LogoutAction.java | 30 ++ .../eulerlcs/jmr/litestruts/core/Struts.java | 200 ++++++++ .../eulerlcs/jmr/litestruts/core/View.java | 26 ++ .../jmr/litestruts/degister/StrutsAction.java | 22 + .../degister/StrutsActionResult.java | 13 + .../degister/StrutsActionRulerSet.java | 30 ++ .../jmr/litestruts/degister/StrutsConfig.java | 15 + .../litestruts/degister/StrutsDigester.java | 13 + .../src/main/resources/log4j.xml | 16 + .../jmr-62-litestruts/src/test/java/.gitkeep | 0 .../eulerlcs/jmr/algorithm/ArrayUtilTest.java | 266 +++++++++++ .../jmr/litestruts/core/StrutsTest.java | 38 ++ .../src/test/resources/.gitkeep | 0 .../2.code/jmr-63-download/data/.gitkeep | 0 .../2.code/jmr-63-download/pom.xml | 39 ++ .../eulerlcs/jmr/algorithm/Iterator.java | 8 + .../eulerlcs/jmr/algorithm/LinkedList.java | 126 +++++ .../github/eulerlcs/jmr/algorithm/List.java | 13 + .../eulerlcs/jmr/download/api/Connection.java | 28 ++ .../jmr/download/api/ConnectionException.java | 5 + .../jmr/download/api/ConnectionManager.java | 11 + .../jmr/download/api/DownloadListener.java | 5 + .../jmr/download/core/DownloadThread.java | 20 + .../jmr/download/core/FileDownloader.java | 64 +++ .../jmr/download/impl/ConnectionImpl.java | 25 + .../download/impl/ConnectionManagerImpl.java | 14 + .../src/main/resources/log4j.xml | 16 + .../jmr/download/core/FileDownloaderTest.java | 53 +++ .../src/test/resources/.gitkeep | 0 .../2.code/jmr-64-minijvm/data/.gitkeep | 0 .../2.code/jmr-64-minijvm/pom.xml | 43 ++ .../eulerlcs/jmr/algorithm/LRUPageFrame.java | 110 +++++ .../github/eulerlcs/jmr/algorithm/Stack.java | 24 + .../eulerlcs/jmr/algorithm/StackUtil.java | 43 ++ .../eulerlcs/jmr/jvm/attr/AttributeInfo.java | 19 + .../eulerlcs/jmr/jvm/attr/CodeAttr.java | 52 +++ .../jmr/jvm/attr/LineNumberTable.java | 46 ++ .../jmr/jvm/attr/LocalVariableItem.java | 49 ++ .../jmr/jvm/attr/LocalVariableTable.java | 25 + .../eulerlcs/jmr/jvm/attr/StackMapTable.java | 29 ++ .../eulerlcs/jmr/jvm/clz/AccessFlag.java | 26 ++ .../eulerlcs/jmr/jvm/clz/ClassFile.java | 100 ++++ .../eulerlcs/jmr/jvm/clz/ClassIndex.java | 22 + .../eulerlcs/jmr/jvm/constant/ClassInfo.java | 29 ++ .../jmr/jvm/constant/ConstantInfo.java | 29 ++ .../jmr/jvm/constant/ConstantPool.java | 28 ++ .../jmr/jvm/constant/FieldRefInfo.java | 54 +++ .../jmr/jvm/constant/MethodRefInfo.java | 56 +++ .../jmr/jvm/constant/NameAndTypeInfo.java | 50 ++ .../jmr/jvm/constant/NullConstantInfo.java | 11 + .../eulerlcs/jmr/jvm/constant/StringInfo.java | 28 ++ .../eulerlcs/jmr/jvm/constant/UTF8Info.java | 37 ++ .../github/eulerlcs/jmr/jvm/field/Field.java | 26 ++ .../jmr/jvm/loader/ByteCodeIterator.java | 55 +++ .../jmr/jvm/loader/ClassFileLoader.java | 74 +++ .../jmr/jvm/loader/ClassFileParser.java | 146 ++++++ .../eulerlcs/jmr/jvm/method/Method.java | 48 ++ .../github/eulerlcs/jmr/jvm/util/Util.java | 22 + .../src/main/resources/log4j.xml | 16 + .../jmr/algorithm/LRUPageFrameTest.java | 27 ++ .../jmr/jvm/loader/ClassFileloaderTest.java | 220 +++++++++ .../eulerlcs/jmr/jvm/loader/EmployeeV1.java | 28 ++ .../src/test/resources/.gitkeep | 0 .../5.settingfile/eclipsev45.epf | 186 ++++++++ .../5.settingfile/git cmd help.txt | 43 ++ .../tool.161118.git-source-copy.bat | 37 ++ .../tool.170330.java-maven-source-cleaner.bat | 37 ++ 226 files changed, 10138 insertions(+) create mode 100644 students/41689722.eulerlcs/1.article/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/.gitignore create mode 100644 students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-01-aggregator/src/site/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-02-parent/src/site/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/data/shoppingcart/shoppingcart.data create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/data/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/data/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/5.settingfile/eclipsev45.epf create mode 100644 students/41689722.eulerlcs/5.settingfile/git cmd help.txt create mode 100644 students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat create mode 100644 students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat diff --git a/students/41689722.eulerlcs/1.article/.gitkeep b/students/41689722.eulerlcs/1.article/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/.gitignore b/students/41689722.eulerlcs/2.code/.gitignore new file mode 100644 index 0000000000..c2be49c379 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/.gitignore @@ -0,0 +1,6 @@ +.metadata/ +.recommenders/ +**/.settings/ +**/target/ +**/.classpath +**/.project diff --git a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml b/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml new file mode 100644 index 0000000000..3edeb21d2e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml @@ -0,0 +1,20 @@ + + 4.0.0 + com.github.eulerlcs + jmr-01-aggregator + 0.0.1-SNAPSHOT + pom + eulerlcs master java road aggregator + + + ../jmr-02-parent + ../jmr-11-challenge + ../jmr-51-liuxin-question + ../jmr-52-liuxin-answer + ../jmr-61-collection + ../jmr-62-litestruts + ../jmr-63-download + ../jmr-64-minijvm + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/src/site/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-01-aggregator/src/site/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml b/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml new file mode 100644 index 0000000000..82b785a432 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml @@ -0,0 +1,148 @@ + + 4.0.0 + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + pom + eulerlcs master java road parent + + + + 1.7.24 + 4.12 + 2.17 + 1.8 + 1.8 + + + + + + org.apache.commons + commons-lang3 + 3.5 + + + org.apache.commons + commons-io + 1.3.2 + + + com.github.eulerlcs + jmr-61-collection + ${project.version} + + + commons-digester + commons-digester + 2.1 + + + org.jdom + jdom2 + 2.0.6 + + + dom4j + dom4j + 1.6.1 + + + org.projectlombok + lombok + 1.16.14 + provided + + + org.slf4j + slf4j-api + ${slf4j.version} + + + org.slf4j + slf4j-log4j12 + ${slf4j.version} + + + junit + junit + ${junit.version} + test + + + com.github.stefanbirkner + system-rules + 1.16.1 + test + + + + + + + + + org.apache.maven.plugins + maven-source-plugin + 3.0.1 + + + attach-source + + jar-no-fork + + + + + + org.apache.maven.plugins + maven-compiler-plugin + 3.6.1 + + ${maven.compiler.source} + ${maven.compiler.target} + + + + org.apache.maven.plugins + maven-jar-plugin + 3.0.2 + + + org.apache.maven.plugins + maven-javadoc-plugin + 2.10.4 + + true + 1.8 + protected + UTF-8 + UTF-8 + UTF-8 + + + + org.apache.maven.plugins + maven-surefire-plugin + 2.19.1 + + + org.apache.maven.plugins + maven-surefire-report-plugin + 2.19.1 + + true + + + + + + + + org.apache.maven.plugins + maven-source-plugin + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-02-parent/src/site/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-02-parent/src/site/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/shoppingcart/shoppingcart.data b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/shoppingcart/shoppingcart.data new file mode 100644 index 0000000000000000000000000000000000000000..336fd732b4dcf94a212cb3a8f2718aca7a10584b GIT binary patch literal 131 zcmZ=T{#&s4I+ra20|O5Ok5^(@qC$vnaYklQiG%X5hwke{s(~^b3>;t?-_mpkeYhwu zgRo0!cB+C`X?l82W?s62OMXsHu>=3>R=FL4Z-Cllq1pm6^Bjb~9_o+L_y!a;V&DTC O=ABxp;GB_|nFj!(-zjkb literal 0 HcmV?d00001 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml new file mode 100644 index 0000000000..e989327e9d --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml @@ -0,0 +1,12 @@ + + + a + b + c + d + e + f + g + h + i + diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml new file mode 100644 index 0000000000..748019e106 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml @@ -0,0 +1,5 @@ + + + a.txt + b.txt + diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml new file mode 100644 index 0000000000..589a5f69ee --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml @@ -0,0 +1,48 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-11-challenge + eulerlcs master java road challenge + + + + + commons-digester + commons-digester + + + org.jdom + jdom2 + + + dom4j + dom4j + + + org.projectlombok + lombok + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + com.github.stefanbirkner + system-rules + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java new file mode 100644 index 0000000000..82c8b60d56 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java @@ -0,0 +1,58 @@ +package com.github.eulerlcs.jmr.challenge.classloader.core; + +import java.io.ByteArrayOutputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStream; + +public class FileSystemClassLoader extends ClassLoader { + + private String rootDir; + + public FileSystemClassLoader(String rootDir) { + this.rootDir = rootDir; + } + + @Override + protected Class findClass(String name) throws ClassNotFoundException { + byte[] classData = getClassData(name); + if (classData == null) { + throw new ClassNotFoundException(); + } else { + return defineClass(name, classData, 0, classData.length); + } + } + + private byte[] getClassData(String className) { + String path = classNameToPath(className); + InputStream ins = null; + try { + ins = new FileInputStream(path); + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + int bufferSize = 4096; + byte[] buffer = new byte[bufferSize]; + int bytesNumRead = 0; + while ((bytesNumRead = ins.read(buffer)) != -1) { + baos.write(buffer, 0, bytesNumRead); + } + return baos.toByteArray(); + } catch (IOException e) { + e.printStackTrace(); + } finally { + if (ins != null) { + try { + ins.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + + return null; + } + + private String classNameToPath(String className) { + return rootDir + File.separatorChar + className.replace('.', File.separatorChar) + ".class"; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java new file mode 100644 index 0000000000..697bf8065f --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java @@ -0,0 +1,5 @@ +package com.github.eulerlcs.jmr.challenge.classloader.core; + +public interface ICalculator extends Versioned { + String calculate(String expression); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java new file mode 100644 index 0000000000..c0f524a1b4 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java @@ -0,0 +1,46 @@ +package com.github.eulerlcs.jmr.challenge.classloader.core; + +import java.io.ByteArrayOutputStream; +import java.io.InputStream; +import java.net.URL; + +public class NetworkClassLoader extends ClassLoader { + + private String rootUrl; + + public NetworkClassLoader(String rootUrl) { + this.rootUrl = rootUrl; + } + + protected Class findClass(String name) throws ClassNotFoundException { + byte[] classData = getClassData(name); + if (classData == null) { + throw new ClassNotFoundException(); + } else { + return defineClass(name, classData, 0, classData.length); + } + } + + private byte[] getClassData(String className) { + String path = classNameToPath(className); + try { + URL url = new URL(path); + InputStream ins = url.openStream(); + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + int bufferSize = 4096; + byte[] buffer = new byte[bufferSize]; + int bytesNumRead = 0; + while ((bytesNumRead = ins.read(buffer)) != -1) { + baos.write(buffer, 0, bytesNumRead); + } + return baos.toByteArray(); + } catch (Exception e) { + e.printStackTrace(); + } + return null; + } + + private String classNameToPath(String className) { + return rootUrl + "/" + className.replace('.', '/') + ".class"; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java new file mode 100644 index 0000000000..34dfacbbd1 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java @@ -0,0 +1,5 @@ +package com.github.eulerlcs.jmr.challenge.classloader.core; + +public interface Versioned { + String getVersion(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java new file mode 100644 index 0000000000..d19ee1dbe0 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java @@ -0,0 +1,24 @@ +package com.github.eulerlcs.jmr.challenge.classloader.driver; + +import com.github.eulerlcs.jmr.challenge.classloader.core.ICalculator; +import com.github.eulerlcs.jmr.challenge.classloader.core.NetworkClassLoader; + +public class CalculatorTest { + + public static void main(String[] args) { + String url = "http://localhost:8080/ClassloaderTest/classes"; + NetworkClassLoader ncl = new NetworkClassLoader(url); + String basicClassName = "com.example.CalculatorBasic"; + String advancedClassName = "com.example.CalculatorAdvanced"; + try { + Class clazz = ncl.loadClass(basicClassName); + ICalculator calculator = (ICalculator) clazz.newInstance(); + System.out.println(calculator.getVersion()); + clazz = ncl.loadClass(advancedClassName); + calculator = (ICalculator) clazz.newInstance(); + System.out.println(calculator.getVersion()); + } catch (Exception e) { + e.printStackTrace(); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java new file mode 100644 index 0000000000..3a9226b8ca --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java @@ -0,0 +1,36 @@ +package com.github.eulerlcs.jmr.challenge.classloader.driver; + +import java.io.File; +import java.lang.reflect.Method; + +import com.github.eulerlcs.jmr.challenge.classloader.core.FileSystemClassLoader; + +public class ClassIdentity { + + public static void main(String[] args) { + new ClassIdentity().testClassIdentity(); + } + + public void testClassIdentity() { + String userDir = System.getProperty("user.dir"); + String classDataRootPath = userDir + File.separator + "data" + File.separator + "classloader"; + + FileSystemClassLoader fscl1 = new FileSystemClassLoader(classDataRootPath); + FileSystemClassLoader fscl2 = new FileSystemClassLoader(classDataRootPath); + String className = "com.github.eulerlcs.jmr.challenge.classloader.sample.Sample"; + + try { + Class class1 = fscl1.loadClass(className); + Object obj1 = class1.newInstance(); + + Class class2 = fscl2.loadClass(className); + Object obj2 = class2.newInstance(); + + Method setSampleMethod = class1.getMethod("setSample", java.lang.Object.class); + + setSampleMethod.invoke(obj1, obj2); + } catch (Exception e) { + e.printStackTrace(); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java new file mode 100644 index 0000000000..38916b6db5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java @@ -0,0 +1,12 @@ +package com.github.eulerlcs.jmr.challenge.classloader.driver; + +public class ClassLoaderTree { + + public static void main(String[] args) { + ClassLoader loader = ClassLoaderTree.class.getClassLoader(); + while (loader != null) { + System.out.println(loader.toString()); + loader = loader.getParent(); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java new file mode 100644 index 0000000000..d35a4ee992 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java @@ -0,0 +1,7 @@ +/** + * download from ibm developerworks + * + * @see https://www.ibm.com/developerworks/cn/java/j-lo-classloader/ + */ +package com.github.eulerlcs.jmr.challenge.classloader; \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java new file mode 100644 index 0000000000..9076a4f4c8 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java @@ -0,0 +1,15 @@ +package com.github.eulerlcs.jmr.challenge.classloader.sampleRename; + +import com.github.eulerlcs.jmr.challenge.classloader.core.ICalculator; + +public class CalculatorAdvanced implements ICalculator { + + public String calculate(String expression) { + return "Result is " + expression; + } + + public String getVersion() { + return "2.0"; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java new file mode 100644 index 0000000000..d5f7b054dd --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java @@ -0,0 +1,15 @@ +package com.github.eulerlcs.jmr.challenge.classloader.sampleRename; + +import com.github.eulerlcs.jmr.challenge.classloader.core.ICalculator; + +public class CalculatorBasic implements ICalculator { + + public String calculate(String expression) { + return expression; + } + + public String getVersion() { + return "1.0"; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java new file mode 100644 index 0000000000..c67a7278e8 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java @@ -0,0 +1,10 @@ +package com.github.eulerlcs.jmr.challenge.classloader.sampleRename; + +public class Sample { + @SuppressWarnings("unused") + private Sample instance; + + public void setSample(Object instance) { + this.instance = (Sample) instance; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java new file mode 100644 index 0000000000..2afd5b2074 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java @@ -0,0 +1,13 @@ +package com.github.eulerlcs.jmr.challenge.systemrules; + +public class AppWithExit { + public static String message; + + public static void doSomethingAndExit() { + message = "exit ..."; + System.exit(1); + } + + public static void doNothing() { + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java new file mode 100644 index 0000000000..1710e69d47 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java @@ -0,0 +1,5 @@ +/** + * copy from http://stefanbirkner.github.io/system-rules/index.html + */ + +package com.github.eulerlcs.jmr.challenge.systemrules; \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java new file mode 100644 index 0000000000..3f58d74c7f --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java @@ -0,0 +1,17 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.digester.core; + +import org.apache.commons.digester.Digester; + +import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.Hello; + +public class HelloDigester { + public static Digester newInstance() { + Digester d = new Digester(); + + d.addObjectCreate("files", Hello.class); + d.addSetProperties("files"); + d.addRuleSet(new HelloFileRulerSet("files/")); + + return d; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java new file mode 100644 index 0000000000..3d62c8c93e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java @@ -0,0 +1,28 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.digester.core; + +import org.apache.commons.digester.Digester; +import org.apache.commons.digester.RuleSetBase; + +import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.HelloFile; + +final class HelloFileRulerSet extends RuleSetBase { + protected String prefix = null; + + public HelloFileRulerSet() { + this(""); + } + + public HelloFileRulerSet(String prefix) { + super(); + this.namespaceURI = null; + this.prefix = prefix; + } + + @Override + public void addRuleInstances(Digester digester) { + digester.addObjectCreate(prefix + "file", HelloFile.class); + digester.addSetProperties(prefix + "file", "dir", "path"); + digester.addBeanPropertySetter(prefix + "file", "name"); + digester.addSetNext(prefix + "file", "addFile"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java new file mode 100644 index 0000000000..59a2987909 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java @@ -0,0 +1,28 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.digester.driver; + +import java.io.File; +import java.io.IOException; + +import org.apache.commons.digester.Digester; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.xml.sax.SAXException; + +import com.github.eulerlcs.jmr.challenge.xmlparser.digester.core.HelloDigester; +import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.Hello; + +public class Driver { + private final static Logger log = LoggerFactory.getLogger(Driver.class); + + public static void main(String[] args) { + Digester d = HelloDigester.newInstance(); + + try { + File file = new File("data//xmlparser", "hello.xml"); + Hello helloEntity = (Hello) d.parse(file); + log.debug("hello.value=[{}]", helloEntity.getValue()); + } catch (IOException | SAXException e) { + e.printStackTrace(); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java new file mode 100644 index 0000000000..415dbef23a --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java @@ -0,0 +1,19 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity; + +import java.util.ArrayList; +import java.util.List; + +import lombok.Getter; +import lombok.Setter; + +@Getter +@Setter +public class Hello { + private String project; + private String value; + private List files = new ArrayList<>(); + + public void addFile(HelloFile file) { + files.add(file); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java new file mode 100644 index 0000000000..2892a3058e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java @@ -0,0 +1,11 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity; + +import lombok.Getter; +import lombok.Setter; + +@Getter +@Setter +public class HelloFile { + private String path; + private String name; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java new file mode 100644 index 0000000000..c50bce4a15 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java @@ -0,0 +1,29 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; + +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; + +import lombok.Getter; + +@Getter +@XmlRootElement(name = "app-config") +public class AppConfig { + @XmlElement(name = "input-path") + private String inputPath; + @XmlElement(name = "input-look-subfolder") + private boolean inputLookSubfolder; + @XmlElement(name = "input-encode") + private String inputEncode; + @XmlElement(name = "output-path") + private String outputPath; + @XmlElement(name = "output-by-package-tree") + private boolean outputByPackageTree; + @XmlElement(name = "output-prefix") + private String outputPrefix; + @XmlElement(name = "output-subfix") + private String outputSubfix; + @XmlElement(name = "output-encode") + private String outputEncode; + @XmlElement(name = "output-package-name") + private String outputPackageName; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java new file mode 100644 index 0000000000..15c5686e2e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java @@ -0,0 +1,20 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; + +import java.io.File; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +public class Driver { + private final static Logger log = LoggerFactory.getLogger(Driver.class); + + public static void main(String[] args) { + File xml = new File("data//xmlparser", "hello.xml"); + Hello hello = JaxbParser.loadAppConfig(xml, Hello.class); + log.debug("hello.value=[{}]", hello.getValue()); + + xml = new File("data//xmlparser", "app-config.xml"); + AppConfig appConfig = JaxbParser.loadAppConfig(xml, AppConfig.class); + log.debug("process-args.InputPath=[{}] ", appConfig.getInputPath()); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java new file mode 100644 index 0000000000..5bad90241e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java @@ -0,0 +1,22 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; + +import java.util.List; + +import javax.xml.bind.annotation.XmlAttribute; +import javax.xml.bind.annotation.XmlElement; +import javax.xml.bind.annotation.XmlRootElement; + +import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.HelloFile; + +import lombok.Getter; + +@Getter +@XmlRootElement(name = "files") +public class Hello { + @XmlAttribute + private String project; + @XmlAttribute + private String value; + @XmlElement(name = "file") + private List files; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java new file mode 100644 index 0000000000..c5bdd127f1 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java @@ -0,0 +1,14 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; + +import javax.xml.bind.annotation.XmlAttribute; +import javax.xml.bind.annotation.XmlValue; + +import lombok.Getter; + +@Getter +public class HelloFile { + @XmlAttribute(name = "dir") + private String path; + @XmlValue + private String name; +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java new file mode 100644 index 0000000000..720f524426 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java @@ -0,0 +1,22 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; + +import java.io.File; + +import javax.xml.bind.JAXBContext; +import javax.xml.bind.Unmarshaller; + +/* jaxb: Java Architecture for XML Binding */ +public class JaxbParser { + @SuppressWarnings("unchecked") + public static E loadAppConfig(File xml, Class clazz) { + E entity = null; + try { + JAXBContext jc = JAXBContext.newInstance(clazz); + Unmarshaller u = jc.createUnmarshaller(); + entity = (E) u.unmarshal(xml); + } catch (Exception e) { + e.printStackTrace(); + } + return entity; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java new file mode 100644 index 0000000000..4f7a71c4bc --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java @@ -0,0 +1,13 @@ +/** + * 各种xml库 + *
    + *
  • apache digester + *
  • dom + *
  • dom4j + *
  • ldom + *
  • jaxb + *
  • sax + *
+ */ + +package com.github.eulerlcs.jmr.challenge.xmlparser; \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java new file mode 100644 index 0000000000..d15739c5c9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java @@ -0,0 +1,19 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.sax; + +import java.io.File; + +import javax.xml.parsers.SAXParser; +import javax.xml.parsers.SAXParserFactory; + +public class Driver { + public static void main(String[] args) { + SAXParserFactory factory = SAXParserFactory.newInstance(); + File xml = new File("data//xmlparser", "hello.xml"); + try { + SAXParser parser = factory.newSAXParser(); + parser.parse(xml, new HelloSaxParser()); + } catch (Exception e) { + e.printStackTrace(); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java new file mode 100644 index 0000000000..26cc926b11 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java @@ -0,0 +1,42 @@ +package com.github.eulerlcs.jmr.challenge.xmlparser.sax; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.xml.sax.Attributes; +import org.xml.sax.SAXException; +import org.xml.sax.helpers.DefaultHandler; + +/* sax: simple api for xml */ +public class HelloSaxParser extends DefaultHandler { + protected static Logger log = LoggerFactory.getLogger(HelloSaxParser.class); + + @Override + public void startDocument() throws SAXException { + super.startDocument(); + log.debug("sax startDocument"); + } + + @Override + public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { + super.startElement(uri, localName, qName, attributes); + log.debug("sax startElement qName: [{}]", qName); + } + + @Override + public void characters(char[] ch, int start, int length) throws SAXException { + super.characters(ch, start, length); + log.debug("sax characters: [{}]", new String(ch, start, length)); + } + + @Override + public void endElement(String uri, String localName, String qName) throws SAXException { + super.endElement(uri, localName, qName); + log.debug("sax endElement qName: [{}]", qName); + } + + @Override + public void endDocument() throws SAXException { + super.endDocument(); + log.debug("sax endDocument"); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java new file mode 100644 index 0000000000..b18db9d387 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java @@ -0,0 +1,132 @@ +package com.github.eulerlcs.jmr.challenge.zzz.master170219; + +import java.io.DataInputStream; +import java.io.FileInputStream; +import java.io.IOException; +import java.lang.reflect.Constructor; +import java.lang.reflect.Field; +import java.lang.reflect.Method; +import java.util.ArrayList; + +public class Try170205 { + public static void main(String[] args) throws Exception { + task94(); + task93(); + task84(); + task83(); + task65(); + task64(); + + ArrayList list = new ArrayList(); + show(list); + } + + public static void show(ArrayList list) { + // .... + } + + public static void task64() { + DataInputStream dis = null; + double price = 0; + int count = 0; + double sum = 0; + String disp = ""; + + try { + dis = new DataInputStream(new FileInputStream("data/shoppingcart.data")); + while (dis.available() > 0) { + price = dis.readDouble(); + count = dis.readInt(); + disp = dis.readUTF(); + System.out.println(disp); + sum += price * count; + } + + System.out.println("sum=" + sum); + } catch (IOException e) { + e.printStackTrace(); + } finally { + try { + dis.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + + } + + public static void task65() { + DataInputStream dis = null; + byte[] magic = { (byte) 0xca, (byte) 0xfe, (byte) 0xba, (byte) 0xbe }; + boolean ret = true; + + try { + dis = new DataInputStream(new FileInputStream("data/sc.class")); + for (int i = 0; i < 4; i++) { + if (magic[i] != dis.readByte()) { + ret = false; + break; + } + } + } catch (IOException e) { + e.printStackTrace(); + } finally { + try { + dis.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + + if (ret) { + System.out.println("it is cafebabe"); + } else { + System.out.println("it is not cafebabe"); + } + } + + public static void task83() throws Exception { + Class clazz = Class.forName("shoppingcart.Employee"); + Constructor ct = clazz.getConstructor(String.class, int.class); + Object obj = ct.newInstance("ref", 22); + + Method sayHello = clazz.getDeclaredMethod("sayHello"); + sayHello.invoke(obj); + + Method getID = clazz.getDeclaredMethod("getID"); + getID.setAccessible(true); + String ids = (String) getID.invoke(obj); + System.out.println("getID=" + ids); + + Field[] flds = clazz.getDeclaredFields(); + for (Field fld : flds) { + System.out.println(fld); + } + } + + public static void task84() throws Exception { + ArrayList list = new ArrayList<>(); + list.add(3232); + + Class clazz = ArrayList.class; + + Field elementDataField = clazz.getDeclaredField("elementData"); + elementDataField.setAccessible(true); + Object[] elementData = (Object[]) elementDataField.get(list); + if (elementData.length > 1) { + elementData[1] = "added by reflection"; + } + } + + public static void task93() { + ArrayList list1 = new ArrayList(); + ArrayList list2 = new ArrayList(); + System.out.println(list1.getClass().equals(list2.getClass())); + } + + public static void task94() { + ArrayList numbers = new ArrayList(); + numbers.add(new Integer(10)); + numbers.add(new Double(10.0d)); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java new file mode 100644 index 0000000000..5492441572 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java @@ -0,0 +1,34 @@ +package com.github.eulerlcs.jmr.challenge.zzz.master170219; + +public class Try170212 { + + public static void main(String[] args) { + t28(); + } + + public static void changeStr(String str) { + str = "welcome"; + } + + public static void t28() { + String str = "1234"; + changeStr(str); + System.out.println(str); + } + + public static void t34() { + Try170212 x = new Try170212(); + Try170212.Hello obj = x.new Hello(""); + obj.msg += ",World!"; + System.out.println(obj.msg); + } + + class Hello { + public String msg = "Hello"; + + public Hello(String msg) { + this.msg = msg; + } + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java new file mode 100644 index 0000000000..559dc44a7c --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java @@ -0,0 +1,47 @@ +package com.github.eulerlcs.jmr.challenge.zzz.master170219; + +import java.util.ArrayList; +import java.util.Date; + +public class Try170219 { + public static void main(String[] args) { + Integer[] a = new Integer[10]; + case003(a); + } + + public static void case001() { + Fruit f = new Apple(); + f.setDate(new Date()); + } + + public static void case002() { + ArrayList list1 = new ArrayList(); + ArrayList list2 = new ArrayList(); + System.out.println(list1.getClass().equals(list2.getClass())); + } + + public static void case003(Number[] n) { + // nop + } + +} + +class Fruit { + public void setDate(Object d) { + System.out.println("Fruit.setDate(Object d)"); + } + + // public void setDate2(Object d) { + // System.out.println("Fruit.setDate(Object d)"); + // } +} + +class Apple extends Fruit { + public void setDate(Date d) { + System.out.println("Apple.setDate(Date d)"); + } + + public void setDate2(Date d) { + System.out.println("Apple.setDate(Date d)"); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java new file mode 100644 index 0000000000..48b4f67670 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java @@ -0,0 +1,227 @@ +package com.hoo.download; + +import java.io.DataInputStream; +import java.io.DataOutputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.net.HttpURLConnection; +import java.net.MalformedURLException; +import java.net.URL; + +import com.hoo.entity.DownloadInfo; +import com.hoo.util.LogUtils; + +/** + * function: 分批量下载文件 + * + * @author hoojo + * @createDate 2011-9-22 下午05:51:54 + * @file BatchDownloadFile.java + * @package com.hoo.download + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public class BatchDownloadFile implements Runnable { + // 下载文件信息 + private DownloadInfo downloadInfo; + // 一组开始下载位置 + private long[] startPos; + // 一组结束下载位置 + private long[] endPos; + // 休眠时间 + private static final int SLEEP_SECONDS = 500; + // 子线程下载 + private DownloadFile[] fileItem; + // 文件长度 + private int length; + // 是否第一个文件 + private boolean first = true; + // 是否停止下载 + private boolean stop = false; + // 临时文件信息 + private File tempFile; + + public BatchDownloadFile(DownloadInfo downloadInfo) { + this.downloadInfo = downloadInfo; + String tempPath = this.downloadInfo.getFilePath() + File.separator + downloadInfo.getFileName() + ".position"; + tempFile = new File(tempPath); + // 如果存在读入点位置的文件 + if (tempFile.exists()) { + first = false; + // 就直接读取内容 + try { + readPosInfo(); + } catch (IOException e) { + e.printStackTrace(); + } + } else { + // 数组的长度就要分成多少段的数量 + startPos = new long[downloadInfo.getSplitter()]; + endPos = new long[downloadInfo.getSplitter()]; + } + } + + @Override + public void run() { + // 首次下载,获取下载文件长度 + if (first) { + length = this.getFileSize();// 获取文件长度 + if (length == -1) { + LogUtils.log("file length is know!"); + stop = true; + } else if (length == -2) { + LogUtils.log("read file length is error!"); + stop = true; + } else if (length > 0) { + /** + * eg start: 1, 3, 5, 7, 9 end: 3, 5, 7, 9, length + */ + for (int i = 0, len = startPos.length; i < len; i++) { + int size = i * (length / len); + startPos[i] = size; + + // 设置最后一个结束点的位置 + if (i == len - 1) { + endPos[i] = length; + } else { + size = (i + 1) * (length / len); + endPos[i] = size; + } + LogUtils.log("start-end Position[" + i + "]: " + startPos[i] + "-" + endPos[i]); + } + } else { + LogUtils.log("get file length is error, download is stop!"); + stop = true; + } + } + + // 子线程开始下载 + if (!stop) { + // 创建单线程下载对象数组 + fileItem = new DownloadFile[startPos.length];// startPos.length = + // downloadInfo.getSplitter() + for (int i = 0; i < startPos.length; i++) { + try { + // 创建指定个数单线程下载对象,每个线程独立完成指定块内容的下载 + fileItem[i] = new DownloadFile(downloadInfo.getUrl(), + this.downloadInfo.getFilePath() + File.separator + downloadInfo.getFileName(), startPos[i], + endPos[i], i); + fileItem[i].start();// 启动线程,开始下载 + LogUtils.log("Thread: " + i + ", startPos: " + startPos[i] + ", endPos: " + endPos[i]); + } catch (IOException e) { + e.printStackTrace(); + } + } + + // 循环写入下载文件长度信息 + while (!stop) { + try { + writePosInfo(); + LogUtils.log("downloading……"); + Thread.sleep(SLEEP_SECONDS); + stop = true; + } catch (IOException e) { + e.printStackTrace(); + } catch (InterruptedException e) { + e.printStackTrace(); + } + for (int i = 0; i < startPos.length; i++) { + if (!fileItem[i].isDownloadOver()) { + stop = false; + break; + } + } + } + LogUtils.info("Download task is finished!"); + } + } + + /** + * 将写入点数据保存在临时文件中 + * + * @author hoojo + * @createDate 2011-9-23 下午05:25:37 + * @throws IOException + */ + private void writePosInfo() throws IOException { + DataOutputStream dos = new DataOutputStream(new FileOutputStream(tempFile)); + dos.writeInt(startPos.length); + for (int i = 0; i < startPos.length; i++) { + dos.writeLong(fileItem[i].getStartPos()); + dos.writeLong(fileItem[i].getEndPos()); + // LogUtils.info("[" + fileItem[i].getStartPos() + "#" + + // fileItem[i].getEndPos() + "]"); + } + dos.close(); + } + + /** + * function:读取写入点的位置信息 + * + * @author hoojo + * @createDate 2011-9-23 下午05:30:29 + * @throws IOException + */ + private void readPosInfo() throws IOException { + DataInputStream dis = new DataInputStream(new FileInputStream(tempFile)); + int startPosLength = dis.readInt(); + startPos = new long[startPosLength]; + endPos = new long[startPosLength]; + for (int i = 0; i < startPosLength; i++) { + startPos[i] = dis.readLong(); + endPos[i] = dis.readLong(); + } + dis.close(); + } + + /** + * function: 获取下载文件的长度 + * + * @author hoojo + * @createDate 2011-9-26 下午12:15:08 + * @return + */ + private int getFileSize() { + int fileLength = -1; + try { + URL url = new URL(this.downloadInfo.getUrl()); + HttpURLConnection conn = (HttpURLConnection) url.openConnection(); + + DownloadFile.setHeader(conn); + + int stateCode = conn.getResponseCode(); + // 判断http status是否为HTTP/1.1 206 Partial Content或者200 OK + if (stateCode != HttpURLConnection.HTTP_OK && stateCode != HttpURLConnection.HTTP_PARTIAL) { + LogUtils.log("Error Code: " + stateCode); + return -2; + } else if (stateCode >= 400) { + LogUtils.log("Error Code: " + stateCode); + return -2; + } else { + // 获取长度 + fileLength = conn.getContentLength(); + LogUtils.log("FileLength: " + fileLength); + } + + // 读取文件长度 + /* + * for (int i = 1; ; i++) { String header = + * conn.getHeaderFieldKey(i); if (header != null) { if + * ("Content-Length".equals(header)) { fileLength = + * Integer.parseInt(conn.getHeaderField(i)); break; } } else { + * break; } } + */ + + DownloadFile.printHeader(conn); + } catch (MalformedURLException e) { + e.printStackTrace(); + } catch (IOException e) { + e.printStackTrace(); + } + return fileLength; + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java new file mode 100644 index 0000000000..784efa1d88 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java @@ -0,0 +1,176 @@ +package com.hoo.download; + +import java.io.IOException; +import java.io.InputStream; +import java.net.HttpURLConnection; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.URLConnection; + +import com.hoo.util.LogUtils; + +/** + * function: 单线程下载文件 + * + * @author hoojo + * @createDate 2011-9-22 下午02:55:10 + * @file DownloadFile.java + * @package com.hoo.download + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public class DownloadFile extends Thread { + + // 下载文件url + private String url; + // 下载文件起始位置 + private long startPos; + // 下载文件结束位置 + private long endPos; + // 线程id + private int threadId; + + // 下载是否完成 + private boolean isDownloadOver = false; + + private SaveItemFile itemFile; + + private static final int BUFF_LENGTH = 1024 * 8; + + /** + * @param url + * 下载文件url + * @param name + * 文件名称 + * @param startPos + * 下载文件起点 + * @param endPos + * 下载文件结束点 + * @param threadId + * 线程id + * @throws IOException + */ + public DownloadFile(String url, String name, long startPos, long endPos, int threadId) throws IOException { + super(); + this.url = url; + this.startPos = startPos; + this.endPos = endPos; + this.threadId = threadId; + // 分块下载写入文件内容 + this.itemFile = new SaveItemFile(name, startPos); + } + + @Override + public void run() { + while (endPos > startPos && !isDownloadOver) { + try { + URL url = new URL(this.url); + HttpURLConnection conn = (HttpURLConnection) url.openConnection(); + + // 设置连接超时时间为10000ms + conn.setConnectTimeout(10000); + // 设置读取数据超时时间为10000ms + conn.setReadTimeout(10000); + + setHeader(conn); + + String property = "bytes=" + startPos + "-"; + conn.setRequestProperty("RANGE", property); + + // 输出log信息 + LogUtils.log("开始 " + threadId + ":" + property + endPos); + // printHeader(conn); + + // 获取文件输入流,读取文件内容 + InputStream is = conn.getInputStream(); + + byte[] buff = new byte[BUFF_LENGTH]; + int length = -1; + LogUtils.log("#start#Thread: " + threadId + ", startPos: " + startPos + ", endPos: " + endPos); + while ((length = is.read(buff)) > 0 && startPos < endPos && !isDownloadOver) { + // 写入文件内容,返回最后写入的长度 + startPos += itemFile.write(buff, 0, length); + } + LogUtils.log("#over#Thread: " + threadId + ", startPos: " + startPos + ", endPos: " + endPos); + LogUtils.log("Thread " + threadId + " is execute over!"); + this.isDownloadOver = true; + } catch (MalformedURLException e) { + e.printStackTrace(); + } catch (IOException e) { + e.printStackTrace(); + } finally { + try { + if (itemFile != null) { + itemFile.close(); + } + } catch (IOException e) { + e.printStackTrace(); + } + } + } + if (endPos < startPos && !isDownloadOver) { + LogUtils.log("Thread " + threadId + " startPos > endPos, not need download file !"); + this.isDownloadOver = true; + } + if (endPos == startPos && !isDownloadOver) { + LogUtils.log("Thread " + threadId + " startPos = endPos, not need download file !"); + this.isDownloadOver = true; + } + } + + /** + * function: 打印下载文件头部信息 + * + * @author hoojo + * @createDate 2011-9-22 下午05:44:35 + * @param conn + * HttpURLConnection + */ + public static void printHeader(URLConnection conn) { + int i = 1; + while (true) { + String header = conn.getHeaderFieldKey(i); + i++; + if (header != null) { + LogUtils.info(header + ":" + conn.getHeaderField(i)); + } else { + break; + } + } + } + + /** + * function: 设置URLConnection的头部信息,伪装请求信息 + * + * @author hoojo + * @createDate 2011-9-28 下午05:29:43 + * @param con + */ + public static void setHeader(URLConnection conn) { + conn.setRequestProperty("User-Agent", + "Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.0.3) Gecko/2008092510 Ubuntu/8.04 (hardy) Firefox/3.0.3"); + conn.setRequestProperty("Accept-Language", "en-us,en;q=0.7,zh-cn;q=0.3"); + conn.setRequestProperty("Accept-Encoding", "utf-8"); + conn.setRequestProperty("Accept-Charset", "ISO-8859-1,utf-8;q=0.7,*;q=0.7"); + conn.setRequestProperty("Keep-Alive", "300"); + conn.setRequestProperty("connnection", "keep-alive"); + conn.setRequestProperty("If-Modified-Since", "Fri, 02 Jan 2009 17:00:05 GMT"); + conn.setRequestProperty("If-None-Match", "\"1261d8-4290-df64d224\""); + conn.setRequestProperty("Cache-conntrol", "max-age=0"); + conn.setRequestProperty("Referer", "https://www.github.com"); + } + + public boolean isDownloadOver() { + return isDownloadOver; + } + + public long getStartPos() { + return startPos; + } + + public long getEndPos() { + return endPos; + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java new file mode 100644 index 0000000000..c0dcb62ac3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java @@ -0,0 +1,68 @@ +package com.hoo.download; + +import java.io.IOException; +import java.io.RandomAccessFile; + +/** + * function: 写入文件、保存文件 + * + * @author hoojo + * @createDate 2011-9-21 下午05:44:02 + * @file SaveItemFile.java + * @package com.hoo.download + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public class SaveItemFile { + // 存储文件 + private RandomAccessFile itemFile; + + public SaveItemFile() throws IOException { + this("", 0); + } + + /** + * @param name + * 文件路径、名称 + * @param pos + * 写入点位置 position + * @throws IOException + */ + public SaveItemFile(String name, long pos) throws IOException { + itemFile = new RandomAccessFile(name, "rw"); + // 在指定的pos位置开始写入数据 + itemFile.seek(pos); + } + + /** + * function: 同步方法写入文件 + * + * @author hoojo + * @createDate 2011-9-26 下午12:21:22 + * @param buff + * 缓冲数组 + * @param start + * 起始位置 + * @param length + * 长度 + * @return + */ + public synchronized int write(byte[] buff, int start, int length) { + int i = -1; + try { + itemFile.write(buff, start, length); + i = length; + } catch (IOException e) { + e.printStackTrace(); + } + return i; + } + + public void close() throws IOException { + if (itemFile != null) { + itemFile.close(); + } + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java new file mode 100644 index 0000000000..7ef4ba5477 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java @@ -0,0 +1,125 @@ + +package com.hoo.entity; + +/** + * function: 下载文件信息类 + * + * @author hoojo + * @createDate 2011-9-21 下午05:14:58 + * @file DownloadInfo.java + * @package com.hoo.entity + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public class DownloadInfo { + // 下载文件url + private String url; + // 下载文件名称 + private String fileName; + // 下载文件路径 + private String filePath; + // 分成多少段下载, 每一段用一个线程完成下载 + private int splitter; + + // 下载文件默认保存路径 + private final static String FILE_PATH = "C:/temp"; + // 默认分块数、线程数 + private final static int SPLITTER_NUM = 5; + + public DownloadInfo() { + super(); + } + + /** + * @param url + * 下载地址 + */ + public DownloadInfo(String url) { + this(url, null, null, SPLITTER_NUM); + } + + /** + * @param url + * 下载地址url + * @param splitter + * 分成多少段或是多少个线程下载 + */ + public DownloadInfo(String url, int splitter) { + this(url, null, null, splitter); + } + + /*** + * @param url + * 下载地址 + * @param fileName + * 文件名称 + * @param filePath + * 文件保存路径 + * @param splitter + * 分成多少段或是多少个线程下载 + */ + public DownloadInfo(String url, String fileName, String filePath, int splitter) { + super(); + if (url == null || "".equals(url)) { + throw new RuntimeException("url is not null!"); + } + this.url = url; + this.fileName = (fileName == null || "".equals(fileName)) ? getFileName(url) : fileName; + this.filePath = (filePath == null || "".equals(filePath)) ? FILE_PATH : filePath; + this.splitter = (splitter < 1) ? SPLITTER_NUM : splitter; + } + + /** + * function: 通过url获得文件名称 + * + * @author hoojo + * @createDate 2011-9-30 下午05:00:00 + * @param url + * @return + */ + private String getFileName(String url) { + return url.substring(url.lastIndexOf("/") + 1, url.length()); + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + if (url == null || "".equals(url)) { + throw new RuntimeException("url is not null!"); + } + this.url = url; + } + + public String getFileName() { + return fileName; + } + + public void setFileName(String fileName) { + this.fileName = (fileName == null || "".equals(fileName)) ? getFileName(url) : fileName; + } + + public String getFilePath() { + return filePath; + } + + public void setFilePath(String filePath) { + this.filePath = (filePath == null || "".equals(filePath)) ? FILE_PATH : filePath; + } + + public int getSplitter() { + return splitter; + } + + public void setSplitter(int splitter) { + this.splitter = (splitter < 1) ? SPLITTER_NUM : splitter; + } + + @Override + public String toString() { + return this.url + "#" + this.fileName + "#" + this.filePath + "#" + this.splitter; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java new file mode 100644 index 0000000000..3ca0384319 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java @@ -0,0 +1,40 @@ +package com.hoo.util; + +import com.hoo.download.BatchDownloadFile; +import com.hoo.entity.DownloadInfo; + +/** + * function: 分块多线程下载工具类 + * + * @author hoojo + * @createDate 2011-9-28 下午05:22:18 + * @file DownloadUtils.java + * @package com.hoo.util + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public abstract class DownloadUtils { + + public static void download(String url) { + DownloadInfo bean = new DownloadInfo(url); + LogUtils.info(bean); + BatchDownloadFile down = new BatchDownloadFile(bean); + new Thread(down).start(); + } + + public static void download(String url, int threadNum) { + DownloadInfo bean = new DownloadInfo(url, threadNum); + LogUtils.info(bean); + BatchDownloadFile down = new BatchDownloadFile(bean); + new Thread(down).start(); + } + + public static void download(String url, String fileName, String filePath, int threadNum) { + DownloadInfo bean = new DownloadInfo(url, fileName, filePath, threadNum); + LogUtils.info(bean); + BatchDownloadFile down = new BatchDownloadFile(bean); + new Thread(down).start(); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java new file mode 100644 index 0000000000..562a0ec047 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java @@ -0,0 +1,39 @@ +/** + * copy from http://blog.csdn.net/ibm_hoojo/article/details/6838222 + */ +package com.hoo.util; + +/** + * function: 下载测试 + * + * @author hoojo + * @createDate 2011-9-23 下午05:49:46 + * @file TestDownloadMain.java + * @package com.hoo.download + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public class DownloadUtilsTest { + public static void main(String[] args) { + /* + * DownloadInfo bean = new DownloadInfo( + * "http://i7.meishichina.com/Health/UploadFiles/201109/2011092116224363.jpg" + * ); System.out.println(bean); BatchDownloadFile down = new + * BatchDownloadFile(bean); new Thread(down).start(); + */ + + // DownloadUtils.download("http://i7.meishichina.com/Health/UploadFiles/201109/2011092116224363.jpg"); + DownloadUtils.download("https://github.com/dracome/coding2017/archive/master.zip", 5); + + try { + Thread.sleep(30 * 1000); + } catch (InterruptedException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + int i = 3; + System.out.println(i); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java new file mode 100644 index 0000000000..62d48bd0f9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java @@ -0,0 +1,40 @@ +package com.hoo.util; + +/** + * function: 日志工具类 + * + * @author hoojo + * @createDate 2011-9-21 下午05:21:27 + * @file LogUtils.java + * @package com.hoo.util + * @project MultiThreadDownLoad + * @blog http://blog.csdn.net/IBM_hoojo + * @email hoojo_@126.com + * @version 1.0 + */ +public abstract class LogUtils { + + public static void log(Object message) { + System.err.println(message); + } + + public static void log(String message) { + System.err.println(message); + } + + public static void log(int message) { + System.err.println(message); + } + + public static void info(Object message) { + System.out.println(message); + } + + public static void info(String message) { + System.out.println(message); + } + + public static void info(int message) { + System.out.println(message); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java new file mode 100644 index 0000000000..c849302200 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java @@ -0,0 +1,51 @@ +/* copy from http://stefanbirkner.github.io/system-rules/index.html */ + +package com.github.eulerlcs.jmr.challenge.systemrules; + +import static org.junit.Assert.assertEquals; + +import org.junit.Rule; +import org.junit.Test; +import org.junit.contrib.java.lang.system.Assertion; +import org.junit.contrib.java.lang.system.ExpectedSystemExit; + +public class AppWithExitTest { + @Rule + public final ExpectedSystemExit exit = ExpectedSystemExit.none(); + + @Test + public void exits() { + exit.expectSystemExit(); + AppWithExit.doSomethingAndExit(); + } + + @Test + public void exitsWithStatusCode1() { + exit.expectSystemExitWithStatus(1); + AppWithExit.doSomethingAndExit(); + } + + @Test + public void writesMessage() { + exit.expectSystemExitWithStatus(1); + exit.checkAssertionAfterwards(new Assertion() { + @Override + public void checkAssertion() { + assertEquals("exit ...", AppWithExit.message); + } + }); + AppWithExit.doSomethingAndExit(); + } + + @Test + public void systemExitWithStatusCode1() { + exit.expectSystemExitWithStatus(1); + AppWithExit.doSomethingAndExit(); + } + + @Test + public void noSystemExit() { + AppWithExit.doNothing(); + // passes + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml new file mode 100644 index 0000000000..dc562ded7e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml @@ -0,0 +1,35 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-51-liuxin-question + eulerlcs master java road copy from liuxin question + + + + org.apache.commons + commons-lang3 + + + org.apache.commons + commons-io + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java new file mode 100644 index 0000000000..76dc0f3a40 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java @@ -0,0 +1,28 @@ +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/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java new file mode 100644 index 0000000000..1551a80b3d --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java @@ -0,0 +1,5 @@ +package com.coderising.download.api; + +public class ConnectionException extends Exception { + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java new file mode 100644 index 0000000000..787984f170 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java @@ -0,0 +1,11 @@ +package com.coderising.download.api; + +public interface ConnectionManager { + /** + * 给定一个url , 打开一个连接 + * + * @param url + * @return + */ + public Connection open(String url) throws ConnectionException; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java new file mode 100644 index 0000000000..bf9807b307 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java @@ -0,0 +1,5 @@ +package com.coderising.download.api; + +public interface DownloadListener { + public void notifyFinished(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java new file mode 100644 index 0000000000..ba94bee146 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java @@ -0,0 +1,21 @@ +package com.coderising.download.core; + +import com.coderising.download.api.Connection; + +public class DownloadThread extends Thread { + + Connection conn; + int startPos; + int endPos; + + public DownloadThread(Connection conn, int startPos, int endPos) { + + this.conn = conn; + this.startPos = startPos; + this.endPos = endPos; + } + + public void run() { + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java new file mode 100644 index 0000000000..23ee19ab02 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java @@ -0,0 +1,68 @@ +package com.coderising.download.core; + +import com.coderising.download.api.Connection; +import com.coderising.download.api.ConnectionException; +import com.coderising.download.api.ConnectionManager; +import com.coderising.download.api.DownloadListener; + +public class FileDownloader { + + String url; + + DownloadListener listener; + + ConnectionManager cm; + + 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 { + + conn = cm.open(this.url); + + int length = conn.getContentLength(); + + new DownloadThread(conn, 0, length - 1).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/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java new file mode 100644 index 0000000000..1831118927 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java @@ -0,0 +1,26 @@ +package com.coderising.download.impl; + +import java.io.IOException; + +import com.coderising.download.api.Connection; + +public class ConnectionImpl implements Connection { + + @Override + public byte[] read(int startPos, int endPos) throws IOException { + + return null; + } + + @Override + public int getContentLength() { + + return 0; + } + + @Override + public void close() { + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java new file mode 100644 index 0000000000..6585b835c4 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java @@ -0,0 +1,15 @@ +package com.coderising.download.impl; + +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 { + + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java new file mode 100644 index 0000000000..3391da9616 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java @@ -0,0 +1,19 @@ +package com.coderising.jvm.attr; + +public abstract class AttributeInfo { + public static final String CODE = "Code"; + public static final String CONST_VALUE = "ConstantValue"; + public static final String EXCEPTIONS = "Exceptions"; + public static final String LINE_NUM_TABLE = "LineNumberTable"; + public static final String LOCAL_VAR_TABLE = "LocalVariableTable"; + public static final String STACK_MAP_TABLE = "StackMapTable"; + int attrNameIndex; + int attrLen; + + public AttributeInfo(int attrNameIndex, int attrLen) { + + this.attrNameIndex = attrNameIndex; + this.attrLen = attrLen; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java new file mode 100644 index 0000000000..f7ed2f1297 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java @@ -0,0 +1,52 @@ +package com.coderising.jvm.attr; + +import com.coderising.jvm.clz.ClassFile; +import com.coderising.jvm.loader.ByteCodeIterator; + +public class CodeAttr extends AttributeInfo { + private int maxStack; + private int maxLocals; + private int codeLen; + private String code; + + public String getCode() { + return code; + } + + // private ByteCodeCommand[] cmds ; + // public ByteCodeCommand[] getCmds() { + // return cmds; + // } + private LineNumberTable lineNumTable; + private LocalVariableTable localVarTable; + private StackMapTable stackMapTable; + + public CodeAttr(int attrNameIndex, int attrLen, int maxStack, int maxLocals, int codeLen, + String code /* ByteCodeCommand[] cmds */) { + super(attrNameIndex, attrLen); + this.maxStack = maxStack; + this.maxLocals = maxLocals; + this.codeLen = codeLen; + this.code = code; + // this.cmds = cmds; + } + + public void setLineNumberTable(LineNumberTable t) { + this.lineNumTable = t; + } + + public void setLocalVariableTable(LocalVariableTable t) { + this.localVarTable = t; + } + + public static CodeAttr parse(ClassFile clzFile, ByteCodeIterator iter) { + + return null; + } + + private void setStackMapTable(StackMapTable t) { + this.stackMapTable = t; + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java new file mode 100644 index 0000000000..71553b4fbb --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java @@ -0,0 +1,46 @@ +package com.coderising.jvm.attr; + +import java.util.ArrayList; +import java.util.List; + +import com.coderising.jvm.loader.ByteCodeIterator; + +public class LineNumberTable extends AttributeInfo { + List items = new ArrayList(); + + private static class LineNumberItem { + int startPC; + int lineNum; + + public int getStartPC() { + return startPC; + } + + public void setStartPC(int startPC) { + this.startPC = startPC; + } + + public int getLineNum() { + return lineNum; + } + + public void setLineNum(int lineNum) { + this.lineNum = lineNum; + } + } + + public void addLineNumberItem(LineNumberItem item) { + this.items.add(item); + } + + public LineNumberTable(int attrNameIndex, int attrLen) { + super(attrNameIndex, attrLen); + + } + + public static LineNumberTable parse(ByteCodeIterator iter) { + + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java new file mode 100644 index 0000000000..9561e904a9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java @@ -0,0 +1,49 @@ +package com.coderising.jvm.attr; + +public class LocalVariableItem { + private int startPC; + private int length; + private int nameIndex; + private int descIndex; + private int index; + + public int getStartPC() { + return startPC; + } + + public void setStartPC(int startPC) { + this.startPC = startPC; + } + + public int getLength() { + return length; + } + + public void setLength(int length) { + this.length = length; + } + + public int getNameIndex() { + return nameIndex; + } + + public void setNameIndex(int nameIndex) { + this.nameIndex = nameIndex; + } + + public int getDescIndex() { + return descIndex; + } + + public void setDescIndex(int descIndex) { + this.descIndex = descIndex; + } + + public int getIndex() { + return index; + } + + public void setIndex(int index) { + this.index = index; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java new file mode 100644 index 0000000000..b8a3ccfa8f --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java @@ -0,0 +1,25 @@ +package com.coderising.jvm.attr; + +import java.util.ArrayList; +import java.util.List; + +import com.coderising.jvm.loader.ByteCodeIterator; + +public class LocalVariableTable extends AttributeInfo { + + List items = new ArrayList(); + + public LocalVariableTable(int attrNameIndex, int attrLen) { + super(attrNameIndex, attrLen); + } + + public static LocalVariableTable parse(ByteCodeIterator iter) { + + return null; + } + + private void addLocalVariableItem(LocalVariableItem item) { + this.items.add(item); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java new file mode 100644 index 0000000000..14427e19ee --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java @@ -0,0 +1,29 @@ +package com.coderising.jvm.attr; + +import com.coderising.jvm.loader.ByteCodeIterator; + +public class StackMapTable extends AttributeInfo { + + private String originalCode; + + public StackMapTable(int attrNameIndex, int attrLen) { + super(attrNameIndex, attrLen); + } + + public static StackMapTable parse(ByteCodeIterator iter) { + int index = iter.nextU2ToInt(); + int len = iter.nextU4ToInt(); + StackMapTable t = new StackMapTable(index, len); + + // 后面的StackMapTable太过复杂, 不再处理, 只把原始的代码读进来保存 + String code = iter.nextUxToHexString(len); + t.setOriginalCode(code); + + return t; + } + + private void setOriginalCode(String code) { + this.originalCode = code; + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java new file mode 100644 index 0000000000..2cc6092de0 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java @@ -0,0 +1,26 @@ +package com.coderising.jvm.clz; + +public class AccessFlag { + private int flagValue; + + public AccessFlag(int value) { + this.flagValue = value; + } + + public int getFlagValue() { + return flagValue; + } + + public void setFlagValue(int flag) { + this.flagValue = flag; + } + + public boolean isPublicClass() { + return (this.flagValue & 0x0001) != 0; + } + + public boolean isFinalClass() { + return (this.flagValue & 0x0010) != 0; + } + +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java new file mode 100644 index 0000000000..ad5a7d71db --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java @@ -0,0 +1,100 @@ +package com.coderising.jvm.clz; + +import java.util.ArrayList; +import java.util.List; + +import com.coderising.jvm.constant.ClassInfo; +import com.coderising.jvm.constant.ConstantPool; +import com.coderising.jvm.field.Field; +import com.coderising.jvm.method.Method; + +public class ClassFile { + + private int minorVersion; + private int majorVersion; + + private AccessFlag accessFlag; + private ClassIndex clzIndex; + private ConstantPool pool; + private List fields = new ArrayList(); + private List methods = new ArrayList(); + + public ClassIndex getClzIndex() { + return clzIndex; + } + + public AccessFlag getAccessFlag() { + return accessFlag; + } + + public void setAccessFlag(AccessFlag accessFlag) { + this.accessFlag = accessFlag; + } + + public ConstantPool getConstantPool() { + return pool; + } + + public int getMinorVersion() { + return minorVersion; + } + + public void setMinorVersion(int minorVersion) { + this.minorVersion = minorVersion; + } + + public int getMajorVersion() { + return majorVersion; + } + + public void setMajorVersion(int majorVersion) { + this.majorVersion = majorVersion; + } + + public void setConstPool(ConstantPool pool) { + this.pool = pool; + + } + + public void setClassIndex(ClassIndex clzIndex) { + this.clzIndex = clzIndex; + } + + public void addField(Field f) { + this.fields.add(f); + } + + public List getFields() { + return this.fields; + } + + public void addMethod(Method m) { + this.methods.add(m); + } + + public List getMethods() { + return methods; + } + + public void print() { + + if (this.accessFlag.isPublicClass()) { + System.out.println("Access flag : public "); + } + System.out.println("Class Name:" + getClassName()); + + System.out.println("Super Class Name:" + getSuperClassName()); + + } + + private String getClassName() { + int thisClassIndex = this.clzIndex.getThisClassIndex(); + ClassInfo thisClass = (ClassInfo) this.getConstantPool().getConstantInfo(thisClassIndex); + return thisClass.getClassName(); + } + + private String getSuperClassName() { + ClassInfo superClass = (ClassInfo) this.getConstantPool().getConstantInfo(this.clzIndex.getSuperClassIndex()); + return superClass.getClassName(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java new file mode 100644 index 0000000000..0212bc9fb3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java @@ -0,0 +1,22 @@ +package com.coderising.jvm.clz; + +public class ClassIndex { + private int thisClassIndex; + private int superClassIndex; + + public int getThisClassIndex() { + return thisClassIndex; + } + + public void setThisClassIndex(int thisClassIndex) { + this.thisClassIndex = thisClassIndex; + } + + public int getSuperClassIndex() { + return superClassIndex; + } + + public void setSuperClassIndex(int superClassIndex) { + this.superClassIndex = superClassIndex; + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java new file mode 100644 index 0000000000..4b593e7347 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java @@ -0,0 +1,28 @@ +package com.coderising.jvm.constant; + +public class ClassInfo extends ConstantInfo { + private int type = ConstantInfo.CLASS_INFO; + private int utf8Index; + + public ClassInfo(ConstantPool pool) { + super(pool); + } + + public int getUtf8Index() { + return utf8Index; + } + + public void setUtf8Index(int utf8Index) { + this.utf8Index = utf8Index; + } + + public int getType() { + return type; + } + + public String getClassName() { + int index = getUtf8Index(); + UTF8Info utf8Info = (UTF8Info) constantPool.getConstantInfo(index); + return utf8Info.getValue(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java new file mode 100644 index 0000000000..5ef8fbfef8 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java @@ -0,0 +1,29 @@ +package com.coderising.jvm.constant; + +public abstract class ConstantInfo { + public static final int UTF8_INFO = 1; + public static final int FLOAT_INFO = 4; + public static final int CLASS_INFO = 7; + public static final int STRING_INFO = 8; + public static final int FIELD_INFO = 9; + public static final int METHOD_INFO = 10; + public static final int NAME_AND_TYPE_INFO = 12; + protected ConstantPool constantPool; + + public ConstantInfo() { + } + + public ConstantInfo(ConstantPool pool) { + this.constantPool = pool; + } + + public abstract int getType(); + + public ConstantPool getConstantPool() { + return constantPool; + } + + public ConstantInfo getConstantInfo(int index) { + return this.constantPool.getConstantInfo(index); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java new file mode 100644 index 0000000000..49ece7d089 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java @@ -0,0 +1,28 @@ +package com.coderising.jvm.constant; + +import java.util.ArrayList; +import java.util.List; + +public class ConstantPool { + + private List constantInfos = new ArrayList(); + + public ConstantPool() { + } + + public void addConstantInfo(ConstantInfo info) { + this.constantInfos.add(info); + } + + public ConstantInfo getConstantInfo(int index) { + return this.constantInfos.get(index); + } + + public String getUTF8String(int index) { + return ((UTF8Info) this.constantInfos.get(index)).getValue(); + } + + public Object getSize() { + return this.constantInfos.size() - 1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java new file mode 100644 index 0000000000..469a30b95e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java @@ -0,0 +1,54 @@ +package com.coderising.jvm.constant; + +public class FieldRefInfo extends ConstantInfo { + private int type = ConstantInfo.FIELD_INFO; + private int classInfoIndex; + private int nameAndTypeIndex; + + public FieldRefInfo(ConstantPool pool) { + super(pool); + } + + @Override + public int getType() { + return type; + } + + public int getClassInfoIndex() { + return classInfoIndex; + } + + public void setClassInfoIndex(int classInfoIndex) { + this.classInfoIndex = classInfoIndex; + } + + public int getNameAndTypeIndex() { + return nameAndTypeIndex; + } + + public void setNameAndTypeIndex(int nameAndTypeIndex) { + this.nameAndTypeIndex = nameAndTypeIndex; + } + + @Override + public String toString() { + NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); + return getClassName() + " : " + typeInfo.getName() + ":" + typeInfo.getTypeInfo() + "]"; + } + + public String getClassName() { + ClassInfo classInfo = (ClassInfo) this.getConstantInfo(this.getClassInfoIndex()); + UTF8Info utf8Info = (UTF8Info) this.getConstantInfo(classInfo.getUtf8Index()); + return utf8Info.getValue(); + } + + public String getFieldName() { + NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getName(); + } + + public String getFieldType() { + NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getTypeInfo(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java new file mode 100644 index 0000000000..837e501f9f --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java @@ -0,0 +1,56 @@ +package com.coderising.jvm.constant; + +public class MethodRefInfo extends ConstantInfo { + private int type = ConstantInfo.METHOD_INFO; + + private int classInfoIndex; + private int nameAndTypeIndex; + + public MethodRefInfo(ConstantPool pool) { + super(pool); + } + + @Override + public int getType() { + return type; + } + + public int getClassInfoIndex() { + return classInfoIndex; + } + + public void setClassInfoIndex(int classInfoIndex) { + this.classInfoIndex = classInfoIndex; + } + + public int getNameAndTypeIndex() { + return nameAndTypeIndex; + } + + public void setNameAndTypeIndex(int nameAndTypeIndex) { + this.nameAndTypeIndex = nameAndTypeIndex; + } + + @Override + public String toString() { + return getClassName() + " : " + this.getMethodName() + " : " + this.getParamAndReturnType(); + } + + public String getClassName() { + ConstantPool pool = this.getConstantPool(); + ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(this.getClassInfoIndex()); + return clzInfo.getClassName(); + } + + public String getMethodName() { + ConstantPool pool = this.getConstantPool(); + NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getName(); + } + + public String getParamAndReturnType() { + ConstantPool pool = this.getConstantPool(); + NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getTypeInfo(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java new file mode 100644 index 0000000000..a792e2dc13 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java @@ -0,0 +1,48 @@ +package com.coderising.jvm.constant; + +public class NameAndTypeInfo extends ConstantInfo { + public int type = ConstantInfo.NAME_AND_TYPE_INFO; + + private int index1; + private int index2; + + public NameAndTypeInfo(ConstantPool pool) { + super(pool); + } + + public int getIndex1() { + return index1; + } + + public void setIndex1(int index1) { + this.index1 = index1; + } + + public int getIndex2() { + return index2; + } + + public void setIndex2(int index2) { + this.index2 = index2; + } + + public int getType() { + return type; + } + + public String getName() { + ConstantPool pool = this.getConstantPool(); + UTF8Info utf8Info1 = (UTF8Info) pool.getConstantInfo(index1); + return utf8Info1.getValue(); + } + + public String getTypeInfo() { + ConstantPool pool = this.getConstantPool(); + UTF8Info utf8Info2 = (UTF8Info) pool.getConstantInfo(index2); + return utf8Info2.getValue(); + } + + public String toString() { + return "(" + getName() + "," + getTypeInfo() + ")"; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java new file mode 100644 index 0000000000..6e4e3750c7 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java @@ -0,0 +1,11 @@ +package com.coderising.jvm.constant; + +public class NullConstantInfo extends ConstantInfo { + public NullConstantInfo() { + } + + @Override + public int getType() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java new file mode 100644 index 0000000000..3282aad968 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java @@ -0,0 +1,28 @@ +package com.coderising.jvm.constant; + +public class StringInfo extends ConstantInfo { + private int type = ConstantInfo.STRING_INFO; + private int index; + + public StringInfo(ConstantPool pool) { + super(pool); + } + + @Override + public int getType() { + return type; + } + + public int getIndex() { + return index; + } + + public void setIndex(int index) { + this.index = index; + } + + @Override + public String toString() { + return this.getConstantPool().getUTF8String(index); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java new file mode 100644 index 0000000000..dc4d0b0b64 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java @@ -0,0 +1,37 @@ +package com.coderising.jvm.constant; + +public class UTF8Info extends ConstantInfo { + private int type = ConstantInfo.UTF8_INFO; + private int length; + private String value; + + public UTF8Info(ConstantPool pool) { + super(pool); + } + + public int getLength() { + return length; + } + + public void setLength(int length) { + this.length = length; + } + + @Override + public int getType() { + return type; + } + + @Override + public String toString() { + return "UTF8Info [type=" + type + ", length=" + length + ", value=" + value + ")]"; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java new file mode 100644 index 0000000000..64742c6596 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java @@ -0,0 +1,26 @@ +package com.coderising.jvm.field; + +import com.coderising.jvm.constant.ConstantPool; +import com.coderising.jvm.loader.ByteCodeIterator; + +public class Field { + private int accessFlag; + private int nameIndex; + private int descriptorIndex; + + private ConstantPool pool; + + public Field(int accessFlag, int nameIndex, int descriptorIndex, ConstantPool pool) { + + this.accessFlag = accessFlag; + this.nameIndex = nameIndex; + this.descriptorIndex = descriptorIndex; + this.pool = pool; + } + + public static Field parse(ConstantPool pool, ByteCodeIterator iter) { + + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java new file mode 100644 index 0000000000..3cc8ab6697 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java @@ -0,0 +1,55 @@ +package com.coderising.jvm.loader; + +import java.util.Arrays; + +import com.coderising.jvm.util.Util; + +public class ByteCodeIterator { + byte[] codes; + int pos = 0; + + ByteCodeIterator(byte[] codes) { + this.codes = codes; + } + + public byte[] getBytes(int len) { + if (pos + len >= codes.length) { + throw new ArrayIndexOutOfBoundsException(); + } + + byte[] data = Arrays.copyOfRange(codes, pos, pos + len); + pos += len; + return data; + } + + public int nextU1toInt() { + + return Util.byteToInt(new byte[] { codes[pos++] }); + } + + public int nextU2ToInt() { + return Util.byteToInt(new byte[] { codes[pos++], codes[pos++] }); + } + + public int nextU4ToInt() { + return Util.byteToInt(new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] }); + } + + public String nextU4ToHexString() { + return Util.byteToHexString((new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] })); + } + + public String nextUxToHexString(int len) { + byte[] tmp = new byte[len]; + + for (int i = 0; i < len; i++) { + tmp[i] = codes[pos++]; + } + return Util.byteToHexString(tmp).toLowerCase(); + + } + + public void back(int n) { + this.pos -= n; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java new file mode 100644 index 0000000000..1af1946bb3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java @@ -0,0 +1,122 @@ +package com.coderising.jvm.loader; + +import java.io.BufferedInputStream; +import java.io.ByteArrayOutputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +import org.apache.commons.io.IOUtils; +import org.apache.commons.lang3.StringUtils; + +import com.coderising.jvm.clz.ClassFile; + +public class ClassFileLoader { + + private List clzPaths = new ArrayList(); + + public byte[] readBinaryCode(String className) { + + className = className.replace('.', File.separatorChar) + ".class"; + + for (String path : this.clzPaths) { + + String clzFileName = path + File.separatorChar + className; + byte[] codes = loadClassFile(clzFileName); + if (codes != null) { + return codes; + } + } + + return null; + + } + + private byte[] loadClassFile(String clzFileName) { + + File f = new File(clzFileName); + + try { + + return IOUtils.toByteArray(new FileInputStream(f)); + + } catch (IOException e) { + e.printStackTrace(); + return null; + } + } + + public void addClassPath(String path) { + if (this.clzPaths.contains(path)) { + return; + } + + this.clzPaths.add(path); + + } + + public String getClassPath() { + return StringUtils.join(this.clzPaths, ";"); + } + + public ClassFile loadClass(String className) { + byte[] codes = this.readBinaryCode(className); + ClassFileParser parser = new ClassFileParser(); + return parser.parse(codes); + + } + + // ------------------------------backup------------------------ + public String getClassPath_V1() { + + StringBuffer buffer = new StringBuffer(); + for (int i = 0; i < this.clzPaths.size(); i++) { + buffer.append(this.clzPaths.get(i)); + if (i < this.clzPaths.size() - 1) { + buffer.append(";"); + } + } + return buffer.toString(); + } + + private byte[] loadClassFile_V1(String clzFileName) { + + BufferedInputStream bis = null; + + try { + + File f = new File(clzFileName); + + bis = new BufferedInputStream(new FileInputStream(f)); + + ByteArrayOutputStream bos = new ByteArrayOutputStream(); + + byte[] buffer = new byte[1024]; + int length = -1; + + while ((length = bis.read(buffer)) != -1) { + bos.write(buffer, 0, length); + } + + byte[] codes = bos.toByteArray(); + + return codes; + + } catch (IOException e) { + e.printStackTrace(); + + } finally { + if (bis != null) { + try { + bis.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + return null; + + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java new file mode 100644 index 0000000000..b32ca1926b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java @@ -0,0 +1,146 @@ +package com.coderising.jvm.loader; + +import java.io.UnsupportedEncodingException; + +import com.coderising.jvm.clz.AccessFlag; +import com.coderising.jvm.clz.ClassFile; +import com.coderising.jvm.clz.ClassIndex; +import com.coderising.jvm.constant.ClassInfo; +import com.coderising.jvm.constant.ConstantPool; +import com.coderising.jvm.constant.FieldRefInfo; +import com.coderising.jvm.constant.MethodRefInfo; +import com.coderising.jvm.constant.NameAndTypeInfo; +import com.coderising.jvm.constant.NullConstantInfo; +import com.coderising.jvm.constant.StringInfo; +import com.coderising.jvm.constant.UTF8Info; + +public class ClassFileParser { + + public ClassFile parse(byte[] codes) { + + ClassFile clzFile = new ClassFile(); + + ByteCodeIterator iter = new ByteCodeIterator(codes); + + String magicNumber = iter.nextU4ToHexString(); + + if (!"cafebabe".equals(magicNumber)) { + return null; + } + + clzFile.setMinorVersion(iter.nextU2ToInt()); + clzFile.setMajorVersion(iter.nextU2ToInt()); + + ConstantPool pool = parseConstantPool(iter); + clzFile.setConstPool(pool); + + AccessFlag flag = parseAccessFlag(iter); + clzFile.setAccessFlag(flag); + + ClassIndex clzIndex = parseClassInfex(iter); + clzFile.setClassIndex(clzIndex); + + parseInterfaces(iter); + + return clzFile; + } + + private AccessFlag parseAccessFlag(ByteCodeIterator iter) { + + AccessFlag flag = new AccessFlag(iter.nextU2ToInt()); + // System.out.println("Is public class: " + flag.isPublicClass()); + // System.out.println("Is final class : " + flag.isFinalClass()); + + return flag; + } + + private ClassIndex parseClassInfex(ByteCodeIterator iter) { + + int thisClassIndex = iter.nextU2ToInt(); + int superClassIndex = iter.nextU2ToInt(); + + ClassIndex clzIndex = new ClassIndex(); + + clzIndex.setThisClassIndex(thisClassIndex); + clzIndex.setSuperClassIndex(superClassIndex); + + return clzIndex; + + } + + private ConstantPool parseConstantPool(ByteCodeIterator iter) { + + int constPoolCount = iter.nextU2ToInt(); + + System.out.println("Constant Pool Count :" + constPoolCount); + + ConstantPool pool = new ConstantPool(); + + pool.addConstantInfo(new NullConstantInfo()); + + for (int i = 1; i <= constPoolCount - 1; i++) { + + int tag = iter.nextU1toInt(); + + if (tag == 7) { + // Class Info + int utf8Index = iter.nextU2ToInt(); + ClassInfo clzInfo = new ClassInfo(pool); + clzInfo.setUtf8Index(utf8Index); + + pool.addConstantInfo(clzInfo); + } else if (tag == 1) { + // UTF-8 String + int len = iter.nextU2ToInt(); + byte[] data = iter.getBytes(len); + String value = null; + try { + value = new String(data, "UTF-8"); + } catch (UnsupportedEncodingException e) { + e.printStackTrace(); + } + + UTF8Info utf8Str = new UTF8Info(pool); + utf8Str.setLength(len); + utf8Str.setValue(value); + pool.addConstantInfo(utf8Str); + } else if (tag == 8) { + StringInfo info = new StringInfo(pool); + info.setIndex(iter.nextU2ToInt()); + pool.addConstantInfo(info); + } else if (tag == 9) { + FieldRefInfo field = new FieldRefInfo(pool); + field.setClassInfoIndex(iter.nextU2ToInt()); + field.setNameAndTypeIndex(iter.nextU2ToInt()); + pool.addConstantInfo(field); + } else if (tag == 10) { + // MethodRef + MethodRefInfo method = new MethodRefInfo(pool); + method.setClassInfoIndex(iter.nextU2ToInt()); + method.setNameAndTypeIndex(iter.nextU2ToInt()); + pool.addConstantInfo(method); + } else if (tag == 12) { + // Name and Type Info + NameAndTypeInfo nameType = new NameAndTypeInfo(pool); + nameType.setIndex1(iter.nextU2ToInt()); + nameType.setIndex2(iter.nextU2ToInt()); + pool.addConstantInfo(nameType); + } else { + throw new RuntimeException("the constant pool tag " + tag + " has not been implemented yet."); + } + } + + System.out.println("Finished reading Constant pool "); + + return pool; + } + + private void parseInterfaces(ByteCodeIterator iter) { + int interfaceCount = iter.nextU2ToInt(); + + System.out.println("interfaceCount:" + interfaceCount); + + // TODO : 如果实现了interface, 这里需要解析 + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java new file mode 100644 index 0000000000..690e71a8de --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java @@ -0,0 +1,48 @@ +package com.coderising.jvm.method; + +import com.coderising.jvm.attr.CodeAttr; +import com.coderising.jvm.clz.ClassFile; +import com.coderising.jvm.loader.ByteCodeIterator; + +public class Method { + + private int accessFlag; + private int nameIndex; + private int descriptorIndex; + + private CodeAttr codeAttr; + + private ClassFile clzFile; + + public ClassFile getClzFile() { + return clzFile; + } + + public int getNameIndex() { + return nameIndex; + } + + public int getDescriptorIndex() { + return descriptorIndex; + } + + public CodeAttr getCodeAttr() { + return codeAttr; + } + + public void setCodeAttr(CodeAttr code) { + this.codeAttr = code; + } + + public Method(ClassFile clzFile, int accessFlag, int nameIndex, int descriptorIndex) { + this.clzFile = clzFile; + this.accessFlag = accessFlag; + this.nameIndex = nameIndex; + this.descriptorIndex = descriptorIndex; + } + + public static Method parse(ClassFile clzFile, ByteCodeIterator iter) { + return null; + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java new file mode 100644 index 0000000000..1f9e087bb9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java @@ -0,0 +1,22 @@ +package com.coderising.jvm.util; + +public class Util { + public static int byteToInt(byte[] codes) { + String s1 = byteToHexString(codes); + return Integer.valueOf(s1, 16).intValue(); + } + + public static String byteToHexString(byte[] codes) { + StringBuffer buffer = new StringBuffer(); + for (int i = 0; i < codes.length; i++) { + byte b = codes[i]; + int value = b & 0xFF; + String strHex = Integer.toHexString(value); + if (strHex.length() < 2) { + strHex = "0" + strHex; + } + buffer.append(strHex); + } + return buffer.toString(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java new file mode 100644 index 0000000000..5f41f42c62 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java @@ -0,0 +1,42 @@ +package com.coderising.litestruts; + +/** + * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 + * + * @author liuxin + * + */ +public class LoginAction { + private String name; + private String password; + private String message; + + public String getName() { + return name; + } + + public String getPassword() { + return password; + } + + public String execute() { + if ("test".equals(name) && "1234".equals(password)) { + this.message = "login successful"; + return "success"; + } + this.message = "login failed,please check your user/pwd"; + return "fail"; + } + + public void setName(String name) { + this.name = name; + } + + public void setPassword(String password) { + this.password = password; + } + + public String getMessage() { + return this.message; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java new file mode 100644 index 0000000000..5ad5ccb352 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java @@ -0,0 +1,30 @@ +package com.coderising.litestruts; + +import java.util.Map; + +public class Struts { + + public static View runAction(String actionName, Map parameters) { + + /* + * + * 0. 读取配置文件struts.xml + * + * 1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) + * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , + * "password"="1234") , 那就应该调用 setName和setPassword方法 + * + * 2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success" + * + * 3. 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 + * {"message": "登录成功"} , 放到View对象的parameters + * + * 4. 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, + * 放到View对象的jsp字段中。 + * + */ + + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java new file mode 100644 index 0000000000..f1e7fcfa19 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java @@ -0,0 +1,26 @@ +package com.coderising.litestruts; + +import java.util.Map; + +public class View { + private String jsp; + private Map parameters; + + public String getJsp() { + return jsp; + } + + public View setJsp(String jsp) { + this.jsp = jsp; + return this; + } + + public Map getParameters() { + return parameters; + } + + public View setParameters(Map parameters) { + this.parameters = parameters; + return this; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java new file mode 100644 index 0000000000..835e0311d1 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java @@ -0,0 +1,33 @@ +package com.coding.basic; + +public class ArrayList implements List { + + private int size = 0; + + private Object[] elementData = new Object[100]; + + public void add(Object o) { + + } + + public void add(int index, Object o) { + + } + + public Object get(int index) { + return null; + } + + public Object remove(int index) { + return null; + } + + public int size() { + return -1; + } + + public Iterator iterator() { + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java new file mode 100644 index 0000000000..ed475b9433 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java @@ -0,0 +1,96 @@ +package com.coding.basic; + +public class ArrayUtil { + + /** + * 给定一个整形数组a , 对该数组的值进行置换 例如: a = [7, 9 , 30, 3] , 置换后为 [3, 30, 9,7] 如果 a = + * [7, 9, 30, 3, 4] , 置换后为 [4,3, 30 , 9,7] + * + * @param origin + * @return + */ + public void reverseArray(int[] origin) { + + } + + /** + * 现在有如下的一个数组: int oldArr[]={1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5} + * 要求将以上数组中值为0的项去掉,将不为0的值存入一个新的数组,生成的新数组为: {1,3,4,5,6,6,5,4,7,6,7,5} + * + * @param oldArray + * @return + */ + + public int[] removeZero(int[] oldArray) { + return null; + } + + /** + * 给定两个已经排序好的整形数组, a1和a2 , 创建一个新的数组a3, 使得a3 包含a1和a2 的所有元素, 并且仍然是有序的 例如 a1 = + * [3, 5, 7,8] a2 = [4, 5, 6,7] 则 a3 为[3,4,5,6,7,8] , 注意: 已经消除了重复 + * + * @param array1 + * @param array2 + * @return + */ + + public int[] merge(int[] array1, int[] array2) { + return null; + } + + /** + * 把一个已经存满数据的数组 oldArray的容量进行扩展, 扩展后的新数据大小为oldArray.length + size + * 注意,老数组的元素在新数组中需要保持 例如 oldArray = [2,3,6] , size = 3,则返回的新数组为 + * [2,3,6,0,0,0] + * + * @param oldArray + * @param size + * @return + */ + public int[] grow(int[] oldArray, int size) { + return null; + } + + /** + * 斐波那契数列为:1,1,2,3,5,8,13,21...... ,给定一个最大值, 返回小于该值的数列 例如, max = 15 , + * 则返回的数组应该为 [1,1,2,3,5,8,13] max = 1, 则返回空数组 [] + * + * @param max + * @return + */ + public int[] fibonacci(int max) { + return null; + } + + /** + * 返回小于给定最大值max的所有素数数组 例如max = 23, 返回的数组为[2,3,5,7,11,13,17,19] + * + * @param max + * @return + */ + public int[] getPrimes(int max) { + return null; + } + + /** + * 所谓“完数”, 是指这个数恰好等于它的因子之和,例如6=1+2+3 给定一个最大值max, 返回一个数组, 数组中是小于max 的所有完数 + * + * @param max + * @return + */ + public int[] getPerfectNumbers(int max) { + return null; + } + + /** + * 用seperator 把数组 array给连接起来 例如array= [3,8,9], seperator = "-" 则返回值为"3-8-9" + * + * @param array + * @param s + * @return + */ + public String join(int[] array, String seperator) { + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java new file mode 100644 index 0000000000..2f944d3b91 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java @@ -0,0 +1,37 @@ +package com.coding.basic; + +public class BinaryTreeNode { + + private Object data; + private BinaryTreeNode left; + private BinaryTreeNode right; + + public Object getData() { + return data; + } + + public void setData(Object data) { + this.data = data; + } + + public BinaryTreeNode getLeft() { + return left; + } + + public void setLeft(BinaryTreeNode left) { + this.left = left; + } + + public BinaryTreeNode getRight() { + return right; + } + + public void setRight(BinaryTreeNode right) { + this.right = right; + } + + public BinaryTreeNode insert(Object o) { + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java new file mode 100644 index 0000000000..f30dfc8edf --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java @@ -0,0 +1,8 @@ +package com.coding.basic; + +public interface Iterator { + public boolean hasNext(); + + public Object next(); + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java new file mode 100644 index 0000000000..28a3314b0d --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java @@ -0,0 +1,50 @@ +package com.coding.basic; + +/** + * 用双向链表实现LRU算法 + * + * @author liuxin + */ +public class LRUPageFrame { + private static class Node { + Node prev; + Node next; + int pageNum; + + Node() { + } + } + + private int capacity; + private Node first;// 链表头 + private Node last;// 链表尾 + + public LRUPageFrame(int capacity) { + this.capacity = capacity; + } + + /** + * 获取缓存中对象 + * + * @param key + * @return + */ + public void access(int pageNum) { + } + + @Override + public String toString() { + StringBuilder buffer = new StringBuilder(); + Node node = first; + while (node != null) { + buffer.append(node.pageNum); + + node = node.next; + if (node != null) { + buffer.append(","); + } + } + + return buffer.toString(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java new file mode 100644 index 0000000000..4fe91d2c95 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java @@ -0,0 +1,126 @@ +package com.coding.basic; + +public class LinkedList implements List { + + private Node head; + + public void add(Object o) { + + } + + public void add(int index, Object o) { + + } + + public Object get(int index) { + return null; + } + + public Object remove(int index) { + return null; + } + + public int size() { + return -1; + } + + public void addFirst(Object o) { + + } + + public void addLast(Object o) { + + } + + public Object removeFirst() { + return null; + } + + public Object removeLast() { + return null; + } + + public Iterator iterator() { + return null; + } + + private static class Node { + Object data; + Node next; + + } + + /** + * 把该链表逆置 例如链表为 3->7->10 , 逆置后变为 10->7->3 + */ + public void reverse() { + + } + + /** + * 删除一个单链表的前半部分 例如:list = 2->5->7->8 , 删除以后的值为 7->8 如果list = 2->5->7->8->10 + * ,删除以后的值为7,8,10 + * + */ + public void removeFirstHalf() { + + } + + /** + * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 + * + * @param i + * @param length + */ + public void remove(int i, int length) { + + } + + /** + * 假定当前链表和listB均包含已升序排列的整数 从当前链表中取出那些listB所指定的元素 例如当前链表 = + * 11->101->201->301->401->501->601->701 listB = 1->3->4->6 + * 返回的结果应该是[101,301,401,601] + * + * @param list + */ + public int[] getElements(LinkedList list) { + return null; + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 从当前链表中中删除在listB中出现的元素 + * + * @param list + */ + + public void subtract(LinkedList list) { + + } + + /** + * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) + */ + public void removeDuplicateValues() { + + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) + * + * @param min + * @param max + */ + public void removeRange(int min, int max) { + + } + + /** + * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) + * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 + * + * @param list + */ + public LinkedList intersection(LinkedList list) { + return null; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java new file mode 100644 index 0000000000..03fa879b2e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java @@ -0,0 +1,13 @@ +package com.coding.basic; + +public interface List { + public void add(Object o); + + public void add(int index, Object o); + + public Object get(int index); + + public Object remove(int index); + + public int size(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java new file mode 100644 index 0000000000..b2908512c5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java @@ -0,0 +1,19 @@ +package com.coding.basic; + +public class Queue { + + public void enQueue(Object o) { + } + + public Object deQueue() { + return null; + } + + public boolean isEmpty() { + return false; + } + + public int size() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java new file mode 100644 index 0000000000..b09c9b3d91 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java @@ -0,0 +1,26 @@ +package com.coding.basic.stack; + +import com.coding.basic.ArrayList; + +public class Stack { + private ArrayList elementData = new ArrayList(); + + public void push(Object o) { + } + + public Object pop() { + return null; + } + + public Object peek() { + return null; + } + + public boolean isEmpty() { + return false; + } + + public int size() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java new file mode 100644 index 0000000000..de35c05449 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java @@ -0,0 +1,54 @@ +package com.coding.basic.stack; + +import java.util.Stack; + +public class StackUtil { + /** + * 假设栈中的元素是Integer, 从栈顶到栈底是 : 5,4,3,2,1 调用该方法后, 元素次序变为: 1,2,3,4,5 + * 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 + */ + public static void reverse(Stack s) { + } + + public static void addToBottom(Stack s, Integer value) { + if (s.isEmpty()) { + s.push(value); + } else { + Integer top = s.pop(); + addToBottom(s, value); + s.push(top); + } + } + + /** + * 删除栈中的某个元素 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 + * + * @param o + */ + public static void remove(Stack s, Object o) { + + } + + /** + * 从栈顶取得len个元素, 原来的栈中元素保持不变 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, + * 可以使用另外一个栈来辅助 + * + * @param len + * @return + */ + public static Object[] getTop(Stack s, int len) { + return null; + } + + /** + * 字符串s 可能包含这些字符: ( ) [ ] { }, a,b,c... x,yz 使用堆栈检查字符串s中的括号是不是成对出现的。 例如s = + * "([e{d}f])" , 则该字符串中的括号是成对出现, 该方法返回true 如果 s = "([b{x]y})", + * 则该字符串中的括号不是成对出现的, 该方法返回false; + * + * @param s + * @return + */ + public static boolean isValidPairs(String s) { + return false; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java new file mode 100644 index 0000000000..4f2cf4b03a --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java @@ -0,0 +1,13 @@ +package com.coding.basic.stack.expr; + +public class InfixExpr { + String expr = null; + + public InfixExpr(String expr) { + this.expr = expr; + } + + public float evaluate() { + return 0.0f; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml new file mode 100644 index 0000000000..ff7623e6e1 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml @@ -0,0 +1,11 @@ + + + + /jsp/homepage.jsp + /jsp/showLogin.jsp + + + /jsp/welcome.jsp + /jsp/error.jsp + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java new file mode 100644 index 0000000000..8e171cff93 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java @@ -0,0 +1,56 @@ +package com.coderising.download.core; + +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://localhost:8080/test.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/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java new file mode 100644 index 0000000000..6b78de3ddc --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java @@ -0,0 +1,248 @@ +package com.coderising.jvm.loader; + +import java.util.List; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.coderising.jvm.clz.ClassFile; +import com.coderising.jvm.clz.ClassIndex; +import com.coderising.jvm.constant.ClassInfo; +import com.coderising.jvm.constant.ConstantPool; +import com.coderising.jvm.constant.MethodRefInfo; +import com.coderising.jvm.constant.NameAndTypeInfo; +import com.coderising.jvm.constant.UTF8Info; +import com.coderising.jvm.field.Field; +import com.coderising.jvm.method.Method; + +public class ClassFileloaderTest { + private static final String FULL_QUALIFIED_CLASS_NAME = "com/coderising/jvm/test/EmployeeV1"; + + static String path1 = "C:\\Users\\liuxin\\git\\coding2017\\liuxin\\mini-jvm\\bin"; + static String path2 = "C:\temp"; + + static ClassFile clzFile = null; + static { + ClassFileLoader loader = new ClassFileLoader(); + loader.addClassPath(path1); + String className = "com.coderising.jvm.test.EmployeeV1"; + + clzFile = loader.loadClass(className); + clzFile.print(); + } + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testClassPath() { + + ClassFileLoader loader = new ClassFileLoader(); + loader.addClassPath(path1); + loader.addClassPath(path2); + + String clzPath = loader.getClassPath(); + + Assert.assertEquals(path1 + ";" + path2, clzPath); + + } + + @Test + public void testClassFileLength() { + + ClassFileLoader loader = new ClassFileLoader(); + loader.addClassPath(path1); + + String className = "com.coderising.jvm.test.EmployeeV1"; + + byte[] byteCodes = loader.readBinaryCode(className); + + // 注意:这个字节数可能和你的JVM版本有关系, 你可以看看编译好的类到底有多大 + Assert.assertEquals(1056, byteCodes.length); + + } + + @Test + public void testMagicNumber() { + ClassFileLoader loader = new ClassFileLoader(); + loader.addClassPath(path1); + String className = "com.coderising.jvm.test.EmployeeV1"; + byte[] byteCodes = loader.readBinaryCode(className); + byte[] codes = new byte[] { byteCodes[0], byteCodes[1], byteCodes[2], byteCodes[3] }; + + String acctualValue = this.byteToHexString(codes); + + Assert.assertEquals("cafebabe", acctualValue); + } + + private String byteToHexString(byte[] codes) { + StringBuffer buffer = new StringBuffer(); + for (int i = 0; i < codes.length; i++) { + byte b = codes[i]; + int value = b & 0xFF; + String strHex = Integer.toHexString(value); + if (strHex.length() < 2) { + strHex = "0" + strHex; + } + buffer.append(strHex); + } + return buffer.toString(); + } + + /** + * ---------------------------------------------------------------------- + */ + + @Test + public void testVersion() { + + Assert.assertEquals(0, clzFile.getMinorVersion()); + Assert.assertEquals(52, clzFile.getMajorVersion()); + + } + + @Test + public void testConstantPool() { + + ConstantPool pool = clzFile.getConstantPool(); + + Assert.assertEquals(53, pool.getSize()); + + { + ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(1); + Assert.assertEquals(2, clzInfo.getUtf8Index()); + + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(2); + Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, utf8Info.getValue()); + } + { + ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(3); + Assert.assertEquals(4, clzInfo.getUtf8Index()); + + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(4); + Assert.assertEquals("java/lang/Object", utf8Info.getValue()); + } + { + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(5); + Assert.assertEquals("name", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(6); + Assert.assertEquals("Ljava/lang/String;", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(7); + Assert.assertEquals("age", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(8); + Assert.assertEquals("I", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(9); + Assert.assertEquals("", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(10); + Assert.assertEquals("(Ljava/lang/String;I)V", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(11); + Assert.assertEquals("Code", utf8Info.getValue()); + } + + { + MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(12); + Assert.assertEquals(3, methodRef.getClassInfoIndex()); + Assert.assertEquals(13, methodRef.getNameAndTypeIndex()); + } + + { + NameAndTypeInfo nameAndType = (NameAndTypeInfo) pool.getConstantInfo(13); + Assert.assertEquals(9, nameAndType.getIndex1()); + Assert.assertEquals(14, nameAndType.getIndex2()); + } + // 抽查几个吧 + { + MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(45); + Assert.assertEquals(1, methodRef.getClassInfoIndex()); + Assert.assertEquals(46, methodRef.getNameAndTypeIndex()); + } + + { + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(53); + Assert.assertEquals("EmployeeV1.java", utf8Info.getValue()); + } + } + + @Test + public void testClassIndex() { + + ClassIndex clzIndex = clzFile.getClzIndex(); + ClassInfo thisClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getThisClassIndex()); + ClassInfo superClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getSuperClassIndex()); + + Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, thisClassInfo.getClassName()); + Assert.assertEquals("java/lang/Object", superClassInfo.getClassName()); + } + + /** + * 下面是第三次JVM课应实现的测试用例 + */ + @Test + public void testReadFields() { + + List fields = clzFile.getFields(); + Assert.assertEquals(2, fields.size()); + { + Field f = fields.get(0); + Assert.assertEquals("name:Ljava/lang/String;", f.toString()); + } + { + Field f = fields.get(1); + Assert.assertEquals("age:I", f.toString()); + } + } + + @Test + public void testMethods() { + + List methods = clzFile.getMethods(); + ConstantPool pool = clzFile.getConstantPool(); + + { + Method m = methods.get(0); + assertMethodEquals(pool, m, "", "(Ljava/lang/String;I)V", "2ab7000c2a2bb5000f2a1cb50011b1"); + + } + { + Method m = methods.get(1); + assertMethodEquals(pool, m, "setName", "(Ljava/lang/String;)V", "2a2bb5000fb1"); + + } + { + Method m = methods.get(2); + assertMethodEquals(pool, m, "setAge", "(I)V", "2a1bb50011b1"); + } + { + Method m = methods.get(3); + assertMethodEquals(pool, m, "sayHello", "()V", "b2001c1222b60024b1"); + + } + { + Method m = methods.get(4); + assertMethodEquals(pool, m, "main", "([Ljava/lang/String;)V", "bb000159122b101db7002d4c2bb6002fb1"); + } + } + + private void assertMethodEquals(ConstantPool pool, Method m, String expectedName, String expectedDesc, + String expectedCode) { + String methodName = pool.getUTF8String(m.getNameIndex()); + String methodDesc = pool.getUTF8String(m.getDescriptorIndex()); + String code = m.getCodeAttr().getCode(); + Assert.assertEquals(expectedName, methodName); + Assert.assertEquals(expectedDesc, methodDesc); + Assert.assertEquals(expectedCode, code); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java new file mode 100644 index 0000000000..2b80092ecb --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java @@ -0,0 +1,30 @@ +package com.coderising.jvm.loader; + +public class EmployeeV1 { + + private String name; + private int age; + + public EmployeeV1(String name, int age) { + this.name = name; + this.age = age; + } + + public void setName(String name) { + this.name = name; + } + + public void setAge(int age) { + this.age = age; + } + + public void sayHello() { + System.out.println("Hello , this is class Employee "); + } + + public static void main(String[] args) { + EmployeeV1 p = new EmployeeV1("Andy", 29); + p.sayHello(); + + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java new file mode 100644 index 0000000000..f2426db6ea --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java @@ -0,0 +1,38 @@ +package com.coderising.litestruts; + +import java.util.HashMap; +import java.util.Map; + +import org.junit.Assert; +import org.junit.Test; + +public class StrutsTest { + + @Test + public void testLoginActionSuccess() { + + String actionName = "login"; + + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "1234"); + + View view = Struts.runAction(actionName, params); + + Assert.assertEquals("/jsp/homepage.jsp", view.getJsp()); + Assert.assertEquals("login successful", view.getParameters().get("message")); + } + + @Test + public void testLoginActionFailed() { + String actionName = "login"; + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "123456"); // 密码和预设的不一致 + + View view = Struts.runAction(actionName, params); + + Assert.assertEquals("/jsp/showLogin.jsp", view.getJsp()); + Assert.assertEquals("login failed,please check your user/pwd", view.getParameters().get("message")); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java new file mode 100644 index 0000000000..bc139cbe2d --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java @@ -0,0 +1,27 @@ +package com.coding.basic; + +import org.junit.Assert; +import org.junit.Test; + +public class LRUPageFrameTest { + @Test + public void testAccess() { + LRUPageFrame frame = new LRUPageFrame(3); + frame.access(7); + frame.access(0); + frame.access(1); + Assert.assertEquals("1,0,7", frame.toString()); + frame.access(2); + Assert.assertEquals("2,1,0", frame.toString()); + frame.access(0); + Assert.assertEquals("0,2,1", frame.toString()); + frame.access(0); + Assert.assertEquals("0,2,1", frame.toString()); + frame.access(3); + Assert.assertEquals("3,0,2", frame.toString()); + frame.access(0); + Assert.assertEquals("0,3,2", frame.toString()); + frame.access(4); + Assert.assertEquals("4,0,3", frame.toString()); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java new file mode 100644 index 0000000000..5976823f36 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java @@ -0,0 +1,78 @@ +package com.coding.basic.stack; + +import java.util.Stack; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class StackUtilTest { + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testAddToBottom() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + + StackUtil.addToBottom(s, 0); + + Assert.assertEquals("[0, 1, 2, 3]", s.toString()); + + } + + @Test + public void testReverse() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + s.push(4); + s.push(5); + Assert.assertEquals("[1, 2, 3, 4, 5]", s.toString()); + StackUtil.reverse(s); + Assert.assertEquals("[5, 4, 3, 2, 1]", s.toString()); + } + + @Test + public void testRemove() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + StackUtil.remove(s, 2); + Assert.assertEquals("[1, 3]", s.toString()); + } + + @Test + public void testGetTop() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + s.push(4); + s.push(5); + { + Object[] values = StackUtil.getTop(s, 3); + Assert.assertEquals(5, values[0]); + Assert.assertEquals(4, values[1]); + Assert.assertEquals(3, values[2]); + } + } + + @Test + public void testIsValidPairs() { + Assert.assertTrue(StackUtil.isValidPairs("([e{d}f])")); + Assert.assertFalse(StackUtil.isValidPairs("([b{x]y})")); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java new file mode 100644 index 0000000000..2f03b3ac9a --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java @@ -0,0 +1,45 @@ +package com.coding.basic.stack.expr; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class InfixExprTest { + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testEvaluate() { + // InfixExpr expr = new InfixExpr("300*20+12*5-20/4"); + { + InfixExpr expr = new InfixExpr("2+3*4+5"); + Assert.assertEquals(19.0, expr.evaluate(), 0.001f); + } + { + InfixExpr expr = new InfixExpr("3*20+12*5-40/2"); + Assert.assertEquals(100.0, expr.evaluate(), 0.001f); + } + + { + InfixExpr expr = new InfixExpr("3*20/2"); + Assert.assertEquals(30, expr.evaluate(), 0.001f); + } + + { + InfixExpr expr = new InfixExpr("20/2*3"); + Assert.assertEquals(30, expr.evaluate(), 0.001f); + } + + { + InfixExpr expr = new InfixExpr("10-30+50"); + Assert.assertEquals(30, expr.evaluate(), 0.001f); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml new file mode 100644 index 0000000000..80266b31de --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml @@ -0,0 +1,31 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-52-liuxin-answer + eulerlcs master java road copy from liuxin answer + + + + org.jdom + jdom2 + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java new file mode 100644 index 0000000000..76dc0f3a40 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java @@ -0,0 +1,28 @@ +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/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java new file mode 100644 index 0000000000..4666b77756 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java @@ -0,0 +1,8 @@ +package com.coderising.download.api; + +public class ConnectionException extends Exception { + public ConnectionException(Exception e) { + super(e); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java new file mode 100644 index 0000000000..787984f170 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java @@ -0,0 +1,11 @@ +package com.coderising.download.api; + +public interface ConnectionManager { + /** + * 给定一个url , 打开一个连接 + * + * @param url + * @return + */ + public Connection open(String url) throws ConnectionException; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java new file mode 100644 index 0000000000..bf9807b307 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java @@ -0,0 +1,5 @@ +package com.coderising.download.api; + +public interface DownloadListener { + public void notifyFinished(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java new file mode 100644 index 0000000000..faf849d975 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java @@ -0,0 +1,50 @@ +package com.coderising.download.core; + +import java.io.RandomAccessFile; +import java.util.concurrent.CyclicBarrier; + +import com.coderising.download.api.Connection; + +public class DownloadThread extends Thread { + + Connection conn; + int startPos; + int endPos; + CyclicBarrier barrier; + String localFile; + + public DownloadThread(Connection conn, int startPos, int endPos, String localFile, CyclicBarrier barrier) { + + this.conn = conn; + this.startPos = startPos; + this.endPos = endPos; + this.localFile = localFile; + this.barrier = barrier; + } + + public void run() { + + try { + System.out.println("Begin to read [" + startPos + "-" + endPos + "]"); + + byte[] data = conn.read(startPos, endPos); + + RandomAccessFile file = new RandomAccessFile(localFile, "rw"); + + file.seek(startPos); + + file.write(data); + + file.close(); + + conn.close(); + + barrier.await(); // 等待别的线程完成 + + } catch (Exception e) { + e.printStackTrace(); + + } + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java new file mode 100644 index 0000000000..b5831a72bd --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java @@ -0,0 +1,126 @@ +package com.coderising.download.core; + +import java.io.IOException; +import java.io.RandomAccessFile; +import java.util.concurrent.CyclicBarrier; + +import com.coderising.download.api.Connection; +import com.coderising.download.api.ConnectionManager; +import com.coderising.download.api.DownloadListener; + +public class FileDownloader { + + private String url; + private String localFile; + + DownloadListener listener; + + ConnectionManager cm; + + private static final int DOWNLOAD_TRHEAD_NUM = 3; + + public FileDownloader(String _url, String localFile) { + this.url = _url; + this.localFile = localFile; + + } + + 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方法 + + // 下面的代码是示例代码, 也就是说只有一个线程, 你需要改造成多线程的。 + + CyclicBarrier barrier = new CyclicBarrier(DOWNLOAD_TRHEAD_NUM, new Runnable() { + public void run() { + listener.notifyFinished(); + } + }); + + Connection conn = null; + try { + + conn = cm.open(this.url); + + int length = conn.getContentLength(); + + createPlaceHolderFile(this.localFile, length); + + int[][] ranges = allocateDownloadRange(DOWNLOAD_TRHEAD_NUM, length); + + for (int i = 0; i < DOWNLOAD_TRHEAD_NUM; i++) { + + DownloadThread thread = new DownloadThread(cm.open(url), ranges[i][0], ranges[i][1], localFile, + barrier); + + thread.start(); + } + + } catch (Exception e) { + e.printStackTrace(); + } finally { + if (conn != null) { + conn.close(); + } + } + + } + + private void createPlaceHolderFile(String fileName, int contentLen) throws IOException { + + RandomAccessFile file = new RandomAccessFile(fileName, "rw"); + + for (int i = 0; i < contentLen; i++) { + file.write(0); + } + + file.close(); + } + + private int[][] allocateDownloadRange(int threadNum, int contentLen) { + int[][] ranges = new int[threadNum][2]; + + int eachThreadSize = contentLen / threadNum;// 每个线程需要下载的文件大小 + int left = contentLen % threadNum;// 剩下的归最后一个线程来处理 + + for (int i = 0; i < threadNum; i++) { + + int startPos = i * eachThreadSize; + + int endPos = (i + 1) * eachThreadSize - 1; + + if ((i == (threadNum - 1))) { + endPos += left; + } + ranges[i][0] = startPos; + ranges[i][1] = endPos; + + } + + return ranges; + } + + 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/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java new file mode 100644 index 0000000000..d1aa121f75 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java @@ -0,0 +1,84 @@ +package com.coderising.download.impl; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.net.HttpURLConnection; +import java.net.MalformedURLException; +import java.net.URL; +import java.net.URLConnection; +import java.util.Arrays; + +import com.coderising.download.api.Connection; +import com.coderising.download.api.ConnectionException; + +class ConnectionImpl implements Connection { + + URL url; + static final int BUFFER_SIZE = 1024; + + ConnectionImpl(String _url) throws ConnectionException { + try { + url = new URL(_url); + } catch (MalformedURLException e) { + throw new ConnectionException(e); + } + } + + @Override + public byte[] read(int startPos, int endPos) throws IOException { + + HttpURLConnection httpConn = (HttpURLConnection) url.openConnection(); + + httpConn.setRequestProperty("Range", "bytes=" + startPos + "-" + endPos); + + InputStream is = httpConn.getInputStream(); + + // is.skip(startPos); + + byte[] buff = new byte[BUFFER_SIZE]; + + int totalLen = endPos - startPos + 1; + + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + + while (baos.size() < totalLen) { + + int len = is.read(buff); + if (len < 0) { + break; + } + baos.write(buff, 0, len); + } + + if (baos.size() > totalLen) { + byte[] data = baos.toByteArray(); + return Arrays.copyOf(data, totalLen); + } + + return baos.toByteArray(); + } + + @Override + public int getContentLength() { + + URLConnection con; + try { + con = url.openConnection(); + + return con.getContentLength(); + + } catch (IOException e) { + e.printStackTrace(); + } + + return -1; + + } + + @Override + public void close() { + + } + +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java new file mode 100644 index 0000000000..5e98063eaa --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java @@ -0,0 +1,15 @@ +package com.coderising.download.impl; + +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 { + + return new ConnectionImpl(url); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java new file mode 100644 index 0000000000..5b0f60c148 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java @@ -0,0 +1,113 @@ +package com.coderising.litestruts; + +import java.io.IOException; +import java.io.InputStream; +import java.util.HashMap; +import java.util.Map; + +import org.jdom2.Document; +import org.jdom2.Element; +import org.jdom2.JDOMException; +import org.jdom2.input.SAXBuilder; + +public class Configuration { + + Map actions = new HashMap<>(); + + public Configuration(String fileName) { + + String packageName = this.getClass().getPackage().getName(); + + packageName = packageName.replace('.', '/'); + + InputStream is = this.getClass().getResourceAsStream("/" + packageName + "/" + fileName); + + parseXML(is); + + try { + is.close(); + } catch (IOException e) { + throw new ConfigurationException(e); + } + } + + private void parseXML(InputStream is) { + + SAXBuilder builder = new SAXBuilder(); + + try { + + Document doc = builder.build(is); + + Element root = doc.getRootElement(); + + for (Element actionElement : root.getChildren("action")) { + + String actionName = actionElement.getAttributeValue("name"); + String clzName = actionElement.getAttributeValue("class"); + + ActionConfig ac = new ActionConfig(actionName, clzName); + + for (Element resultElement : actionElement.getChildren("result")) { + + String resultName = resultElement.getAttributeValue("name"); + String viewName = resultElement.getText().trim(); + + ac.addViewResult(resultName, viewName); + + } + + this.actions.put(actionName, ac); + } + + } catch (JDOMException e) { + throw new ConfigurationException(e); + + } catch (IOException e) { + throw new ConfigurationException(e); + + } + + } + + public String getClassName(String action) { + ActionConfig ac = this.actions.get(action); + if (ac == null) { + return null; + } + return ac.getClassName(); + } + + public String getResultView(String action, String resultName) { + ActionConfig ac = this.actions.get(action); + if (ac == null) { + return null; + } + return ac.getViewName(resultName); + } + + private static class ActionConfig { + + String name; + String clzName; + Map viewResult = new HashMap<>(); + + public ActionConfig(String actionName, String clzName) { + this.name = actionName; + this.clzName = clzName; + } + + public String getClassName() { + return clzName; + } + + public void addViewResult(String name, String viewName) { + viewResult.put(name, viewName); + } + + public String getViewName(String resultName) { + return viewResult.get(resultName); + } + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java new file mode 100644 index 0000000000..97e286827f --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java @@ -0,0 +1,21 @@ +package com.coderising.litestruts; + +import java.io.IOException; + +import org.jdom2.JDOMException; + +public class ConfigurationException extends RuntimeException { + + public ConfigurationException(String msg) { + super(msg); + } + + public ConfigurationException(JDOMException e) { + super(e); + } + + public ConfigurationException(IOException e) { + super(e); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java new file mode 100644 index 0000000000..5f41f42c62 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java @@ -0,0 +1,42 @@ +package com.coderising.litestruts; + +/** + * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 + * + * @author liuxin + * + */ +public class LoginAction { + private String name; + private String password; + private String message; + + public String getName() { + return name; + } + + public String getPassword() { + return password; + } + + public String execute() { + if ("test".equals(name) && "1234".equals(password)) { + this.message = "login successful"; + return "success"; + } + this.message = "login failed,please check your user/pwd"; + return "fail"; + } + + public void setName(String name) { + this.name = name; + } + + public void setPassword(String password) { + this.password = password; + } + + public String getMessage() { + return this.message; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java new file mode 100644 index 0000000000..1ba13d5245 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java @@ -0,0 +1,120 @@ +package com.coderising.litestruts; + +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +public class ReflectionUtil { + + public static List getSetterMethods(Class clz) { + + return getMethods(clz, "set"); + + } + + public static void setParameters(Object o, Map params) { + + List methods = getSetterMethods(o.getClass()); + + for (String name : params.keySet()) { + + String methodName = "set" + name; + + for (Method m : methods) { + + if (m.getName().equalsIgnoreCase(methodName)) { + try { + m.invoke(o, params.get(name)); + } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { + e.printStackTrace(); + } + } + } + } + + } + + public static List getGetterMethods(Class clz) { + return getMethods(clz, "get"); + } + + private static List getMethods(Class clz, String startWithName) { + + List methods = new ArrayList<>(); + + for (Method m : clz.getDeclaredMethods()) { + + if (m.getName().startsWith(startWithName)) { + + methods.add(m); + + } + + } + + return methods; + } + + public static Map getParamterMap(Object o) { + + Map params = new HashMap<>(); + + List methods = getGetterMethods(o.getClass()); + + for (Method m : methods) { + + String methodName = m.getName(); + String name = methodName.replaceFirst("get", "").toLowerCase(); + try { + Object value = m.invoke(o); + params.put(name, value); + } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { + + e.printStackTrace(); + } + } + + return params; + } + + //////////////////////// Backup /////////////////////////////////// + + public static List getGetterMethods_V1(Class clz) { + + List methods = new ArrayList<>(); + + for (Method m : clz.getDeclaredMethods()) { + + if (m.getName().startsWith("get")) { + + methods.add(m); + + } + + } + + return methods; + } + + public static List getSetterMethods_V1(Class clz) { + + List methods = new ArrayList<>(); + + for (Method m : clz.getDeclaredMethods()) { + + if (m.getName().startsWith("set")) { + + methods.add(m); + + } + + } + + return methods; + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java new file mode 100644 index 0000000000..b3fe556ebc --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java @@ -0,0 +1,56 @@ +package com.coderising.litestruts; + +import java.lang.reflect.Method; +import java.util.Map; + +public class Struts { + private final static Configuration cfg = new Configuration("struts.xml"); + + public static View runAction(String actionName, Map parameters) { + /* + * + * 0. 读取配置文件struts.xml + * + * 1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) + * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , + * "password"="1234") , 那就应该调用 setName和setPassword方法 + * + * 2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success" + * + * 3. 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 + * {"message": "登录成功"} , 放到View对象的parameters + * + * 4. 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, + * 放到View对象的jsp字段中。 + * + */ + + String clzName = cfg.getClassName(actionName); + + if (clzName == null) { + return null; + } + + try { + Class clz = Class.forName(clzName); + Object action = clz.newInstance(); + + ReflectionUtil.setParameters(action, parameters); + + Method m = clz.getDeclaredMethod("execute"); + String resultName = (String) m.invoke(action); + + Map params = ReflectionUtil.getParamterMap(action); + String resultView = cfg.getResultView(actionName, resultName); + View view = new View(); + view.setParameters(params); + view.setJsp(resultView); + return view; + + } catch (Exception e) { + e.printStackTrace(); + } + + return null; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java new file mode 100644 index 0000000000..f1e7fcfa19 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java @@ -0,0 +1,26 @@ +package com.coderising.litestruts; + +import java.util.Map; + +public class View { + private String jsp; + private Map parameters; + + public String getJsp() { + return jsp; + } + + public View setJsp(String jsp) { + this.jsp = jsp; + return this; + } + + public Map getParameters() { + return parameters; + } + + public View setParameters(Map parameters) { + this.parameters = parameters; + return this; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java new file mode 100644 index 0000000000..2f944d3b91 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java @@ -0,0 +1,37 @@ +package com.coding.basic; + +public class BinaryTreeNode { + + private Object data; + private BinaryTreeNode left; + private BinaryTreeNode right; + + public Object getData() { + return data; + } + + public void setData(Object data) { + this.data = data; + } + + public BinaryTreeNode getLeft() { + return left; + } + + public void setLeft(BinaryTreeNode left) { + this.left = left; + } + + public BinaryTreeNode getRight() { + return right; + } + + public void setRight(BinaryTreeNode right) { + this.right = right; + } + + public BinaryTreeNode insert(Object o) { + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java new file mode 100644 index 0000000000..f30dfc8edf --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java @@ -0,0 +1,8 @@ +package com.coding.basic; + +public interface Iterator { + public boolean hasNext(); + + public Object next(); + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java new file mode 100644 index 0000000000..03fa879b2e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java @@ -0,0 +1,13 @@ +package com.coding.basic; + +public interface List { + public void add(Object o); + + public void add(int index, Object o); + + public Object get(int index); + + public Object remove(int index); + + public int size(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java new file mode 100644 index 0000000000..b2908512c5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java @@ -0,0 +1,19 @@ +package com.coding.basic; + +public class Queue { + + public void enQueue(Object o) { + } + + public Object deQueue() { + return null; + } + + public boolean isEmpty() { + return false; + } + + public int size() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java new file mode 100644 index 0000000000..81dfe5bdfe --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java @@ -0,0 +1,36 @@ +package com.coding.basic.array; + +import com.coding.basic.Iterator; +import com.coding.basic.List; + +public class ArrayList implements List { + + private int size = 0; + + private Object[] elementData = new Object[100]; + + public void add(Object o) { + + } + + public void add(int index, Object o) { + + } + + public Object get(int index) { + return null; + } + + public Object remove(int index) { + return null; + } + + public int size() { + return -1; + } + + public Iterator iterator() { + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java new file mode 100644 index 0000000000..0e8e077db7 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java @@ -0,0 +1,96 @@ +package com.coding.basic.array; + +public class ArrayUtil { + + /** + * 给定一个整形数组a , 对该数组的值进行置换 例如: a = [7, 9 , 30, 3] , 置换后为 [3, 30, 9,7] 如果 a = + * [7, 9, 30, 3, 4] , 置换后为 [4,3, 30 , 9,7] + * + * @param origin + * @return + */ + public void reverseArray(int[] origin) { + + } + + /** + * 现在有如下的一个数组: int oldArr[]={1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5} + * 要求将以上数组中值为0的项去掉,将不为0的值存入一个新的数组,生成的新数组为: {1,3,4,5,6,6,5,4,7,6,7,5} + * + * @param oldArray + * @return + */ + + public int[] removeZero(int[] oldArray) { + return null; + } + + /** + * 给定两个已经排序好的整形数组, a1和a2 , 创建一个新的数组a3, 使得a3 包含a1和a2 的所有元素, 并且仍然是有序的 例如 a1 = + * [3, 5, 7,8] a2 = [4, 5, 6,7] 则 a3 为[3,4,5,6,7,8] , 注意: 已经消除了重复 + * + * @param array1 + * @param array2 + * @return + */ + + public int[] merge(int[] array1, int[] array2) { + return null; + } + + /** + * 把一个已经存满数据的数组 oldArray的容量进行扩展, 扩展后的新数据大小为oldArray.length + size + * 注意,老数组的元素在新数组中需要保持 例如 oldArray = [2,3,6] , size = 3,则返回的新数组为 + * [2,3,6,0,0,0] + * + * @param oldArray + * @param size + * @return + */ + public int[] grow(int[] oldArray, int size) { + return null; + } + + /** + * 斐波那契数列为:1,1,2,3,5,8,13,21...... ,给定一个最大值, 返回小于该值的数列 例如, max = 15 , + * 则返回的数组应该为 [1,1,2,3,5,8,13] max = 1, 则返回空数组 [] + * + * @param max + * @return + */ + public int[] fibonacci(int max) { + return null; + } + + /** + * 返回小于给定最大值max的所有素数数组 例如max = 23, 返回的数组为[2,3,5,7,11,13,17,19] + * + * @param max + * @return + */ + public int[] getPrimes(int max) { + return null; + } + + /** + * 所谓“完数”, 是指这个数恰好等于它的因子之和,例如6=1+2+3 给定一个最大值max, 返回一个数组, 数组中是小于max 的所有完数 + * + * @param max + * @return + */ + public int[] getPerfectNumbers(int max) { + return null; + } + + /** + * 用seperator 把数组 array给连接起来 例如array= [3,8,9], seperator = "-" 则返回值为"3-8-9" + * + * @param array + * @param s + * @return + */ + public String join(int[] array, String seperator) { + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java new file mode 100644 index 0000000000..305989d5de --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java @@ -0,0 +1,151 @@ +package com.coding.basic.linklist; + +public class LRUPageFrame { + + private static class Node { + + Node prev; + Node next; + int pageNum; + + Node() { + } + } + + private int capacity; + + private int currentSize; + private Node first;// 链表头 + private Node last;// 链表尾 + + public LRUPageFrame(int capacity) { + this.currentSize = 0; + this.capacity = capacity; + + } + + /** + * 获取缓存中对象 + * + * @param key + * @return + */ + public void access(int pageNum) { + + Node node = find(pageNum); + // 在该队列中存在, 则提到队列头 + if (node != null) { + + moveExistingNodeToHead(node); + + } else { + + node = new Node(); + node.pageNum = pageNum; + + // 缓存容器是否已经超过大小. + if (currentSize >= capacity) { + removeLast(); + + } + + addNewNodetoHead(node); + + } + } + + private void addNewNodetoHead(Node node) { + + if (isEmpty()) { + + node.prev = null; + node.next = null; + first = node; + last = node; + + } else { + node.prev = null; + node.next = first; + first.prev = node; + first = node; + } + this.currentSize++; + } + + private Node find(int data) { + + Node node = first; + while (node != null) { + if (node.pageNum == data) { + return node; + } + node = node.next; + } + return null; + + } + + /** + * 删除链表尾部节点 表示 删除最少使用的缓存对象 + */ + private void removeLast() { + Node prev = last.prev; + prev.next = null; + last.prev = null; + last = prev; + this.currentSize--; + } + + /** + * 移动到链表头,表示这个节点是最新使用过的 + * + * @param node + */ + private void moveExistingNodeToHead(Node node) { + + if (node == first) { + + return; + } else if (node == last) { + // 当前节点是链表尾, 需要放到链表头 + Node prevNode = node.prev; + prevNode.next = null; + last.prev = null; + last = prevNode; + + } else { + // node 在链表的中间, 把node 的前后节点连接起来 + Node prevNode = node.prev; + prevNode.next = node.next; + + Node nextNode = node.next; + nextNode.prev = prevNode; + + } + + node.prev = null; + node.next = first; + first.prev = node; + first = node; + + } + + private boolean isEmpty() { + return (first == null) && (last == null); + } + + public String toString() { + StringBuilder buffer = new StringBuilder(); + Node node = first; + while (node != null) { + buffer.append(node.pageNum); + + node = node.next; + if (node != null) { + buffer.append(","); + } + } + return buffer.toString(); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java new file mode 100644 index 0000000000..6c8b4a3315 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java @@ -0,0 +1,129 @@ +package com.coding.basic.linklist; + +import com.coding.basic.Iterator; +import com.coding.basic.List; + +public class LinkedList implements List { + + private Node head; + + public void add(Object o) { + + } + + public void add(int index, Object o) { + + } + + public Object get(int index) { + return null; + } + + public Object remove(int index) { + return null; + } + + public int size() { + return -1; + } + + public void addFirst(Object o) { + + } + + public void addLast(Object o) { + + } + + public Object removeFirst() { + return null; + } + + public Object removeLast() { + return null; + } + + public Iterator iterator() { + return null; + } + + private static class Node { + Object data; + Node next; + + } + + /** + * 把该链表逆置 例如链表为 3->7->10 , 逆置后变为 10->7->3 + */ + public void reverse() { + + } + + /** + * 删除一个单链表的前半部分 例如:list = 2->5->7->8 , 删除以后的值为 7->8 如果list = 2->5->7->8->10 + * ,删除以后的值为7,8,10 + * + */ + public void removeFirstHalf() { + + } + + /** + * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 + * + * @param i + * @param length + */ + public void remove(int i, int length) { + + } + + /** + * 假定当前链表和listB均包含已升序排列的整数 从当前链表中取出那些listB所指定的元素 例如当前链表 = + * 11->101->201->301->401->501->601->701 listB = 1->3->4->6 + * 返回的结果应该是[101,301,401,601] + * + * @param list + */ + public int[] getElements(LinkedList list) { + return null; + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 从当前链表中中删除在listB中出现的元素 + * + * @param list + */ + + public void subtract(LinkedList list) { + + } + + /** + * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) + */ + public void removeDuplicateValues() { + + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) + * + * @param min + * @param max + */ + public void removeRange(int min, int max) { + + } + + /** + * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) + * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 + * + * @param list + */ + public LinkedList intersection(LinkedList list) { + return null; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java new file mode 100644 index 0000000000..83b76cb872 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java @@ -0,0 +1,26 @@ +package com.coding.basic.stack; + +import com.coding.basic.array.ArrayList; + +public class Stack { + private ArrayList elementData = new ArrayList(); + + public void push(Object o) { + } + + public Object pop() { + return null; + } + + public Object peek() { + return null; + } + + public boolean isEmpty() { + return false; + } + + public int size() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java new file mode 100644 index 0000000000..100bfc46a9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java @@ -0,0 +1,140 @@ +package com.coding.basic.stack; + +import java.util.Stack; + +public class StackUtil { + + public static void bad_reverse(Stack s) { + if (s == null || s.isEmpty()) { + return; + } + Stack tmpStack = new Stack(); + while (!s.isEmpty()) { + tmpStack.push(s.pop()); + } + + s = tmpStack; + + } + + /** + * 假设栈中的元素是Integer, 从栈顶到栈底是 : 5,4,3,2,1 调用该方法后, 元素次序变为: 1,2,3,4,5 + * 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 + */ + public static void reverse(Stack s) { + if (s == null || s.isEmpty()) { + return; + } + Integer top = s.pop(); + reverse(s); + addToBottom(s, top); + + } + + public static void addToBottom(Stack s, Integer value) { + if (s.isEmpty()) { + s.push(value); + } else { + Integer top = s.pop(); + addToBottom(s, value); + s.push(top); + } + + } + + /** + * 删除栈中的某个元素 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 + * + * @param o + */ + public static void remove(Stack s, Object o) { + if (s == null || s.isEmpty()) { + return; + } + Stack tmpStack = new Stack(); + + while (!s.isEmpty()) { + Object value = s.pop(); + if (!value.equals(o)) { + tmpStack.push(value); + } + } + + while (!tmpStack.isEmpty()) { + s.push(tmpStack.pop()); + } + } + + /** + * 从栈顶取得len个元素, 原来的栈中元素保持不变 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, + * 可以使用另外一个栈来辅助 + * + * @param len + * @return + */ + public static Object[] getTop(Stack s, int len) { + + if (s == null || s.isEmpty() || s.size() < len || len <= 0) { + return null; + } + + Stack tmpStack = new Stack(); + int i = 0; + Object[] result = new Object[len]; + while (!s.isEmpty()) { + Object value = s.pop(); + tmpStack.push(value); + result[i++] = value; + if (i == len) { + break; + } + } + + return result; + } + + /** + * 字符串s 可能包含这些字符: ( ) [ ] { }, a,b,c... x,yz 使用堆栈检查字符串s中的括号是不是成对出现的。 例如s = + * "([e{d}f])" , 则该字符串中的括号是成对出现, 该方法返回true 如果 s = "([b{x]y})", + * 则该字符串中的括号不是成对出现的, 该方法返回false; + * + * @param s + * @return + */ + public static boolean isValidPairs(String s) { + + Stack stack = new Stack(); + for (int i = 0; i < s.length(); i++) { + char c = s.charAt(i); + + if (c == '(' || c == '[' || c == '{') { + + stack.push(c); + + } else if (c == ')') { + + char topChar = stack.pop(); + if (topChar != '(') { + return false; + } + + } else if (c == ']') { + + char topChar = stack.pop(); + if (topChar != '[') { + return false; + } + + } else if (c == '}') { + + char topChar = stack.pop(); + if (topChar != '{') { + return false; + } + + } + } + return stack.size() == 0; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java new file mode 100644 index 0000000000..1a479c9b97 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java @@ -0,0 +1,15 @@ +package com.coding.basic.stack.expr; + +public class InfixExpr { + String expr = null; + + public InfixExpr(String expr) { + this.expr = expr; + } + + public float evaluate() { + + return 0.0f; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java new file mode 100644 index 0000000000..feb20c7d5c --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java @@ -0,0 +1,47 @@ +package com.coding.basic.stack.expr; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class InfixExprTest { + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testEvaluate() { + // InfixExpr expr = new InfixExpr("300*20+12*5-20/4"); + { + InfixExpr expr = new InfixExpr("2+3*4+5"); + Assert.assertEquals(19.0, expr.evaluate(), 0.001f); + } + { + InfixExpr expr = new InfixExpr("3*20+12*5-40/2"); + Assert.assertEquals(100.0, expr.evaluate(), 0.001f); + } + + { + InfixExpr expr = new InfixExpr("3*20/2"); + Assert.assertEquals(30, expr.evaluate(), 0.001f); + } + + { + InfixExpr expr = new InfixExpr("20/2*3"); + Assert.assertEquals(30, expr.evaluate(), 0.001f); + } + + { + InfixExpr expr = new InfixExpr("10-30+50"); + Assert.assertEquals(30, expr.evaluate(), 0.001f); + } + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml new file mode 100644 index 0000000000..e5d9aebba8 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml @@ -0,0 +1,11 @@ + + + + /jsp/homepage.jsp + /jsp/showLogin.jsp + + + /jsp/welcome.jsp + /jsp/error.jsp + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java new file mode 100644 index 0000000000..5e4259bddf --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java @@ -0,0 +1,42 @@ +package com.coderising.download.api; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.coderising.download.impl.ConnectionManagerImpl; + +public class ConnectionTest { + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testContentLength() throws Exception { + ConnectionManager connMan = new ConnectionManagerImpl(); + Connection conn = connMan.open("http://www.hinews.cn/pic/0/13/91/26/13912621_821796.jpg"); + Assert.assertEquals(35470, conn.getContentLength()); + } + + @Test + public void testRead() throws Exception { + ConnectionManager connMan = new ConnectionManagerImpl(); + Connection conn = connMan.open("http://www.hinews.cn/pic/0/13/91/26/13912621_821796.jpg"); + + byte[] data = conn.read(0, 35469); + Assert.assertEquals(35470, data.length); + + data = conn.read(0, 1023); + Assert.assertEquals(1024, data.length); + + data = conn.read(1024, 2023); + Assert.assertEquals(1000, data.length); + + // 测试不充分,没有断言内容是否正确 + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java new file mode 100644 index 0000000000..2631a1f90b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java @@ -0,0 +1,56 @@ +package com.coderising.download.core; + +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://www.hinews.cn/pic/0/13/91/26/13912621_821796.jpg"; + + String url = "http://images2015.cnblogs.com/blog/610238/201604/610238-20160421154632101-286208268.png"; + + FileDownloader downloader = new FileDownloader(url, "c:\\coderising\\tmp\\test.jpg"); + + 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/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java new file mode 100644 index 0000000000..b8ab6c04b9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java @@ -0,0 +1,46 @@ +package com.coderising.litestruts; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class ConfigurationTest { + + Configuration cfg = new Configuration("struts.xml"); + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testGetClassName() { + + String clzName = cfg.getClassName("login"); + Assert.assertEquals("com.coderising.litestruts.LoginAction", clzName); + + clzName = cfg.getClassName("logout"); + Assert.assertEquals("com.coderising.litestruts.LogoutAction", clzName); + } + + @Test + public void testGetResultView() { + String jsp = cfg.getResultView("login", "success"); + Assert.assertEquals("/jsp/homepage.jsp", jsp); + + jsp = cfg.getResultView("login", "fail"); + Assert.assertEquals("/jsp/showLogin.jsp", jsp); + + jsp = cfg.getResultView("logout", "success"); + Assert.assertEquals("/jsp/welcome.jsp", jsp); + + jsp = cfg.getResultView("logout", "error"); + Assert.assertEquals("/jsp/error.jsp", jsp); + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java new file mode 100644 index 0000000000..4362ae0ac7 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java @@ -0,0 +1,104 @@ +package com.coderising.litestruts; + +import java.lang.reflect.Field; +import java.lang.reflect.Method; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class ReflectionUtilTest { + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testGetSetterMethod() throws Exception { + + String name = "com.coderising.litestruts.LoginAction"; + Class clz = Class.forName(name); + List methods = ReflectionUtil.getSetterMethods(clz); + + Assert.assertEquals(2, methods.size()); + + List expectedNames = new ArrayList<>(); + expectedNames.add("setName"); + expectedNames.add("setPassword"); + + Set acctualNames = new HashSet<>(); + for (Method m : methods) { + acctualNames.add(m.getName()); + } + + Assert.assertTrue(acctualNames.containsAll(expectedNames)); + } + + @Test + public void testSetParameters() throws Exception { + String name = "com.coderising.litestruts.LoginAction"; + Class clz = Class.forName(name); + Object o = clz.newInstance(); + + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "1234"); + + ReflectionUtil.setParameters(o, params); + + Field f = clz.getDeclaredField("name"); + f.setAccessible(true); + Assert.assertEquals("test", f.get(o)); + + f = clz.getDeclaredField("password"); + f.setAccessible(true); + Assert.assertEquals("1234", f.get(o)); + } + + @Test + public void testGetGetterMethod() throws Exception { + String name = "com.coderising.litestruts.LoginAction"; + Class clz = Class.forName(name); + List methods = ReflectionUtil.getGetterMethods(clz); + + Assert.assertEquals(3, methods.size()); + + List expectedNames = new ArrayList<>(); + expectedNames.add("getMessage"); + expectedNames.add("getName"); + expectedNames.add("getPassword"); + + Set acctualNames = new HashSet<>(); + for (Method m : methods) { + acctualNames.add(m.getName()); + } + + Assert.assertTrue(acctualNames.containsAll(expectedNames)); + } + + @Test + public void testGetParamters() throws Exception { + String name = "com.coderising.litestruts.LoginAction"; + Class clz = Class.forName(name); + LoginAction action = (LoginAction) clz.newInstance(); + action.setName("test"); + action.setPassword("123456"); + + Map params = ReflectionUtil.getParamterMap(action); + + Assert.assertEquals(3, params.size()); + Assert.assertEquals(null, params.get("messaage")); + Assert.assertEquals("test", params.get("name")); + Assert.assertEquals("123456", params.get("password")); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java new file mode 100644 index 0000000000..5174fc47f1 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java @@ -0,0 +1,37 @@ +package com.coderising.litestruts; + +import java.util.HashMap; +import java.util.Map; + +import org.junit.Assert; +import org.junit.Test; + +public class StrutsTest { + @Test + public void testLoginActionSuccess() { + + String actionName = "login"; + + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "1234"); + + View view = Struts.runAction(actionName, params); + + Assert.assertEquals("/jsp/homepage.jsp", view.getJsp()); + Assert.assertEquals("login successful", view.getParameters().get("message")); + } + + @Test + public void testLoginActionFailed() { + String actionName = "login"; + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "123456"); // 密码和预设的不一致 + + View view = Struts.runAction(actionName, params); + + Assert.assertEquals("/jsp/showLogin.jsp", view.getJsp()); + Assert.assertEquals("login failed,please check your user/pwd", view.getParameters().get("message")); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java new file mode 100644 index 0000000000..47ef10e125 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java @@ -0,0 +1,32 @@ +package com.coding.basic.linklist; + +import org.junit.Assert; +import org.junit.Test; + +public class LRUPageFrameTest { + + @Test + public void testAccess() { + LRUPageFrame frame = new LRUPageFrame(3); + frame.access(7); + frame.access(0); + frame.access(1); + Assert.assertEquals("1,0,7", frame.toString()); + frame.access(2); + Assert.assertEquals("2,1,0", frame.toString()); + frame.access(0); + Assert.assertEquals("0,2,1", frame.toString()); + frame.access(0); + Assert.assertEquals("0,2,1", frame.toString()); + frame.access(3); + Assert.assertEquals("3,0,2", frame.toString()); + frame.access(0); + Assert.assertEquals("0,3,2", frame.toString()); + frame.access(4); + Assert.assertEquals("4,0,3", frame.toString()); + frame.access(5); + Assert.assertEquals("5,4,0", frame.toString()); + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java new file mode 100644 index 0000000000..39a1b3f3e0 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java @@ -0,0 +1,197 @@ +package com.coding.basic.linklist; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class LinkedListTest { + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testReverse() { + LinkedList l = new LinkedList(); + + Assert.assertEquals("[]", l.toString()); + + l.add(1); + l.reverse(); + Assert.assertEquals("[1]", l.toString()); + + l.add(2); + l.add(3); + l.add(4); + + l.reverse(); + Assert.assertEquals("[4,3,2,1]", l.toString()); + } + + @Test + public void testRemoveFirstHalf() { + { + LinkedList linkedList = new LinkedList(); + linkedList.add(1); + linkedList.add(2); + linkedList.add(3); + linkedList.add(4); + linkedList.removeFirstHalf(); + Assert.assertEquals("[3,4]", linkedList.toString()); + } + { + LinkedList linkedList = new LinkedList(); + linkedList.add(1); + linkedList.add(2); + linkedList.add(3); + linkedList.add(4); + linkedList.add(5); + linkedList.removeFirstHalf(); + Assert.assertEquals("[3,4,5]", linkedList.toString()); + } + } + + @Test + public void testRemoveIntInt() { + { + LinkedList linkedList = new LinkedList(); + linkedList.add(1); + linkedList.add(2); + linkedList.add(3); + linkedList.add(4); + linkedList.remove(0, 2); + Assert.assertEquals("[3,4]", linkedList.toString()); + } + { + LinkedList linkedList = new LinkedList(); + linkedList.add(1); + linkedList.add(2); + linkedList.add(3); + linkedList.add(4); + linkedList.remove(3, 2); + Assert.assertEquals("[1,2,3]", linkedList.toString()); + } + { + LinkedList linkedList = new LinkedList(); + linkedList.add(1); + linkedList.add(2); + linkedList.add(3); + linkedList.add(4); + linkedList.remove(2, 2); + Assert.assertEquals("[1,2]", linkedList.toString()); + } + } + + @Test + public void testGetElements() { + LinkedList linkedList = new LinkedList(); + linkedList.add(11); + linkedList.add(101); + linkedList.add(201); + linkedList.add(301); + linkedList.add(401); + linkedList.add(501); + linkedList.add(601); + linkedList.add(701); + LinkedList list = new LinkedList(); + list.add(1); + list.add(3); + list.add(4); + list.add(6); + Assert.assertArrayEquals(new int[] { 101, 301, 401, 601 }, linkedList.getElements(list)); + } + + @Test + public void testSubtract() { + LinkedList list1 = new LinkedList(); + list1.add(101); + list1.add(201); + list1.add(301); + list1.add(401); + list1.add(501); + list1.add(601); + list1.add(701); + + LinkedList list2 = new LinkedList(); + + list2.add(101); + list2.add(201); + list2.add(301); + list2.add(401); + list2.add(501); + + list1.subtract(list2); + + Assert.assertEquals("[601,701]", list1.toString()); + } + + @Test + public void testRemoveDuplicateValues() { + LinkedList list = new LinkedList(); + list.add(1); + list.add(1); + list.add(2); + list.add(2); + list.add(3); + list.add(5); + list.add(5); + list.add(6); + list.removeDuplicateValues(); + + Assert.assertEquals("[1,2,3,5,6]", list.toString()); + } + + @Test + public void testRemoveRange() { + { + LinkedList linkedList = new LinkedList(); + + linkedList.add(11); + linkedList.add(12); + linkedList.add(13); + linkedList.add(14); + linkedList.add(16); + linkedList.add(16); + linkedList.add(19); + + linkedList.removeRange(10, 19); + Assert.assertEquals("[19]", linkedList.toString()); + } + + { + LinkedList linkedList = new LinkedList(); + + linkedList.add(11); + linkedList.add(12); + linkedList.add(13); + linkedList.add(14); + linkedList.add(16); + linkedList.add(16); + linkedList.add(19); + + linkedList.removeRange(10, 14); + Assert.assertEquals("[14,16,16,19]", linkedList.toString()); + } + } + + @Test + public void testIntersection() { + LinkedList list1 = new LinkedList(); + list1.add(1); + list1.add(6); + list1.add(7); + + LinkedList list2 = new LinkedList(); + list2.add(2); + list2.add(5); + list2.add(6); + + LinkedList newList = list1.intersection(list2); + Assert.assertEquals("[6]", newList.toString()); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java new file mode 100644 index 0000000000..5976823f36 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java @@ -0,0 +1,78 @@ +package com.coding.basic.stack; + +import java.util.Stack; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class StackUtilTest { + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testAddToBottom() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + + StackUtil.addToBottom(s, 0); + + Assert.assertEquals("[0, 1, 2, 3]", s.toString()); + + } + + @Test + public void testReverse() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + s.push(4); + s.push(5); + Assert.assertEquals("[1, 2, 3, 4, 5]", s.toString()); + StackUtil.reverse(s); + Assert.assertEquals("[5, 4, 3, 2, 1]", s.toString()); + } + + @Test + public void testRemove() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + StackUtil.remove(s, 2); + Assert.assertEquals("[1, 3]", s.toString()); + } + + @Test + public void testGetTop() { + Stack s = new Stack(); + s.push(1); + s.push(2); + s.push(3); + s.push(4); + s.push(5); + { + Object[] values = StackUtil.getTop(s, 3); + Assert.assertEquals(5, values[0]); + Assert.assertEquals(4, values[1]); + Assert.assertEquals(3, values[2]); + } + } + + @Test + public void testIsValidPairs() { + Assert.assertTrue(StackUtil.isValidPairs("([e{d}f])")); + Assert.assertFalse(StackUtil.isValidPairs("([b{x]y})")); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml b/students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml new file mode 100644 index 0000000000..1da435d5b6 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml @@ -0,0 +1,27 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-61-collection + eulerlcs master java road collection + + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java new file mode 100644 index 0000000000..555f5ea954 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java @@ -0,0 +1,438 @@ +/** + * 90% or more copy from jdk + */ +package com.github.eulerlcs.jmr.algorithm; + +import java.util.Arrays; +import java.util.Collection; +import java.util.ConcurrentModificationException; +import java.util.Iterator; +import java.util.List; +import java.util.ListIterator; +import java.util.NoSuchElementException; +import java.util.Objects; +import java.util.RandomAccess; +import java.util.function.Consumer; + +public class ArrayList implements List, RandomAccess { + private static final int MAX_ARRAY_SIZE = 1 << 10; + private transient Object[] elementData = new Object[0]; + private int size; + private transient int modCount = 0; + + @Override + public int size() { + return size; + } + + @Override + public boolean isEmpty() { + return size == 0; + } + + @Override + public boolean contains(Object o) { + if (o == null) { + for (Object obi : elementData) { + if (obi == null) { + return true; + } + } + } else { + for (Object obj : elementData) { + if (o.equals(obj)) { + return true; + } + } + } + return false; + } + + @Override + public boolean containsAll(Collection c) { + for (Object e : c) + if (!contains(e)) + return false; + return true; + } + + @Override + public Object[] toArray() { + return Arrays.copyOf(elementData, size, elementData.getClass()); + } + + @SuppressWarnings("unchecked") + @Override + public T[] toArray(T[] a) { + if (a.length < size) { + return (T[]) Arrays.copyOf(elementData, size, a.getClass()); + } else { + System.arraycopy(elementData, 0, a, 0, size); + if (a.length > size) + a[size] = null; + return a; + } + } + + @Override + public boolean add(E e) { + ensureExplicitCapacity(size + 1); // Increments modCount!! + elementData[size] = e; + size++; + return true; + } + + @Override + public void add(int index, E element) { + if (index >= size) + throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); + ensureExplicitCapacity(size + 1); // Increments modCount!! + System.arraycopy(elementData, index, elementData, index + 1, size - index); + elementData[index] = element; + size++; + } + + @Override + public E remove(int index) { + if (index >= size) + throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); + + modCount++; + @SuppressWarnings("unchecked") + E oldValue = (E) elementData[index]; + int numMoved = size - index - 1; + if (numMoved > 0) + System.arraycopy(elementData, index + 1, elementData, index, numMoved); + elementData[--size] = null;// clear to let GC do its work + + return oldValue; + } + + @Override + public boolean remove(Object o) { + int index = -1; + + if (o == null) { + for (int i = 0; i < size; i++) + if (elementData[i] == null) { + index = i; + break; + } + } else { + for (int i = 0; i < size; i++) + if (o.equals(elementData[i])) { + index = i; + break; + } + } + + if (index > 0) { + modCount++; + int numMoved = size - index - 1; + if (numMoved > 0) + System.arraycopy(elementData, index + 1, elementData, index, numMoved); + elementData[--size] = null;// clear to let GC do its work + + return true; + } + + return false; + } + + @Override + public boolean removeAll(Collection c) { + boolean modified = false; + for (Object obj : c) { + modified |= remove(obj); + } + + return modified; + } + + @Override + public boolean addAll(Collection c) { + Object[] a = c.toArray(); + int numNew = a.length; + ensureExplicitCapacity(size + numNew);// Increments modCount + System.arraycopy(a, 0, elementData, size, numNew); + size += numNew; + return numNew != 0; + } + + @Override + public boolean addAll(int index, Collection c) { + if (index >= size) + throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); + + Object[] a = c.toArray(); + int numNew = a.length; + ensureExplicitCapacity(size + numNew);// Increments modCount + + int numMoved = size - index; + if (numMoved > 0) + System.arraycopy(elementData, index, elementData, index + numNew, numMoved); + + System.arraycopy(a, 0, elementData, index, numNew); + size += numNew; + return numNew != 0; + } + + @Override + public boolean retainAll(Collection c) { + final Object[] elementData = this.elementData; + int r = 0, w = 0; + boolean modified = false; + for (; r < size; r++) + if (c.contains(elementData[r])) + elementData[w++] = elementData[r]; + + if (w != size) { + // clear to let GC do its work + for (int i = w; i < size; i++) + elementData[i] = null; + modCount += size - w; + size = w; + modified = true; + } + + return modified; + } + + @Override + public void clear() { + modCount++; + for (int i = 0; i < size; i++) + elementData[i] = null; + + size = 0; + } + + @Override + public List subList(int fromIndex, int toIndex) { + throw new UnsupportedOperationException(); + } + + @SuppressWarnings("unchecked") + @Override + public E get(int index) { + if (index >= size) + throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); + + return (E) elementData[index]; + } + + @SuppressWarnings("unchecked") + @Override + public E set(int index, E element) { + if (index >= size) + throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); + + E oldValue = (E) elementData[index]; + elementData[index] = element; + return oldValue; + } + + @Override + public int indexOf(Object o) { + if (o == null) { + for (int i = 0; i < size; i++) + if (elementData[i] == null) + return i; + } else { + for (int i = 0; i < size; i++) + if (o.equals(elementData[i])) + return i; + } + + return -1; + } + + @Override + public int lastIndexOf(Object o) { + if (o == null) { + for (int i = size - 1; i >= 0; i--) + if (elementData[i] == null) + return i; + } else { + for (int i = size - 1; i >= 0; i--) + if (o.equals(elementData[i])) + return i; + } + + return -1; + } + + private void ensureExplicitCapacity(int minCapacity) { + modCount++; + + if (elementData.length > minCapacity) { + return; + } else if (minCapacity > MAX_ARRAY_SIZE) { + throw new OutOfMemoryError(); + } + + int oldCapacity = elementData.length; + + int newCapacity = oldCapacity == 0 ? 10 : (oldCapacity + (oldCapacity >> 1)); + if (newCapacity > MAX_ARRAY_SIZE) { + newCapacity = MAX_ARRAY_SIZE; + } + + elementData = Arrays.copyOf(elementData, newCapacity); + } + + @Override + public Iterator iterator() { + return new Itr(); + } + + @Override + public ListIterator listIterator() { + return new ListItr(0); + } + + @Override + public ListIterator listIterator(int index) { + if (index < 0 || index > size) + throw new IndexOutOfBoundsException("Index: " + index); + return new ListItr(index); + } + + /** + * fully copy from jdk ArrayList.Itr + */ + private class Itr implements Iterator { + int cursor; // index of next element to return + int lastRet = -1; // index of last element returned; -1 if no such + int expectedModCount = modCount; + + @Override + public boolean hasNext() { + return cursor != size; + } + + @Override + @SuppressWarnings("unchecked") + public E next() { + checkForComodification(); + int i = cursor; + if (i >= size) + throw new NoSuchElementException(); + Object[] elementData = ArrayList.this.elementData; + if (i >= elementData.length) + throw new ConcurrentModificationException(); + cursor = i + 1; + return (E) elementData[lastRet = i]; + } + + @Override + public void remove() { + if (lastRet < 0) + throw new IllegalStateException(); + checkForComodification(); + + try { + ArrayList.this.remove(lastRet); + cursor = lastRet; + lastRet = -1; + expectedModCount = modCount; + } catch (IndexOutOfBoundsException ex) { + throw new ConcurrentModificationException(); + } + } + + @Override + @SuppressWarnings("unchecked") + public void forEachRemaining(Consumer consumer) { + Objects.requireNonNull(consumer); + final int size = ArrayList.this.size; + int i = cursor; + if (i >= size) { + return; + } + final Object[] elementData = ArrayList.this.elementData; + if (i >= elementData.length) { + throw new ConcurrentModificationException(); + } + while (i != size && modCount == expectedModCount) { + consumer.accept((E) elementData[i++]); + } + // update once at end of iteration to reduce heap write traffic + cursor = i; + lastRet = i - 1; + checkForComodification(); + } + + final void checkForComodification() { + if (modCount != expectedModCount) + throw new ConcurrentModificationException(); + } + } + + /** + * fully copy from jdk ArrayList.ListItr + */ + private class ListItr extends Itr implements ListIterator { + ListItr(int index) { + super(); + cursor = index; + } + + @Override + public boolean hasPrevious() { + return cursor != 0; + } + + @Override + public int nextIndex() { + return cursor; + } + + @Override + public int previousIndex() { + return cursor - 1; + } + + @Override + @SuppressWarnings("unchecked") + public E previous() { + checkForComodification(); + int i = cursor - 1; + if (i < 0) + throw new NoSuchElementException(); + Object[] elementData = ArrayList.this.elementData; + if (i >= elementData.length) + throw new ConcurrentModificationException(); + cursor = i; + return (E) elementData[lastRet = i]; + } + + @Override + public void set(E e) { + if (lastRet < 0) + throw new IllegalStateException(); + checkForComodification(); + + try { + ArrayList.this.set(lastRet, e); + } catch (IndexOutOfBoundsException ex) { + throw new ConcurrentModificationException(); + } + } + + @Override + public void add(E e) { + checkForComodification(); + + try { + int i = cursor; + ArrayList.this.add(i, e); + cursor = i + 1; + lastRet = -1; + expectedModCount = modCount; + } catch (IndexOutOfBoundsException ex) { + throw new ConcurrentModificationException(); + } + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java new file mode 100644 index 0000000000..47ed2e0bef --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java @@ -0,0 +1,44 @@ +package com.github.eulerlcs.jmr.algorithm; + +import java.util.List; + +import org.junit.After; +import org.junit.AfterClass; +import org.junit.Assert; +import org.junit.Before; +import org.junit.BeforeClass; +import org.junit.Test; + +public class TestArrayList { + + @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 test_foreach() { + List list = new ArrayList<>(); + list.add(1); + list.add(2); + list.add(3); + + int sum = 0; + for (Integer item : list) { + sum += item; + } + + Assert.assertEquals(sum, 6); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml new file mode 100644 index 0000000000..a7a77b73df --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml @@ -0,0 +1,11 @@ + + + + /jsp/homepage.jsp + /jsp/showLogin.jsp + + + /jsp/welcome.jsp + /jsp/error.jsp + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml new file mode 100644 index 0000000000..353155e346 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml @@ -0,0 +1,39 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-62-litestruts + eulerlcs master java road lite struts + + + + commons-digester + commons-digester + + + org.projectlombok + lombok + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + com.github.stefanbirkner + system-rules + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java new file mode 100644 index 0000000000..c9cc7522b5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java @@ -0,0 +1,279 @@ +/** + * 问题点: 没写注释,代码比较难读。尤其 merge方法。 + */ +package com.github.eulerlcs.jmr.algorithm; + +import java.util.Arrays; + +public class ArrayUtil { + + /** + * 给定一个整形数组a , 对该数组的值进行置换 例如: a = [7, 9 , 30, 3] , 置换后为 [3, 30, 9,7] 如果 a = + * [7, 9, 30, 3, 4] , 置换后为 [4,3, 30 , 9,7] + * + * @param origin + * @return + */ + public static void reverseArray(int[] origin) { + if (origin == null || origin.length < 2) { + return; + } + + for (int head = 0, tail = origin.length - 1; head < tail; head++, tail--) { + origin[head] = origin[head] ^ origin[tail]; + origin[tail] = origin[head] ^ origin[tail]; + origin[head] = origin[head] ^ origin[tail]; + } + } + + /** + * 现在有如下的一个数组: int oldArr[]={1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5} + * 要求将以上数组中值为0的项去掉,将不为0的值存入一个新的数组,生成的新数组为: {1,3,4,5,6,6,5,4,7,6,7,5} + * + * @param oldArray + * @return + */ + + public static int[] removeZero(int[] oldArray) { + if (oldArray == null) { + return new int[0]; + } + + int count = 0; + for (int i = 0; i < oldArray.length; i++) { + if (oldArray[i] != 0) + count++; + } + + int[] newArray = new int[count]; + int newIndex = 0; + for (int i = 0; i < oldArray.length; i++) { + if (oldArray[i] != 0) { + newArray[newIndex] = oldArray[i]; + newIndex++; + } + } + + return newArray; + } + + /** + * 给定两个已经排序好的整形数组, a1和a2 , 创建一个新的数组a3, 使得a3 包含a1和a2 的所有元素, 并且仍然是有序的 例如 a1 = + * [3, 5, 7,8] a2 = [4, 5, 6,7] 则 a3 为[3,4,5,6,7,8] , 注意: 已经消除了重复 + * + * @param array1 + * @param array2 + * @return + */ + + public static int[] merge(int[] array1, int[] array2) { + if (array1 == null || array1.length == 0) { + if (array2 == null || array2.length == 0) { + return new int[0]; + } else { + return Arrays.copyOf(array2, array2.length); + } + } else if (array2 == null || array2.length == 0) { + return Arrays.copyOf(array1, array1.length); + } + + int[] result = new int[array1.length + array2.length]; + int idxResult = 0; + int idx1 = 0; + int idx2 = 0; + + for (; idx1 < array1.length; idx1++) { + if (array1[idx1] < array2[idx2]) { + result[idxResult] = array1[idx1]; + idxResult++; + } else if (array1[idx1] == array2[idx2]) { + result[idxResult] = array1[idx1]; + idxResult++; + idx2++; + } else { + for (; idx2 < array2.length; idx2++) { + if (array2[idx2] < array1[idx1]) { + result[idxResult] = array2[idx2]; + idxResult++; + } else { + if (array2[idx2] == array1[idx1]) { + idx2++; + } + + break; + } + } + + if (idx2 == array2.length) { + break; + } else { + idx1--; + } + } + } + + if (idx1 < array1.length) { + System.arraycopy(array1, idx1, result, idxResult, array1.length - idx1); + idxResult += array1.length - idx1; + } + + if (idx2 < array2.length) { + System.arraycopy(array2, idx2, result, idxResult, array2.length - idx2); + idxResult += array2.length - idx2; + } + + result = removeZero(result); + return result; + } + + /** + * 把一个已经存满数据的数组 oldArray的容量进行扩展, 扩展后的新数据大小为oldArray.length + size + * 注意,老数组的元素在新数组中需要保持 例如 oldArray = [2,3,6] , size = 3,则返回的新数组为 + * [2,3,6,0,0,0] + * + * @param oldArray + * @param increaseCapacity + * @return + */ + public static int[] grow(int[] oldArray, int increaseCapacity) { + if (oldArray == null || increaseCapacity < 0) { + return new int[0]; + } + + int newCapacity = oldArray.length + increaseCapacity; + + int[] newArray = Arrays.copyOf(oldArray, newCapacity); + + return newArray; + } + + /** + * 斐波那契数列为:1,1,2,3,5,8,13,21...... ,给定一个最大值, 返回小于该值的数列 例如, max = 15 , + * 则返回的数组应该为 [1,1,2,3,5,8,13] max = 1, 则返回空数组 [] + * + * @param max + * @return + */ + public static int[] fibonacci(int max) { + if (max <= 1) { + return new int[0]; + } + + int[] result = new int[10]; + result[0] = 1; + result[1] = 1; + int idx = 2; + int sum = 2; + while (sum < max) { + if (idx >= result.length) { + grow(result, result.length * 2); + } + + result[idx] = sum; + sum = result[idx - 1] + result[idx]; + idx++; + } + + result = removeZero(result); + return result; + } + + /** + * 返回小于给定最大值max的所有素数数组 例如max = 23, 返回的数组为[2,3,5,7,11,13,17,19] + * + * @param max + * @return + */ + public static int[] getPrimes(int max) { + if (max < 2) { + return new int[0]; + } + + int[] all = new int[max]; + int index = 0; + int temp = 0; + + for (int i = 0; i < max; i++) { + all[i] = i; + } + + all[0] = 0; + all[1] = 0; + index = 2; + + // 筛法 + loops: for (; index < max;) { + for (int i = 2;; i++) { + temp = index * i; + if (temp >= max) { + break; + } + all[temp] = 0; + } + + for (int i = index + 1; i < max; i++) { + if (all[i] != 0) { + index = i; + continue loops; + } + } + + break; + } + + int[] result = removeZero(all); + return result; + } + + /** + * 所谓“完数”, 是指这个数恰好等于它的因子之和,例如6=1+2+3 给定一个最大值max, 返回一个数组, 数组中是小于max 的所有完数 + * + * @param max + * @return + */ + public static long[] getPerfectNumbers(long max) { + long[] perfect = new long[49];// 到2016年1月为止,共发现了49个完全数 + int idx = 0; + long sum = 1; + long sqrt = 0; + + for (long n = 2; n < max; n++) { + sum = 1; + sqrt = (long) Math.sqrt(n); + for (long i = 2; i <= sqrt; i++) { + if (n % i == 0) + sum += i + n / i; + } + + if (sum == n) { + perfect[idx] = n; + idx++; + } + } + + // return removeZero(perfect); + return perfect; + } + + /** + * 用separator 把数组 array给连接起来 例如array= [3,8,9], separator = "-" 则返回值为"3-8-9" + * + * @param array + * @param separator + * @return + */ + public static String join(int[] array, String separator) { + if (array == null || array.length == 0) { + return ""; + } + + StringBuilder sb = new StringBuilder(); + + for (int i = 0; i < array.length - 1; i++) { + sb.append(array[i] + separator); + } + sb.append(String.valueOf(array[array.length - 1])); + + return sb.toString(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java new file mode 100644 index 0000000000..4d9af132ac --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java @@ -0,0 +1,30 @@ +package com.github.eulerlcs.jmr.litestruts.action; + +import lombok.Getter; +import lombok.Setter; + +/** + * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 + * + * @author liuxin + * + */ +public class LoginAction { + @Setter + @Getter + private String name; + @Setter + @Getter + private String password; + @Getter + private String message; + + public String execute() { + if ("test".equals(name) && "1234".equals(password)) { + this.message = "login successful"; + return "success"; + } + this.message = "login failed,please check your user/pwd"; + return "fail"; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java new file mode 100644 index 0000000000..119e74e3e9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java @@ -0,0 +1,30 @@ +package com.github.eulerlcs.jmr.litestruts.action; + +import lombok.Getter; +import lombok.Setter; + +/** + * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 + * + * @author liuxin + * + */ +public class LogoutAction { + @Setter + @Getter + private String name; + @Setter + @Getter + private String password; + @Getter + private String message; + + public String execute() { + if ("test".equals(name) && "1234".equals(password)) { + this.message = "login successful"; + return "success"; + } + this.message = "login failed,please check your user/pwd"; + return "error"; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java new file mode 100644 index 0000000000..459abaae99 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java @@ -0,0 +1,200 @@ +package com.github.eulerlcs.jmr.litestruts.core; + +import java.io.File; +import java.io.IOException; +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; +import java.util.HashMap; +import java.util.Map; + +import org.apache.commons.digester.Digester; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.xml.sax.SAXException; + +import com.github.eulerlcs.jmr.litestruts.degister.StrutsConfig; +import com.github.eulerlcs.jmr.litestruts.degister.StrutsDigester; + +/** + *
    + *
  • 读取配置文件struts.xml
  • + *
  • 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) + * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , + * "password"="1234") , 那就应该调用 setName和setPassword方法
  • + *
  • 通过反射调用对象的exectue 方法, 并获得返回值,例如"success"
  • + *
  • 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 + * {"message": "登录成功"} , 放到View对象的parameters
  • + *
  • 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, 放到View对象的jsp字段中。
  • + *
+ */ +public class Struts { + private final static Logger log = LoggerFactory.getLogger(Struts.class); + private static StrutsConfig config = null; + + public static View runAction(String actionName, Map parameters) { + /* + * 0. 读取配置文件struts.xml + * + * 1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) + * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , + * "password"="1234") , 那就应该调用 setName和setPassword方法 + * + * 2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success" + * + * 3. 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 + * {"message": "登录成功"} , 放到View对象的parameters + * + * 4. 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, + * 放到View对象的jsp字段中。 + * + */ + + // 0. + getConfig(); + + // 1.1. + Object object = createInstance(actionName); + if (object == null) { + return null; + } + // 1.2. + if (!prepareParameters(object, parameters)) { + return null; + } + // 2. + String viewId = execute(object); + if (viewId == null) { + return null; + } + // 3. + View view = biuldView(object); + if (view == null) { + return null; + } + + // 4. + String uri = config.getActionMap().get(actionName).getResults().get(viewId).getUrl(); + view.setJsp(uri); + + return view; + } + + private static StrutsConfig getConfig() { + if (config != null) { + return config; + } + + Digester d = StrutsDigester.newInstance(); + try { + File file = new File("data", "struts.xml"); + config = (StrutsConfig) d.parse(file); + } catch (IOException | SAXException e) { + log.error("getConfig", e); + System.exit(1); + } + + return config; + } + + private static Object createInstance(String actionName) { + if (actionName == null) { + return null; + } + + String className = config.getActionMap().get(actionName).getClazz(); + Object object = null; + try { + Class clazz = Class.forName(className); + object = clazz.newInstance(); + } catch (ClassNotFoundException | InstantiationException | IllegalAccessException e) { + log.error("createInstance", e); + } + + return object; + } + + private static boolean prepareParameters(Object object, Map parameters) { + if (parameters == null || parameters.size() == 0) { + return true; + } + + Class clazz = object.getClass(); + Method setter = null; + + try { + for (String key : parameters.keySet()) { + setter = clazz.getMethod(biuldSetterName(key), String.class); + setter.setAccessible(true); + setter.invoke(object, parameters.get(key)); + } + } catch (NoSuchMethodException | SecurityException | IllegalAccessException | IllegalArgumentException + | InvocationTargetException e) { + log.error("prepareParameters", e); + return false; + } + + return true; + } + + private static String biuldSetterName(String name) { + String setterName = "set"; + setterName += name.substring(0, 1).toUpperCase() + name.substring(1); + return setterName; + + } + + private static String debiuldGetterName(String getterName) { + if (getterName == null || getterName.length() <= 3) { + return null; + } + if (!getterName.substring(0, 3).equals("get")) { + return null; + } + + String name = getterName.substring(3, 4).toLowerCase() + getterName.substring(4); + return name; + } + + private static String execute(Object object) { + final String METHOD_EXECUTE = "execute"; + String viewId = null; + + Class clazz = object.getClass(); + try { + Method method = clazz.getMethod(METHOD_EXECUTE); + viewId = (String) method.invoke(object); + } catch (NoSuchMethodException | SecurityException | IllegalAccessException | IllegalArgumentException + | InvocationTargetException e) { + log.error("execute", e); + return viewId; + } + + return viewId; + } + + private static View biuldView(Object object) { + View view = new View(); + Map parameters = new HashMap<>(); + + Class clazz = object.getClass(); + Method[] methods; + try { + methods = clazz.getMethods(); + for (Method method : methods) { + String name = debiuldGetterName(method.getName()); + if (name == null) { + continue; + } + Object value = method.invoke(object); + parameters.put(name, value); + } + + view.setParameters(parameters); + } catch (SecurityException | IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { + log.error("biuldResult", e); + return null; + } + + return view; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java new file mode 100644 index 0000000000..0aa18d5f54 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java @@ -0,0 +1,26 @@ +package com.github.eulerlcs.jmr.litestruts.core; + +import java.util.Map; + +public class View { + private String jsp; + private Map parameters; + + public String getJsp() { + return jsp; + } + + public View setJsp(String jsp) { + this.jsp = jsp; + return this; + } + + public Map getParameters() { + return parameters; + } + + public View setParameters(Map parameters) { + this.parameters = parameters; + return this; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java new file mode 100644 index 0000000000..336f594241 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java @@ -0,0 +1,22 @@ +package com.github.eulerlcs.jmr.litestruts.degister; + +import java.util.HashMap; +import java.util.Map; + +import lombok.Getter; +import lombok.Setter; + +public class StrutsAction { + @Getter + @Setter + private String name; + @Getter + @Setter + private String clazz; + @Getter + private Map results = new HashMap<>(); + + public void addResult(StrutsActionResult result) { + results.put(result.getName(), result); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java new file mode 100644 index 0000000000..64247d4aba --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java @@ -0,0 +1,13 @@ +package com.github.eulerlcs.jmr.litestruts.degister; + +import lombok.Getter; +import lombok.Setter; + +public class StrutsActionResult { + @Getter + @Setter + private String name; + @Getter + @Setter + private String url; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java new file mode 100644 index 0000000000..567f4c7ef1 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java @@ -0,0 +1,30 @@ +package com.github.eulerlcs.jmr.litestruts.degister; + +import org.apache.commons.digester.Digester; +import org.apache.commons.digester.RuleSetBase; + +final class StrutsActionRulerSet extends RuleSetBase { + protected String prefix = null; + + public StrutsActionRulerSet() { + this(""); + } + + public StrutsActionRulerSet(String prefix) { + super(); + this.namespaceURI = null; + this.prefix = prefix; + } + + @Override + public void addRuleInstances(Digester digester) { + digester.addObjectCreate(prefix + "action", StrutsAction.class); + digester.addSetProperties(prefix + "action"); + digester.addSetProperties(prefix + "action", "class", "clazz"); + digester.addSetNext(prefix + "action", "addAction"); + digester.addObjectCreate(prefix + "action/result", StrutsActionResult.class); + digester.addSetProperties(prefix + "action/result"); + digester.addBeanPropertySetter(prefix + "action/result", "url"); + digester.addSetNext(prefix + "action/result", "addResult"); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java new file mode 100644 index 0000000000..b2005c9700 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java @@ -0,0 +1,15 @@ +package com.github.eulerlcs.jmr.litestruts.degister; + +import java.util.HashMap; +import java.util.Map; + +import lombok.Getter; + +public class StrutsConfig { + @Getter + private Map actionMap = new HashMap<>(); + + public void addAction(StrutsAction action) { + actionMap.put(action.getName(), action); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java new file mode 100644 index 0000000000..f466c8cb10 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java @@ -0,0 +1,13 @@ +package com.github.eulerlcs.jmr.litestruts.degister; + +import org.apache.commons.digester.Digester; + +public class StrutsDigester { + public static Digester newInstance() { + Digester d = new Digester(); + d.addObjectCreate("struts", StrutsConfig.class); + d.addSetProperties("struts"); + d.addRuleSet(new StrutsActionRulerSet("struts/")); + return d; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java new file mode 100644 index 0000000000..7242407f74 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java @@ -0,0 +1,266 @@ +/** + * 问题点: 没有全分支覆盖。只简单的测了关键或者关心的case + */ +package com.github.eulerlcs.jmr.algorithm; + +import static org.junit.Assert.assertArrayEquals; +import static org.junit.Assert.assertEquals; + +import org.junit.Test; + +public class ArrayUtilTest { + + @Test + public void reverseArray_null() { + int[] actuals = null; + int[] expecteds = null; + + ArrayUtil.reverseArray(actuals); + + assertArrayEquals(actuals, expecteds); + } + + @Test + public void reverseArray_0() { + int[] actuals = {}; + int[] expecteds = {}; + + ArrayUtil.reverseArray(actuals); + + assertArrayEquals(actuals, expecteds); + } + + @Test + public void reverseArray_1() { + int[] actuals = { 2 }; + int[] expecteds = { 2 }; + + ArrayUtil.reverseArray(actuals); + + assertArrayEquals(actuals, expecteds); + } + + @Test + public void reverseArray_2() { + int[] actuals = { 7, 9 }; + int[] expecteds = { 9, 7 }; + + ArrayUtil.reverseArray(actuals); + + assertArrayEquals(actuals, expecteds); + } + + @Test + public void reverseArray_4() { + int[] actuals = { 7, 9, 30, 3 }; + int[] expecteds = { 3, 30, 9, 7 }; + + ArrayUtil.reverseArray(actuals); + + assertArrayEquals(actuals, expecteds); + } + + @Test + public void reverseArray_5() { + int[] actuals = { 7, 9, 30, 3, 4 }; + int[] expecteds = { 4, 3, 30, 9, 7 }; + + ArrayUtil.reverseArray(actuals); + + assertArrayEquals(actuals, expecteds); + } + + @Test + public void removeZero_null() { + int oldArr[] = null; + int[] expecteds = {}; + + int[] newArr = ArrayUtil.removeZero(oldArr); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void removeZero_0() { + int oldArr[] = {}; + int[] expecteds = {}; + + int[] newArr = ArrayUtil.removeZero(oldArr); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void removeZero_1() { + int oldArr[] = { 0 }; + int[] expecteds = {}; + + int[] newArr = ArrayUtil.removeZero(oldArr); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void removeZero_2() { + int oldArr[] = { 3, 5 }; + int[] expecteds = { 3, 5 }; + + int[] newArr = ArrayUtil.removeZero(oldArr); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void removeZero_3() { + int oldArr[] = { 1, 3, 4, 5, 0, 0, 6, 6, 0, 5, 4, 7, 6, 7, 0, 5 }; + int[] expecteds = { 1, 3, 4, 5, 6, 6, 5, 4, 7, 6, 7, 5 }; + + int[] newArr = ArrayUtil.removeZero(oldArr); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void merge_1() { + int[] a1 = { 3, 5, 7, 8 }; + int[] a2 = { 4, 5, 6, 7 }; + int[] expecteds = { 3, 4, 5, 6, 7, 8 }; + + int[] newArr = ArrayUtil.merge(a1, a2); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void merge_2() { + int[] a1 = { 4, 5, 6, 7 }; + int[] a2 = { 3, 5, 7, 8 }; + int[] expecteds = { 3, 4, 5, 6, 7, 8 }; + + int[] newArr = ArrayUtil.merge(a1, a2); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void grow_1() { + int[] oldArray = { 2, 3, 6 }; + int increaseCapacity = 3; + int[] expecteds = { 2, 3, 6, 0, 0, 0 }; + + int[] newArr = ArrayUtil.grow(oldArray, increaseCapacity); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void fibonacci_1() { + int max = 1; + int[] expecteds = {}; + + int[] newArr = ArrayUtil.fibonacci(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void fibonacci_2() { + int max = 2; + int[] expecteds = { 1, 1 }; + + int[] newArr = ArrayUtil.fibonacci(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void fibonacci_15() { + int max = 15; + int[] expecteds = { 1, 1, 2, 3, 5, 8, 13 }; + + int[] newArr = ArrayUtil.fibonacci(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPrimes_1() { + int max = 1; + int[] expecteds = {}; + + int[] newArr = ArrayUtil.getPrimes(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPrimes_2() { + int max = 2; + int[] expecteds = {}; + + int[] newArr = ArrayUtil.getPrimes(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPrimes_3() { + int max = 3; + int[] expecteds = { 2 }; + + int[] newArr = ArrayUtil.getPrimes(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPrimes_4() { + int max = 4; + int[] expecteds = { 2, 3 }; + + int[] newArr = ArrayUtil.getPrimes(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPrimes_23() { + int max = 23; + int[] expecteds = { 2, 3, 5, 7, 11, 13, 17, 19 }; + + int[] newArr = ArrayUtil.getPrimes(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPrimes_24() { + int max = 24; + int[] expecteds = { 2, 3, 5, 7, 11, 13, 17, 19, 23 }; + + int[] newArr = ArrayUtil.getPrimes(max); + + assertArrayEquals(newArr, expecteds); + } + + @Test + public void getPerfectNumbers_max() { + long max = Long.MAX_VALUE; + max = 10000; + long[] expecteds = { 6, 28, 496, 8128, 33550336, 8589869056L, 137438691328L, 2305843008139952128L }; + + long[] newArr = ArrayUtil.getPerfectNumbers(max); + + assertEquals(newArr[3], expecteds[3]); + } + + @Test + public void join_0() { + int[] array = { 3, 8, 9 }; + String separator = "-"; + String expected = "3-8-9"; + + String actual = ArrayUtil.join(array, separator); + assertEquals(expected, actual); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java new file mode 100644 index 0000000000..b2fa989915 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java @@ -0,0 +1,38 @@ +package com.github.eulerlcs.jmr.litestruts.core; + +import java.util.HashMap; +import java.util.Map; + +import org.junit.Assert; +import org.junit.Test; + +public class StrutsTest { + + @Test + public void testLoginActionSuccess() { + + String actionName = "login"; + + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "1234"); + + View view = Struts.runAction(actionName, params); + + Assert.assertEquals("/jsp/homepage.jsp", view.getJsp()); + Assert.assertEquals("login successful", view.getParameters().get("message")); + } + + @Test + public void testLoginActionFailed() { + String actionName = "login"; + Map params = new HashMap(); + params.put("name", "test"); + params.put("password", "123456"); // 密码和预设的不一致 + + View view = Struts.runAction(actionName, params); + + Assert.assertEquals("/jsp/showLogin.jsp", view.getJsp()); + Assert.assertEquals("login failed,please check your user/pwd", view.getParameters().get("message")); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/data/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-63-download/data/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml b/students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml new file mode 100644 index 0000000000..8656e91371 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml @@ -0,0 +1,39 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-63-download + eulerlcs master java road - download file by multiple thread + + + + commons-digester + commons-digester + + + org.projectlombok + lombok + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + com.github.stefanbirkner + system-rules + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java new file mode 100644 index 0000000000..78d537e842 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java @@ -0,0 +1,8 @@ +package com.github.eulerlcs.jmr.algorithm; + +public interface Iterator { + public boolean hasNext(); + + public Object next(); + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java new file mode 100644 index 0000000000..7f42cc502b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java @@ -0,0 +1,126 @@ +package com.github.eulerlcs.jmr.algorithm; + +public class LinkedList implements List { + + private Node head; + + public void add(Object o) { + + } + + public void add(int index, Object o) { + + } + + public Object get(int index) { + return null; + } + + public Object remove(int index) { + return null; + } + + public int size() { + return -1; + } + + public void addFirst(Object o) { + + } + + public void addLast(Object o) { + + } + + public Object removeFirst() { + return null; + } + + public Object removeLast() { + return null; + } + + public Iterator iterator() { + return null; + } + + private static class Node { + Object data; + Node next; + + } + + /** + * 把该链表逆置 例如链表为 3->7->10 , 逆置后变为 10->7->3 + */ + public void reverse() { + + } + + /** + * 删除一个单链表的前半部分 例如:list = 2->5->7->8 , 删除以后的值为 7->8 如果list = 2->5->7->8->10 + * ,删除以后的值为7,8,10 + * + */ + public void removeFirstHalf() { + + } + + /** + * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 + * + * @param i + * @param length + */ + public void remove(int i, int length) { + + } + + /** + * 假定当前链表和list均包含已升序排列的整数 从当前链表中取出那些list所指定的元素 例如当前链表 = + * 11->101->201->301->401->501->601->701 listB = 1->3->4->6 + * 返回的结果应该是[101,301,401,601] + * + * @param list + */ + public static int[] getElements(LinkedList list) { + return null; + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 从当前链表中中删除在list中出现的元素 + * + * @param list + */ + + public void subtract(LinkedList list) { + + } + + /** + * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) + */ + public void removeDuplicateValues() { + + } + + /** + * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) + * + * @param min + * @param max + */ + public void removeRange(int min, int max) { + + } + + /** + * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) + * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 + * + * @param list + */ + public LinkedList intersection(LinkedList list) { + return null; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java new file mode 100644 index 0000000000..d693a0895d --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java @@ -0,0 +1,13 @@ +package com.github.eulerlcs.jmr.algorithm; + +public interface List { + public void add(Object o); + + public void add(int index, Object o); + + public Object get(int index); + + public Object remove(int index); + + public int size(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java new file mode 100644 index 0000000000..30042c8db0 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java @@ -0,0 +1,28 @@ +package com.github.eulerlcs.jmr.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/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java new file mode 100644 index 0000000000..2ba4d3978c --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java @@ -0,0 +1,5 @@ +package com.github.eulerlcs.jmr.download.api; + +public class ConnectionException extends Exception { + private static final long serialVersionUID = 1L; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java new file mode 100644 index 0000000000..e2faed7df6 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java @@ -0,0 +1,11 @@ +package com.github.eulerlcs.jmr.download.api; + +public interface ConnectionManager { + /** + * 给定一个url , 打开一个连接 + * + * @param url + * @return + */ + public Connection open(String url) throws ConnectionException; +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java new file mode 100644 index 0000000000..80400ab21b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java @@ -0,0 +1,5 @@ +package com.github.eulerlcs.jmr.download.api; + +public interface DownloadListener { + public void notifyFinished(); +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java new file mode 100644 index 0000000000..179a037a92 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java @@ -0,0 +1,20 @@ +package com.github.eulerlcs.jmr.download.core; + +import com.github.eulerlcs.jmr.download.api.Connection; + +public class DownloadThread extends Thread { + Connection conn; + int startPos; + int endPos; + + public DownloadThread(Connection conn, int startPos, int endPos) { + this.conn = conn; + this.startPos = startPos; + this.endPos = endPos; + } + + @Override + public void run() { + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java new file mode 100644 index 0000000000..fa3c193960 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java @@ -0,0 +1,64 @@ +package com.github.eulerlcs.jmr.download.core; + +import com.github.eulerlcs.jmr.download.api.Connection; +import com.github.eulerlcs.jmr.download.api.ConnectionException; +import com.github.eulerlcs.jmr.download.api.ConnectionManager; +import com.github.eulerlcs.jmr.download.api.DownloadListener; + +public class FileDownloader { + + String url; + + DownloadListener listener; + + ConnectionManager cm; + + 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 { + conn = cm.open(this.url); + + int length = conn.getContentLength(); + + new DownloadThread(conn, 0, length - 1).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/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java new file mode 100644 index 0000000000..72b679702b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java @@ -0,0 +1,25 @@ +package com.github.eulerlcs.jmr.download.impl; + +import java.io.IOException; + +import com.github.eulerlcs.jmr.download.api.Connection; + +public class ConnectionImpl implements Connection { + + @Override + public byte[] read(int startPos, int endPos) throws IOException { + + return null; + } + + @Override + public int getContentLength() { + + return 0; + } + + @Override + public void close() { + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java new file mode 100644 index 0000000000..b24ae09984 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java @@ -0,0 +1,14 @@ +package com.github.eulerlcs.jmr.download.impl; + +import com.github.eulerlcs.jmr.download.api.Connection; +import com.github.eulerlcs.jmr.download.api.ConnectionException; +import com.github.eulerlcs.jmr.download.api.ConnectionManager; + +public class ConnectionManagerImpl implements ConnectionManager { + + @Override + public Connection open(String url) throws ConnectionException { + + return null; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java new file mode 100644 index 0000000000..531601606e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java @@ -0,0 +1,53 @@ +package com.github.eulerlcs.jmr.download.core; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +import com.github.eulerlcs.jmr.download.api.ConnectionManager; +import com.github.eulerlcs.jmr.download.api.DownloadListener; +import com.github.eulerlcs.jmr.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://localhost:8080/test.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/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/data/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/data/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml new file mode 100644 index 0000000000..76b2d2e4be --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml @@ -0,0 +1,43 @@ + + 4.0.0 + + com.github.eulerlcs + jmr-02-parent + 0.0.1-SNAPSHOT + ../jmr-02-parent/pom.xml + + jmr-64-minijvm + eulerlcs master java road - mini jvm + + + + com.github.eulerlcs + jmr-61-collection + + + commons-digester + commons-digester + + + org.projectlombok + lombok + + + org.slf4j + slf4j-api + + + org.slf4j + slf4j-log4j12 + + + junit + junit + + + com.github.stefanbirkner + system-rules + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java new file mode 100644 index 0000000000..25268be2dc --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java @@ -0,0 +1,110 @@ +package com.github.eulerlcs.jmr.algorithm; + +/** + * 用双向链表实现LRU算法 + * + * @author liuxin, eulerlcs + */ +public class LRUPageFrame { + private static class Node { + Node prev; + Node next; + int pageNum; + } + + private int capacity; + private int length = 0; + private Node first;// 链表头 + private Node last;// 链表尾 + + public LRUPageFrame(int capacity) { + this.capacity = capacity; + } + + /** + * 获取缓存中对象 + * + * @param pageNum + */ + public void access(int pageNum) { + Node node = findNode(pageNum); + + if (node != null) { + moveToFirst(node); + } else { + node = new Node(); + node.pageNum = pageNum; + addToFirst(node); + } + } + + private Node findNode(int pageNum) { + Node node = first; + + while (node != null) { + if (node.pageNum == pageNum) { + return node; + } else { + node = node.next; + } + } + + return null; + } + + private void moveToFirst(Node node) { + if (node == first) { + return; + } else if (node == last) { + last = node.prev; + } + + if (node.prev != null) { + node.prev.next = node.next; + } + if (node.next != null) { + node.next.prev = node.prev; + } + + first.prev = node; + node.prev = null; + node.next = first; + + first = node; + } + + private void addToFirst(Node node) { + if (first == null) { + first = node; + last = first; + } else { + first.prev = node; + node.next = first; + first = node; + } + + length++; + if (length > capacity) { + last.prev.next = null; + last = last.prev; + + length = capacity; + } + } + + @Override + public String toString() { + StringBuilder buffer = new StringBuilder(); + Node node = first; + while (node != null) { + buffer.append(node.pageNum); + + node = node.next; + if (node != null) { + buffer.append(","); + } + } + + return buffer.toString(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java new file mode 100644 index 0000000000..6f2c895554 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java @@ -0,0 +1,24 @@ +package com.github.eulerlcs.jmr.algorithm; + +public class Stack { + private ArrayList elementData = new ArrayList(); + + public void push(Object o) { + } + + public Object pop() { + return null; + } + + public Object peek() { + return null; + } + + public boolean isEmpty() { + return false; + } + + public int size() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java new file mode 100644 index 0000000000..1c0a56be56 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java @@ -0,0 +1,43 @@ +package com.github.eulerlcs.jmr.algorithm; + +public class StackUtil { + /** + * 假设栈中的元素是Integer, 从栈顶到栈底是 : 5,4,3,2,1 调用该方法后, 元素次序变为: 1,2,3,4,5 + * 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 + */ + public static void reverse(Stack s) { + + } + + /** + * 删除栈中的某个元素 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 + * + * @param o + */ + public static void remove(Stack s, Object o) { + + } + + /** + * 从栈顶取得len个元素, 原来的栈中元素保持不变 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, + * 可以使用另外一个栈来辅助 + * + * @param len + * @return + */ + public static Object[] getTop(Stack s, int len) { + return null; + } + + /** + * 字符串s 可能包含这些字符: ( ) [ ] { }, a,b,c... x,yz 使用堆栈检查字符串s中的括号是不是成对出现的。 例如s = + * "([e{d}f])" , 则该字符串中的括号是成对出现, 该方法返回true 如果 s = "([b{x]y})", + * 则该字符串中的括号不是成对出现的, 该方法返回false; + * + * @param s + * @return + */ + public static boolean isValidPairs(String s) { + return false; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java new file mode 100644 index 0000000000..a74ee2eaaf --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java @@ -0,0 +1,19 @@ +package com.github.eulerlcs.jmr.jvm.attr; + +public abstract class AttributeInfo { + public static final String CODE = "Code"; + public static final String CONST_VALUE = "ConstantValue"; + public static final String EXCEPTIONS = "Exceptions"; + public static final String LINE_NUM_TABLE = "LineNumberTable"; + public static final String LOCAL_VAR_TABLE = "LocalVariableTable"; + public static final String STACK_MAP_TABLE = "StackMapTable"; + int attrNameIndex; + int attrLen; + + public AttributeInfo(int attrNameIndex, int attrLen) { + + this.attrNameIndex = attrNameIndex; + this.attrLen = attrLen; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java new file mode 100644 index 0000000000..ee99466cad --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java @@ -0,0 +1,52 @@ +package com.github.eulerlcs.jmr.jvm.attr; + +import com.github.eulerlcs.jmr.jvm.clz.ClassFile; +import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; + +public class CodeAttr extends AttributeInfo { + private int maxStack; + private int maxLocals; + private int codeLen; + private String code; + + public String getCode() { + return code; + } + + // private ByteCodeCommand[] cmds ; + // public ByteCodeCommand[] getCmds() { + // return cmds; + // } + private LineNumberTable lineNumTable; + private LocalVariableTable localVarTable; + private StackMapTable stackMapTable; + + public CodeAttr(int attrNameIndex, int attrLen, int maxStack, int maxLocals, int codeLen, + String code /* ByteCodeCommand[] cmds */) { + super(attrNameIndex, attrLen); + this.maxStack = maxStack; + this.maxLocals = maxLocals; + this.codeLen = codeLen; + this.code = code; + // this.cmds = cmds; + } + + public void setLineNumberTable(LineNumberTable t) { + this.lineNumTable = t; + } + + public void setLocalVariableTable(LocalVariableTable t) { + this.localVarTable = t; + } + + public static CodeAttr parse(ClassFile clzFile, ByteCodeIterator iter) { + + return null; + } + + private void setStackMapTable(StackMapTable t) { + this.stackMapTable = t; + + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java new file mode 100644 index 0000000000..3c3ee7e256 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java @@ -0,0 +1,46 @@ +package com.github.eulerlcs.jmr.jvm.attr; + +import java.util.ArrayList; +import java.util.List; + +import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; + +public class LineNumberTable extends AttributeInfo { + List items = new ArrayList(); + + private static class LineNumberItem { + int startPC; + int lineNum; + + public int getStartPC() { + return startPC; + } + + public void setStartPC(int startPC) { + this.startPC = startPC; + } + + public int getLineNum() { + return lineNum; + } + + public void setLineNum(int lineNum) { + this.lineNum = lineNum; + } + } + + public void addLineNumberItem(LineNumberItem item) { + this.items.add(item); + } + + public LineNumberTable(int attrNameIndex, int attrLen) { + super(attrNameIndex, attrLen); + + } + + public static LineNumberTable parse(ByteCodeIterator iter) { + + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java new file mode 100644 index 0000000000..19483e48d5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java @@ -0,0 +1,49 @@ +package com.github.eulerlcs.jmr.jvm.attr; + +public class LocalVariableItem { + private int startPC; + private int length; + private int nameIndex; + private int descIndex; + private int index; + + public int getStartPC() { + return startPC; + } + + public void setStartPC(int startPC) { + this.startPC = startPC; + } + + public int getLength() { + return length; + } + + public void setLength(int length) { + this.length = length; + } + + public int getNameIndex() { + return nameIndex; + } + + public void setNameIndex(int nameIndex) { + this.nameIndex = nameIndex; + } + + public int getDescIndex() { + return descIndex; + } + + public void setDescIndex(int descIndex) { + this.descIndex = descIndex; + } + + public int getIndex() { + return index; + } + + public void setIndex(int index) { + this.index = index; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java new file mode 100644 index 0000000000..a847d9222e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java @@ -0,0 +1,25 @@ +package com.github.eulerlcs.jmr.jvm.attr; + +import java.util.ArrayList; +import java.util.List; + +import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; + +public class LocalVariableTable extends AttributeInfo { + + List items = new ArrayList(); + + public LocalVariableTable(int attrNameIndex, int attrLen) { + super(attrNameIndex, attrLen); + } + + public static LocalVariableTable parse(ByteCodeIterator iter) { + + return null; + } + + private void addLocalVariableItem(LocalVariableItem item) { + this.items.add(item); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java new file mode 100644 index 0000000000..e281ce8616 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java @@ -0,0 +1,29 @@ +package com.github.eulerlcs.jmr.jvm.attr; + +import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; + +public class StackMapTable extends AttributeInfo { + + private String originalCode; + + public StackMapTable(int attrNameIndex, int attrLen) { + super(attrNameIndex, attrLen); + } + + public static StackMapTable parse(ByteCodeIterator iter) { + int index = iter.nextU2ToInt(); + int len = iter.nextU4ToInt(); + StackMapTable t = new StackMapTable(index, len); + + // 后面的StackMapTable太过复杂, 不再处理, 只把原始的代码读进来保存 + String code = iter.nextUxToHexString(len); + t.setOriginalCode(code); + + return t; + } + + private void setOriginalCode(String code) { + this.originalCode = code; + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java new file mode 100644 index 0000000000..2e912067fd --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java @@ -0,0 +1,26 @@ +package com.github.eulerlcs.jmr.jvm.clz; + +public class AccessFlag { + private int flagValue; + + public AccessFlag(int value) { + this.flagValue = value; + } + + public int getFlagValue() { + return flagValue; + } + + public void setFlagValue(int flag) { + this.flagValue = flag; + } + + public boolean isPublicClass() { + return (this.flagValue & 0x0001) != 0; + } + + public boolean isFinalClass() { + return (this.flagValue & 0x0010) != 0; + } + +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java new file mode 100644 index 0000000000..7b84ca588e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java @@ -0,0 +1,100 @@ +package com.github.eulerlcs.jmr.jvm.clz; + +import java.util.ArrayList; +import java.util.List; + +import com.github.eulerlcs.jmr.jvm.constant.ClassInfo; +import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; +import com.github.eulerlcs.jmr.jvm.field.Field; +import com.github.eulerlcs.jmr.jvm.method.Method; + +public class ClassFile { + + private int minorVersion; + private int majorVersion; + + private AccessFlag accessFlag; + private ClassIndex clzIndex; + private ConstantPool pool; + private List fields = new ArrayList(); + private List methods = new ArrayList(); + + public ClassIndex getClzIndex() { + return clzIndex; + } + + public AccessFlag getAccessFlag() { + return accessFlag; + } + + public void setAccessFlag(AccessFlag accessFlag) { + this.accessFlag = accessFlag; + } + + public ConstantPool getConstantPool() { + return pool; + } + + public int getMinorVersion() { + return minorVersion; + } + + public void setMinorVersion(int minorVersion) { + this.minorVersion = minorVersion; + } + + public int getMajorVersion() { + return majorVersion; + } + + public void setMajorVersion(int majorVersion) { + this.majorVersion = majorVersion; + } + + public void setConstPool(ConstantPool pool) { + this.pool = pool; + + } + + public void setClassIndex(ClassIndex clzIndex) { + this.clzIndex = clzIndex; + } + + public void addField(Field f) { + this.fields.add(f); + } + + public List getFields() { + return this.fields; + } + + public void addMethod(Method m) { + this.methods.add(m); + } + + public List getMethods() { + return methods; + } + + public void print() { + + if (this.accessFlag.isPublicClass()) { + System.out.println("Access flag : public "); + } + System.out.println("Class Name:" + getClassName()); + + System.out.println("Super Class Name:" + getSuperClassName()); + + } + + private String getClassName() { + int thisClassIndex = this.clzIndex.getThisClassIndex(); + ClassInfo thisClass = (ClassInfo) this.getConstantPool().getConstantInfo(thisClassIndex); + return thisClass.getClassName(); + } + + private String getSuperClassName() { + ClassInfo superClass = (ClassInfo) this.getConstantPool().getConstantInfo(this.clzIndex.getSuperClassIndex()); + return superClass.getClassName(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java new file mode 100644 index 0000000000..819b538406 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java @@ -0,0 +1,22 @@ +package com.github.eulerlcs.jmr.jvm.clz; + +public class ClassIndex { + private int thisClassIndex; + private int superClassIndex; + + public int getThisClassIndex() { + return thisClassIndex; + } + + public void setThisClassIndex(int thisClassIndex) { + this.thisClassIndex = thisClassIndex; + } + + public int getSuperClassIndex() { + return superClassIndex; + } + + public void setSuperClassIndex(int superClassIndex) { + this.superClassIndex = superClassIndex; + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java new file mode 100644 index 0000000000..d2bc776faf --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java @@ -0,0 +1,29 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class ClassInfo extends ConstantInfo { + private int type = ConstantInfo.CLASS_INFO; + private int utf8Index; + + public ClassInfo(ConstantPool pool) { + super(pool); + } + + public int getUtf8Index() { + return utf8Index; + } + + public void setUtf8Index(int utf8Index) { + this.utf8Index = utf8Index; + } + + @Override + public int getType() { + return type; + } + + public String getClassName() { + int index = getUtf8Index(); + UTF8Info utf8Info = (UTF8Info) constantPool.getConstantInfo(index); + return utf8Info.getValue(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java new file mode 100644 index 0000000000..c283fb56a5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java @@ -0,0 +1,29 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public abstract class ConstantInfo { + public static final int UTF8_INFO = 1; + public static final int FLOAT_INFO = 4; + public static final int CLASS_INFO = 7; + public static final int STRING_INFO = 8; + public static final int FIELD_INFO = 9; + public static final int METHOD_INFO = 10; + public static final int NAME_AND_TYPE_INFO = 12; + protected ConstantPool constantPool; + + public ConstantInfo() { + } + + public ConstantInfo(ConstantPool pool) { + this.constantPool = pool; + } + + public abstract int getType(); + + public ConstantPool getConstantPool() { + return constantPool; + } + + public ConstantInfo getConstantInfo(int index) { + return this.constantPool.getConstantInfo(index); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java new file mode 100644 index 0000000000..ff1af9d094 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java @@ -0,0 +1,28 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +import java.util.ArrayList; +import java.util.List; + +public class ConstantPool { + + private List constantInfos = new ArrayList(); + + public ConstantPool() { + } + + public void addConstantInfo(ConstantInfo info) { + this.constantInfos.add(info); + } + + public ConstantInfo getConstantInfo(int index) { + return this.constantInfos.get(index); + } + + public String getUTF8String(int index) { + return ((UTF8Info) this.constantInfos.get(index)).getValue(); + } + + public Object getSize() { + return this.constantInfos.size() - 1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java new file mode 100644 index 0000000000..e5220ac5c4 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java @@ -0,0 +1,54 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class FieldRefInfo extends ConstantInfo { + private int type = ConstantInfo.FIELD_INFO; + private int classInfoIndex; + private int nameAndTypeIndex; + + public FieldRefInfo(ConstantPool pool) { + super(pool); + } + + @Override + public int getType() { + return type; + } + + public int getClassInfoIndex() { + return classInfoIndex; + } + + public void setClassInfoIndex(int classInfoIndex) { + this.classInfoIndex = classInfoIndex; + } + + public int getNameAndTypeIndex() { + return nameAndTypeIndex; + } + + public void setNameAndTypeIndex(int nameAndTypeIndex) { + this.nameAndTypeIndex = nameAndTypeIndex; + } + + @Override + public String toString() { + NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); + return getClassName() + " : " + typeInfo.getName() + ":" + typeInfo.getTypeInfo() + "]"; + } + + public String getClassName() { + ClassInfo classInfo = (ClassInfo) this.getConstantInfo(this.getClassInfoIndex()); + UTF8Info utf8Info = (UTF8Info) this.getConstantInfo(classInfo.getUtf8Index()); + return utf8Info.getValue(); + } + + public String getFieldName() { + NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getName(); + } + + public String getFieldType() { + NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getTypeInfo(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java new file mode 100644 index 0000000000..4dc4ae3d1b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java @@ -0,0 +1,56 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class MethodRefInfo extends ConstantInfo { + private int type = ConstantInfo.METHOD_INFO; + + private int classInfoIndex; + private int nameAndTypeIndex; + + public MethodRefInfo(ConstantPool pool) { + super(pool); + } + + @Override + public int getType() { + return type; + } + + public int getClassInfoIndex() { + return classInfoIndex; + } + + public void setClassInfoIndex(int classInfoIndex) { + this.classInfoIndex = classInfoIndex; + } + + public int getNameAndTypeIndex() { + return nameAndTypeIndex; + } + + public void setNameAndTypeIndex(int nameAndTypeIndex) { + this.nameAndTypeIndex = nameAndTypeIndex; + } + + @Override + public String toString() { + return getClassName() + " : " + this.getMethodName() + " : " + this.getParamAndReturnType(); + } + + public String getClassName() { + ConstantPool pool = this.getConstantPool(); + ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(this.getClassInfoIndex()); + return clzInfo.getClassName(); + } + + public String getMethodName() { + ConstantPool pool = this.getConstantPool(); + NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getName(); + } + + public String getParamAndReturnType() { + ConstantPool pool = this.getConstantPool(); + NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); + return typeInfo.getTypeInfo(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java new file mode 100644 index 0000000000..6674006efd --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java @@ -0,0 +1,50 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class NameAndTypeInfo extends ConstantInfo { + public int type = ConstantInfo.NAME_AND_TYPE_INFO; + + private int index1; + private int index2; + + public NameAndTypeInfo(ConstantPool pool) { + super(pool); + } + + public int getIndex1() { + return index1; + } + + public void setIndex1(int index1) { + this.index1 = index1; + } + + public int getIndex2() { + return index2; + } + + public void setIndex2(int index2) { + this.index2 = index2; + } + + @Override + public int getType() { + return type; + } + + public String getName() { + ConstantPool pool = this.getConstantPool(); + UTF8Info utf8Info1 = (UTF8Info) pool.getConstantInfo(index1); + return utf8Info1.getValue(); + } + + public String getTypeInfo() { + ConstantPool pool = this.getConstantPool(); + UTF8Info utf8Info2 = (UTF8Info) pool.getConstantInfo(index2); + return utf8Info2.getValue(); + } + + @Override + public String toString() { + return "(" + getName() + "," + getTypeInfo() + ")"; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java new file mode 100644 index 0000000000..c4267ca5fc --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java @@ -0,0 +1,11 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class NullConstantInfo extends ConstantInfo { + public NullConstantInfo() { + } + + @Override + public int getType() { + return -1; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java new file mode 100644 index 0000000000..6f3575a5e0 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java @@ -0,0 +1,28 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class StringInfo extends ConstantInfo { + private int type = ConstantInfo.STRING_INFO; + private int index; + + public StringInfo(ConstantPool pool) { + super(pool); + } + + @Override + public int getType() { + return type; + } + + public int getIndex() { + return index; + } + + public void setIndex(int index) { + this.index = index; + } + + @Override + public String toString() { + return this.getConstantPool().getUTF8String(index); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java new file mode 100644 index 0000000000..2435cc554e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java @@ -0,0 +1,37 @@ +package com.github.eulerlcs.jmr.jvm.constant; + +public class UTF8Info extends ConstantInfo { + private int type = ConstantInfo.UTF8_INFO; + private int length; + private String value; + + public UTF8Info(ConstantPool pool) { + super(pool); + } + + public int getLength() { + return length; + } + + public void setLength(int length) { + this.length = length; + } + + @Override + public int getType() { + return type; + } + + @Override + public String toString() { + return "UTF8Info [type=" + type + ", length=" + length + ", value=" + value + ")]"; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java new file mode 100644 index 0000000000..d0f54964ac --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java @@ -0,0 +1,26 @@ +package com.github.eulerlcs.jmr.jvm.field; + +import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; +import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; + +public class Field { + private int accessFlag; + private int nameIndex; + private int descriptorIndex; + + private ConstantPool pool; + + public Field(int accessFlag, int nameIndex, int descriptorIndex, ConstantPool pool) { + + this.accessFlag = accessFlag; + this.nameIndex = nameIndex; + this.descriptorIndex = descriptorIndex; + this.pool = pool; + } + + public static Field parse(ConstantPool pool, ByteCodeIterator iter) { + + return null; + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java new file mode 100644 index 0000000000..095a81dece --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java @@ -0,0 +1,55 @@ +package com.github.eulerlcs.jmr.jvm.loader; + +import java.util.Arrays; + +import com.github.eulerlcs.jmr.jvm.util.Util; + +public class ByteCodeIterator { + byte[] codes; + int pos = 0; + + ByteCodeIterator(byte[] codes) { + this.codes = codes; + } + + public byte[] getBytes(int len) { + if (pos + len >= codes.length) { + throw new ArrayIndexOutOfBoundsException(); + } + + byte[] data = Arrays.copyOfRange(codes, pos, pos + len); + pos += len; + return data; + } + + public int nextU1toInt() { + + return Util.byteToInt(new byte[] { codes[pos++] }); + } + + public int nextU2ToInt() { + return Util.byteToInt(new byte[] { codes[pos++], codes[pos++] }); + } + + public int nextU4ToInt() { + return Util.byteToInt(new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] }); + } + + public String nextU4ToHexString() { + return Util.byteToHexString((new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] })); + } + + public String nextUxToHexString(int len) { + byte[] tmp = new byte[len]; + + for (int i = 0; i < len; i++) { + tmp[i] = codes[pos++]; + } + return Util.byteToHexString(tmp).toLowerCase(); + + } + + public void back(int n) { + this.pos -= n; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java new file mode 100644 index 0000000000..49018cb0a7 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java @@ -0,0 +1,74 @@ +package com.github.eulerlcs.jmr.jvm.loader; + +import java.io.DataInputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.github.eulerlcs.jmr.jvm.clz.ClassFile; + +public class ClassFileLoader { + private final static Logger log = LoggerFactory.getLogger(ClassFileLoader.class); + + private List clzPaths = new ArrayList(); + + public byte[] readBinaryCode(String className) { + File file = findClassFile(className); + if (file == null) { + return new byte[0]; + } + + byte[] ret = null; + byte[] bytes = new byte[(int) file.length()]; + try (DataInputStream dis = new DataInputStream(new FileInputStream(file))) { + dis.readFully(bytes); + ret = bytes; + } catch (IOException e) { + log.error("ClassFileLoader read error!", e); + } + + return ret; + } + + private File findClassFile(String className) { + String sub = className.replace(".", File.separator) + ".class"; + for (String clzPath : clzPaths) { + File file = new File(clzPath, sub); + if (file.exists()) { + return file; + } + } + + return null; + } + + public void addClassPath(String path) { + clzPaths.add(path); + } + + public String getClassPath() { + if (clzPaths.size() == 0) { + return ""; + } + + StringBuilder sb = new StringBuilder(); + for (String clzPath : clzPaths) { + sb.append(";"); + sb.append(clzPath); + } + + String cat = sb.toString(); + return cat.length() > 0 ? cat.substring(1) : ""; + } + + public ClassFile loadClass(String className) { + byte[] codes = this.readBinaryCode(className); + ClassFileParser parser = new ClassFileParser(); + return parser.parse(codes); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java new file mode 100644 index 0000000000..394c35beb9 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java @@ -0,0 +1,146 @@ +package com.github.eulerlcs.jmr.jvm.loader; + +import java.io.UnsupportedEncodingException; + +import com.github.eulerlcs.jmr.jvm.clz.AccessFlag; +import com.github.eulerlcs.jmr.jvm.clz.ClassFile; +import com.github.eulerlcs.jmr.jvm.clz.ClassIndex; +import com.github.eulerlcs.jmr.jvm.constant.ClassInfo; +import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; +import com.github.eulerlcs.jmr.jvm.constant.FieldRefInfo; +import com.github.eulerlcs.jmr.jvm.constant.MethodRefInfo; +import com.github.eulerlcs.jmr.jvm.constant.NameAndTypeInfo; +import com.github.eulerlcs.jmr.jvm.constant.NullConstantInfo; +import com.github.eulerlcs.jmr.jvm.constant.StringInfo; +import com.github.eulerlcs.jmr.jvm.constant.UTF8Info; + +public class ClassFileParser { + + public ClassFile parse(byte[] codes) { + + ClassFile clzFile = new ClassFile(); + + ByteCodeIterator iter = new ByteCodeIterator(codes); + + String magicNumber = iter.nextU4ToHexString(); + + if (!"cafebabe".equals(magicNumber)) { + return null; + } + + clzFile.setMinorVersion(iter.nextU2ToInt()); + clzFile.setMajorVersion(iter.nextU2ToInt()); + + ConstantPool pool = parseConstantPool(iter); + clzFile.setConstPool(pool); + + AccessFlag flag = parseAccessFlag(iter); + clzFile.setAccessFlag(flag); + + ClassIndex clzIndex = parseClassInfex(iter); + clzFile.setClassIndex(clzIndex); + + parseInterfaces(iter); + + return clzFile; + } + + private AccessFlag parseAccessFlag(ByteCodeIterator iter) { + + AccessFlag flag = new AccessFlag(iter.nextU2ToInt()); + // System.out.println("Is public class: " + flag.isPublicClass()); + // System.out.println("Is final class : " + flag.isFinalClass()); + + return flag; + } + + private ClassIndex parseClassInfex(ByteCodeIterator iter) { + + int thisClassIndex = iter.nextU2ToInt(); + int superClassIndex = iter.nextU2ToInt(); + + ClassIndex clzIndex = new ClassIndex(); + + clzIndex.setThisClassIndex(thisClassIndex); + clzIndex.setSuperClassIndex(superClassIndex); + + return clzIndex; + + } + + private ConstantPool parseConstantPool(ByteCodeIterator iter) { + + int constPoolCount = iter.nextU2ToInt(); + + System.out.println("Constant Pool Count :" + constPoolCount); + + ConstantPool pool = new ConstantPool(); + + pool.addConstantInfo(new NullConstantInfo()); + + for (int i = 1; i <= constPoolCount - 1; i++) { + + int tag = iter.nextU1toInt(); + + if (tag == 7) { + // Class Info + int utf8Index = iter.nextU2ToInt(); + ClassInfo clzInfo = new ClassInfo(pool); + clzInfo.setUtf8Index(utf8Index); + + pool.addConstantInfo(clzInfo); + } else if (tag == 1) { + // UTF-8 String + int len = iter.nextU2ToInt(); + byte[] data = iter.getBytes(len); + String value = null; + try { + value = new String(data, "UTF-8"); + } catch (UnsupportedEncodingException e) { + e.printStackTrace(); + } + + UTF8Info utf8Str = new UTF8Info(pool); + utf8Str.setLength(len); + utf8Str.setValue(value); + pool.addConstantInfo(utf8Str); + } else if (tag == 8) { + StringInfo info = new StringInfo(pool); + info.setIndex(iter.nextU2ToInt()); + pool.addConstantInfo(info); + } else if (tag == 9) { + FieldRefInfo field = new FieldRefInfo(pool); + field.setClassInfoIndex(iter.nextU2ToInt()); + field.setNameAndTypeIndex(iter.nextU2ToInt()); + pool.addConstantInfo(field); + } else if (tag == 10) { + // MethodRef + MethodRefInfo method = new MethodRefInfo(pool); + method.setClassInfoIndex(iter.nextU2ToInt()); + method.setNameAndTypeIndex(iter.nextU2ToInt()); + pool.addConstantInfo(method); + } else if (tag == 12) { + // Name and Type Info + NameAndTypeInfo nameType = new NameAndTypeInfo(pool); + nameType.setIndex1(iter.nextU2ToInt()); + nameType.setIndex2(iter.nextU2ToInt()); + pool.addConstantInfo(nameType); + } else { + throw new RuntimeException("the constant pool tag " + tag + " has not been implemented yet."); + } + } + + System.out.println("Finished reading Constant pool "); + + return pool; + } + + private void parseInterfaces(ByteCodeIterator iter) { + int interfaceCount = iter.nextU2ToInt(); + + System.out.println("interfaceCount:" + interfaceCount); + + // TODO : 如果实现了interface, 这里需要解析 + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java new file mode 100644 index 0000000000..2f043bc42e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java @@ -0,0 +1,48 @@ +package com.github.eulerlcs.jmr.jvm.method; + +import com.github.eulerlcs.jmr.jvm.attr.CodeAttr; +import com.github.eulerlcs.jmr.jvm.clz.ClassFile; +import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; + +public class Method { + + private int accessFlag; + private int nameIndex; + private int descriptorIndex; + + private com.github.eulerlcs.jmr.jvm.attr.CodeAttr codeAttr; + + private ClassFile clzFile; + + public ClassFile getClzFile() { + return clzFile; + } + + public int getNameIndex() { + return nameIndex; + } + + public int getDescriptorIndex() { + return descriptorIndex; + } + + public CodeAttr getCodeAttr() { + return codeAttr; + } + + public void setCodeAttr(CodeAttr code) { + this.codeAttr = code; + } + + public Method(ClassFile clzFile, int accessFlag, int nameIndex, int descriptorIndex) { + this.clzFile = clzFile; + this.accessFlag = accessFlag; + this.nameIndex = nameIndex; + this.descriptorIndex = descriptorIndex; + } + + public static Method parse(ClassFile clzFile, ByteCodeIterator iter) { + return null; + + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java new file mode 100644 index 0000000000..7cc99ed27e --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java @@ -0,0 +1,22 @@ +package com.github.eulerlcs.jmr.jvm.util; + +public class Util { + public static int byteToInt(byte[] codes) { + String s1 = byteToHexString(codes); + return Integer.valueOf(s1, 16).intValue(); + } + + public static String byteToHexString(byte[] codes) { + StringBuffer buffer = new StringBuffer(); + for (int i = 0; i < codes.length; i++) { + byte b = codes[i]; + int value = b & 0xFF; + String strHex = Integer.toHexString(value); + if (strHex.length() < 2) { + strHex = "0" + strHex; + } + buffer.append(strHex); + } + return buffer.toString(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java new file mode 100644 index 0000000000..debc4d7eb6 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java @@ -0,0 +1,27 @@ +package com.github.eulerlcs.jmr.algorithm; + +import org.junit.Assert; +import org.junit.Test; + +public class LRUPageFrameTest { + @Test + public void testAccess() { + LRUPageFrame frame = new LRUPageFrame(3); + frame.access(7); + frame.access(0); + frame.access(1); + Assert.assertEquals("1,0,7", frame.toString()); + frame.access(2); + Assert.assertEquals("2,1,0", frame.toString()); + frame.access(0); + Assert.assertEquals("0,2,1", frame.toString()); + frame.access(0); + Assert.assertEquals("0,2,1", frame.toString()); + frame.access(3); + Assert.assertEquals("3,0,2", frame.toString()); + frame.access(0); + Assert.assertEquals("0,3,2", frame.toString()); + frame.access(4); + Assert.assertEquals("4,0,3", frame.toString()); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java new file mode 100644 index 0000000000..1e18416b61 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java @@ -0,0 +1,220 @@ +package com.github.eulerlcs.jmr.jvm.loader; + +import java.io.File; +import java.util.List; + +import javax.xml.bind.DatatypeConverter; + +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +import com.github.eulerlcs.jmr.jvm.clz.ClassFile; +import com.github.eulerlcs.jmr.jvm.clz.ClassIndex; +import com.github.eulerlcs.jmr.jvm.constant.ClassInfo; +import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; +import com.github.eulerlcs.jmr.jvm.constant.MethodRefInfo; +import com.github.eulerlcs.jmr.jvm.constant.NameAndTypeInfo; +import com.github.eulerlcs.jmr.jvm.constant.UTF8Info; +import com.github.eulerlcs.jmr.jvm.field.Field; +import com.github.eulerlcs.jmr.jvm.method.Method; + +public class ClassFileloaderTest { + private static final String FULL_QUALIFIED_CLASS_NAME = "com/coderising/jvm/test/EmployeeV1"; + private static String userDir = System.getProperty("user.dir"); + private static String path1 = "C:\temp"; + private static String path2 = userDir + File.separator + "target" + File.separator + "test-classes"; + private static String className = EmployeeV1.class.getName(); + static ClassFileLoader loader = null; + static ClassFile clzFile = null; + static { + loader = new ClassFileLoader(); + loader.addClassPath(path1); + loader.addClassPath(path2); + clzFile = loader.loadClass(className); + clzFile.print(); + } + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + loader = null; + } + + @Test + public void testClassPath() { + String clzPath = loader.getClassPath(); + Assert.assertEquals(path1 + ";" + path2, clzPath); + } + + @Test + public void testClassFileLength() { + byte[] byteCodes = loader.readBinaryCode(className); + // 注意:这个字节数可能和你的JVM版本有关系, 你可以看看编译好的类到底有多大 + Assert.assertEquals(1078, byteCodes.length); + + } + + @Test + public void testMagicNumber() { + byte[] byteCodes = loader.readBinaryCode(className); + byte[] codes = new byte[] { byteCodes[0], byteCodes[1], byteCodes[2], byteCodes[3] }; + String acctualValue = DatatypeConverter.printHexBinary(codes); + + Assert.assertEquals("CAFEBABE", acctualValue); + } + + /** + * ---------------------------------------------------------------------- + */ + + @Test + public void testVersion() { + + Assert.assertEquals(0, clzFile.getMinorVersion()); + Assert.assertEquals(52, clzFile.getMajorVersion()); + + } + + @Test + public void testConstantPool() { + + ConstantPool pool = clzFile.getConstantPool(); + + Assert.assertEquals(53, pool.getSize()); + + { + ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(1); + Assert.assertEquals(2, clzInfo.getUtf8Index()); + + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(2); + Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, utf8Info.getValue()); + } + { + ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(3); + Assert.assertEquals(4, clzInfo.getUtf8Index()); + + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(4); + Assert.assertEquals("java/lang/Object", utf8Info.getValue()); + } + { + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(5); + Assert.assertEquals("name", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(6); + Assert.assertEquals("Ljava/lang/String;", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(7); + Assert.assertEquals("age", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(8); + Assert.assertEquals("I", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(9); + Assert.assertEquals("", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(10); + Assert.assertEquals("(Ljava/lang/String;I)V", utf8Info.getValue()); + + utf8Info = (UTF8Info) pool.getConstantInfo(11); + Assert.assertEquals("Code", utf8Info.getValue()); + } + + { + MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(12); + Assert.assertEquals(3, methodRef.getClassInfoIndex()); + Assert.assertEquals(13, methodRef.getNameAndTypeIndex()); + } + + { + NameAndTypeInfo nameAndType = (NameAndTypeInfo) pool.getConstantInfo(13); + Assert.assertEquals(9, nameAndType.getIndex1()); + Assert.assertEquals(14, nameAndType.getIndex2()); + } + // 抽查几个吧 + { + MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(45); + Assert.assertEquals(1, methodRef.getClassInfoIndex()); + Assert.assertEquals(46, methodRef.getNameAndTypeIndex()); + } + + { + UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(53); + Assert.assertEquals("EmployeeV1.java", utf8Info.getValue()); + } + } + + @Test + public void testClassIndex() { + + ClassIndex clzIndex = clzFile.getClzIndex(); + ClassInfo thisClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getThisClassIndex()); + ClassInfo superClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getSuperClassIndex()); + + Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, thisClassInfo.getClassName()); + Assert.assertEquals("java/lang/Object", superClassInfo.getClassName()); + } + + /** + * 下面是第三次JVM课应实现的测试用例 + */ + @Test + public void testReadFields() { + + List fields = clzFile.getFields(); + Assert.assertEquals(2, fields.size()); + { + Field f = fields.get(0); + Assert.assertEquals("name:Ljava/lang/String;", f.toString()); + } + { + Field f = fields.get(1); + Assert.assertEquals("age:I", f.toString()); + } + } + + @Test + public void testMethods() { + + List methods = clzFile.getMethods(); + ConstantPool pool = clzFile.getConstantPool(); + + { + Method m = methods.get(0); + assertMethodEquals(pool, m, "", "(Ljava/lang/String;I)V", "2ab7000c2a2bb5000f2a1cb50011b1"); + + } + { + Method m = methods.get(1); + assertMethodEquals(pool, m, "setName", "(Ljava/lang/String;)V", "2a2bb5000fb1"); + + } + { + Method m = methods.get(2); + assertMethodEquals(pool, m, "setAge", "(I)V", "2a1bb50011b1"); + } + { + Method m = methods.get(3); + assertMethodEquals(pool, m, "sayHello", "()V", "b2001c1222b60024b1"); + + } + { + Method m = methods.get(4); + assertMethodEquals(pool, m, "main", "([Ljava/lang/String;)V", "bb000159122b101db7002d4c2bb6002fb1"); + } + } + + private void assertMethodEquals(ConstantPool pool, Method m, String expectedName, String expectedDesc, + String expectedCode) { + String methodName = pool.getUTF8String(m.getNameIndex()); + String methodDesc = pool.getUTF8String(m.getDescriptorIndex()); + String code = m.getCodeAttr().getCode(); + Assert.assertEquals(expectedName, methodName); + Assert.assertEquals(expectedDesc, methodDesc); + Assert.assertEquals(expectedCode, code); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java new file mode 100644 index 0000000000..070ad19083 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java @@ -0,0 +1,28 @@ +package com.github.eulerlcs.jmr.jvm.loader; + +public class EmployeeV1 { + private String name; + private int age; + + public EmployeeV1(String name, int age) { + this.name = name; + this.age = age; + } + + public void setName(String name) { + this.name = name; + } + + public void setAge(int age) { + this.age = age; + } + + public void sayHello() { + System.out.println("Hello , this is class Employee "); + } + + public static void main(String[] args) { + EmployeeV1 p = new EmployeeV1("Andy", 29); + p.sayHello(); + } +} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/5.settingfile/eclipsev45.epf b/students/41689722.eulerlcs/5.settingfile/eclipsev45.epf new file mode 100644 index 0000000000..ca88d61e06 --- /dev/null +++ b/students/41689722.eulerlcs/5.settingfile/eclipsev45.epf @@ -0,0 +1,186 @@ +#Sat Mar 11 11:44:44 JST 2017 +\!/= +/configuration/org.eclipse.core.net/org.eclipse.core.net.hasMigrated=true +/configuration/org.eclipse.ui.ide/MAX_RECENT_WORKSPACES=10 +/configuration/org.eclipse.ui.ide/RECENT_WORKSPACES=E\:\\10.github.repo\\coding2017.eulerlcs\\group09\\41689722.eulerlcs\\2.code +/configuration/org.eclipse.ui.ide/RECENT_WORKSPACES_PROTOCOL=3 +/configuration/org.eclipse.ui.ide/SHOW_RECENT_WORKSPACES=false +/configuration/org.eclipse.ui.ide/SHOW_WORKSPACE_SELECTION_DIALOG=true +/instance/org.eclipse.core.net/org.eclipse.core.net.hasMigrated=true +/instance/org.eclipse.core.resources/encoding=UTF-8 +/instance/org.eclipse.core.resources/version=1 +/instance/org.eclipse.debug.core/prefWatchExpressions=\r\n\r\n +/instance/org.eclipse.debug.ui/org.eclipse.debug.ui.PREF_LAUNCH_PERSPECTIVES=\r\n\r\n +/instance/org.eclipse.debug.ui/pref_state_memento.org.eclipse.debug.ui.DebugVieworg.eclipse.debug.ui.DebugView=\r\n +/instance/org.eclipse.debug.ui/pref_state_memento.org.eclipse.debug.ui.ExpressionView=\r\n\r\n\r\n +/instance/org.eclipse.debug.ui/pref_state_memento.org.eclipse.debug.ui.VariableView=\r\n +/instance/org.eclipse.debug.ui/preferredDetailPanes=DefaultDetailPane\:DefaultDetailPane| +/instance/org.eclipse.e4.ui.css.swt.theme/themeid=org.eclipse.e4.ui.css.theme.e4_default6.0,6.1,6.2,6.3,10.0 +/instance/org.eclipse.e4.ui.workbench.renderers.swt/enableMRU=true +/instance/org.eclipse.e4.ui.workbench.renderers.swt/themeEnabled=true +/instance/org.eclipse.egit.core/GitRepositoriesView.GitDirectories=E\:\\10.github.repo\\coding2017.eulerlcs\\.git; +/instance/org.eclipse.egit.core/GitRepositoriesView.GitDirectories.relative=E\:\\10.github.repo\\coding2017.eulerlcs\\.git; +/instance/org.eclipse.epp.logging.aeri.ide/resetSendMode=KEEP +/instance/org.eclipse.epp.logging.aeri.ide/resetSendModeOn=0 +/instance/org.eclipse.epp.logging.aeri.ide/sendMode=NOTIFY +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.codeComplete.visibilityCheck=enabled +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8 +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.compliance=1.8 +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.problem.assertIdentifier=error +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.problem.enumIdentifier=error +/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.source=1.8 +/instance/org.eclipse.jdt.launching/org.eclipse.jdt.launching.PREF_VM_XML=\r\n\r\n\r\n\r\n\r\n\r\n +/instance/org.eclipse.jdt.ui/content_assist_number_of_computers=24 +/instance/org.eclipse.jdt.ui/content_assist_proposals_background=255,255,255 +/instance/org.eclipse.jdt.ui/content_assist_proposals_foreground=0,0,0 +/instance/org.eclipse.jdt.ui/editor_save_participant_org.eclipse.jdt.ui.postsavelistener.cleanup=true +/instance/org.eclipse.jdt.ui/fontPropagated=true +/instance/org.eclipse.jdt.ui/org.eclipse.jdt.internal.ui.navigator.layout=2 +/instance/org.eclipse.jdt.ui/org.eclipse.jdt.internal.ui.navigator.librariesnode=true +/instance/org.eclipse.jdt.ui/org.eclipse.jdt.ui.editor.tab.width= +/instance/org.eclipse.jdt.ui/org.eclipse.jdt.ui.formatterprofiles.version=12 +/instance/org.eclipse.jdt.ui/org.eclipse.jdt.ui.javadoclocations.migrated=true +/instance/org.eclipse.jdt.ui/org.eclipse.jface.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.jdt.ui/proposalOrderMigrated=true +/instance/org.eclipse.jdt.ui/sourceHoverBackgroundColor=255,255,225 +/instance/org.eclipse.jdt.ui/sp_cleanup.add_default_serial_version_id=true +/instance/org.eclipse.jdt.ui/sp_cleanup.add_generated_serial_version_id=false +/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_annotations=true +/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_deprecated_annotations=true +/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_methods=false +/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_nls_tags=false +/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_override_annotations=true +/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_override_annotations_interface_methods=true +/instance/org.eclipse.jdt.ui/sp_cleanup.add_serial_version_id=false +/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_blocks=true +/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_parentheses_in_expressions=false +/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_this_for_non_static_field_access=false +/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_this_for_non_static_method_access=false +/instance/org.eclipse.jdt.ui/sp_cleanup.convert_functional_interfaces=false +/instance/org.eclipse.jdt.ui/sp_cleanup.convert_to_enhanced_for_loop=false +/instance/org.eclipse.jdt.ui/sp_cleanup.correct_indentation=false +/instance/org.eclipse.jdt.ui/sp_cleanup.format_source_code=true +/instance/org.eclipse.jdt.ui/sp_cleanup.format_source_code_changes_only=false +/instance/org.eclipse.jdt.ui/sp_cleanup.insert_inferred_type_arguments=false +/instance/org.eclipse.jdt.ui/sp_cleanup.make_local_variable_final=true +/instance/org.eclipse.jdt.ui/sp_cleanup.make_parameters_final=false +/instance/org.eclipse.jdt.ui/sp_cleanup.make_private_fields_final=true +/instance/org.eclipse.jdt.ui/sp_cleanup.make_type_abstract_if_missing_method=false +/instance/org.eclipse.jdt.ui/sp_cleanup.make_variable_declarations_final=false +/instance/org.eclipse.jdt.ui/sp_cleanup.never_use_blocks=false +/instance/org.eclipse.jdt.ui/sp_cleanup.never_use_parentheses_in_expressions=true +/instance/org.eclipse.jdt.ui/sp_cleanup.on_save_use_additional_actions=true +/instance/org.eclipse.jdt.ui/sp_cleanup.organize_imports=true +/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_field_accesses_with_declaring_class=false +/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_member_accesses_through_instances_with_declaring_class=true +/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class=true +/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_member_accesses_with_declaring_class=false +/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_method_accesses_with_declaring_class=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_private_constructors=true +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_redundant_type_arguments=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_trailing_whitespaces=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_trailing_whitespaces_all=true +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_trailing_whitespaces_ignore_empty=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unnecessary_casts=true +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unnecessary_nls_tags=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_imports=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_local_variables=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_fields=true +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_members=false +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_methods=true +/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_types=true +/instance/org.eclipse.jdt.ui/sp_cleanup.sort_members=false +/instance/org.eclipse.jdt.ui/sp_cleanup.sort_members_all=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_anonymous_class_creation=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_blocks=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_blocks_only_for_return_and_throw=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_lambda=true +/instance/org.eclipse.jdt.ui/sp_cleanup.use_parentheses_in_expressions=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_field_access=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_field_access_only_if_necessary=true +/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_method_access=false +/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_method_access_only_if_necessary=true +/instance/org.eclipse.jdt.ui/spelling_locale_initialized=true +/instance/org.eclipse.jdt.ui/tabWidthPropagated=true +/instance/org.eclipse.jdt.ui/useAnnotationsPrefPage=true +/instance/org.eclipse.jdt.ui/useQuickDiffPrefPage=true +/instance/org.eclipse.jst.j2ee.webservice.ui/areThereWebServices=false +/instance/org.eclipse.m2e.discovery/org.eclipse.m2e.discovery.pref.projects= +/instance/org.eclipse.mylyn.context.core/mylyn.attention.migrated=true +/instance/org.eclipse.mylyn.monitor.ui/org.eclipse.mylyn.monitor.activity.tracking.enabled.checked=true +/instance/org.eclipse.mylyn.tasks.ui/migrated.task.repositories.secure.store=true +/instance/org.eclipse.mylyn.tasks.ui/org.eclipse.mylyn.tasks.ui.filters.nonmatching=true +/instance/org.eclipse.mylyn.tasks.ui/org.eclipse.mylyn.tasks.ui.filters.nonmatching.encouraged=true +/instance/org.eclipse.mylyn.tasks.ui/org.eclipse.mylyn.tasks.ui.welcome.message=true +/instance/org.eclipse.oomph.workingsets/working.set.group=\n\n +/instance/org.eclipse.rse.core/org.eclipse.rse.systemtype.local.systemType.defaultUserId=euler +/instance/org.eclipse.rse.ui/org.eclipse.rse.preferences.order.connections=euler-PC.Local +/instance/org.eclipse.team.ui/org.eclipse.team.ui.first_time=false +/instance/org.eclipse.ui.editors/overviewRuler_migration=migrated_3.1 +/instance/org.eclipse.ui.ide/PROBLEMS_FILTERS_MIGRATE=true +/instance/org.eclipse.ui.ide/platformState=1488095469945 +/instance/org.eclipse.ui.ide/quickStart=false +/instance/org.eclipse.ui.ide/tipsAndTricks=true +/instance/org.eclipse.ui.workbench//org.eclipse.ui.commands/state/org.eclipse.ui.navigator.resources.nested.changeProjectPresentation/org.eclipse.ui.commands.radioState=false +/instance/org.eclipse.ui.workbench//org.eclipse.ui.commands/state/org.eclipse.wst.xml.views.XPathView.processor.xpathprocessor/org.eclipse.ui.commands.radioState=xpath10 +/instance/org.eclipse.ui.workbench/ColorsAndFontsPreferencePage.expandedCategories=Torg.eclipse.ui.workbenchMisc\tTorg.eclipse.jdt.ui.presentation\tTorg.eclipse.wst.sse.ui +/instance/org.eclipse.ui.workbench/ColorsAndFontsPreferencePage.selectedElement=Forg.eclipse.jface.textfont +/instance/org.eclipse.ui.workbench/PLUGINS_NOT_ACTIVATED_ON_STARTUP=org.eclipse.m2e.discovery;org.eclipse.rse.ui; +/instance/org.eclipse.ui.workbench/REMOTE_COMMANDS_VIEW_FONT=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.compare.contentmergeviewer.TextMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.debug.ui.DetailPaneFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.debug.ui.MemoryViewTableFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.debug.ui.consoleFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.egit.ui.CommitMessageEditorFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.egit.ui.CommitMessageFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.egit.ui.DiffHeadlineFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.jdt.internal.ui.compare.JavaMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.jdt.internal.ui.compare.PropertiesFileMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.jdt.ui.PropertiesFileEditor.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.jdt.ui.editors.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.jface.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.mylyn.wikitext.ui.presentation.textFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.pde.internal.ui.compare.ManifestContentMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.pde.internal.ui.compare.PluginContentMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.ui.commands=\r\n +/instance/org.eclipse.ui.workbench/org.eclipse.wst.jsdt.internal.ui.compare.JavaMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.wst.jsdt.ui.editors.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/org.eclipse.wst.sse.ui.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui.workbench/terminal.views.view.font.definition=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.ui/showIntro=false +/instance/org.eclipse.wst.jsdt.ui/fontPropagated=true +/instance/org.eclipse.wst.jsdt.ui/org.eclipse.jface.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; +/instance/org.eclipse.wst.jsdt.ui/org.eclipse.wst.jsdt.ui.editor.tab.width= +/instance/org.eclipse.wst.jsdt.ui/org.eclipse.wst.jsdt.ui.formatterprofiles.version=11 +/instance/org.eclipse.wst.jsdt.ui/org.eclipse.wst.jsdt.ui.javadoclocations.migrated=true +/instance/org.eclipse.wst.jsdt.ui/proposalOrderMigrated=true +/instance/org.eclipse.wst.jsdt.ui/tabWidthPropagated=true +/instance/org.eclipse.wst.jsdt.ui/useAnnotationsPrefPage=true +/instance/org.eclipse.wst.jsdt.ui/useQuickDiffPrefPage=true +@org.eclipse.core.net=1.3.0.v20160418-1534 +@org.eclipse.core.resources=3.11.1.v20161107-2032 +@org.eclipse.debug.core=3.10.100.v20160419-1720 +@org.eclipse.debug.ui=3.11.202.v20161114-0338 +@org.eclipse.e4.ui.css.swt.theme=0.10.100.v20160523-0836 +@org.eclipse.e4.ui.workbench.renderers.swt=0.14.0.v20160525-0940 +@org.eclipse.egit.core=4.4.1.201607150455-r +@org.eclipse.epp.logging.aeri.ide=2.0.3.v20161205-0933 +@org.eclipse.jdt.core=3.12.2.v20161117-1814 +@org.eclipse.jdt.launching=3.8.101.v20161111-2014 +@org.eclipse.jdt.ui=3.12.2.v20160929-0804 +@org.eclipse.jst.j2ee.webservice.ui=1.1.500.v201302011850 +@org.eclipse.m2e.discovery=1.7.0.20160603-1933 +@org.eclipse.mylyn.context.core=3.21.0.v20160701-1337 +@org.eclipse.mylyn.monitor.ui=3.21.0.v20160630-1702 +@org.eclipse.mylyn.tasks.ui=3.21.0.v20160913-2131 +@org.eclipse.oomph.workingsets=1.6.0.v20161019-0656 +@org.eclipse.rse.core=3.3.100.201603151753 +@org.eclipse.rse.ui=3.3.300.201610252046 +@org.eclipse.team.ui=3.8.0.v20160518-1906 +@org.eclipse.ui=3.108.1.v20160929-1045 +@org.eclipse.ui.editors=3.10.1.v20161106-1856 +@org.eclipse.ui.ide=3.12.2.v20161115-1450 +@org.eclipse.ui.workbench=3.108.2.v20161025-2029 +@org.eclipse.wst.jsdt.ui=2.0.0.v201608301904 +file_export_version=3.0 diff --git a/students/41689722.eulerlcs/5.settingfile/git cmd help.txt b/students/41689722.eulerlcs/5.settingfile/git cmd help.txt new file mode 100644 index 0000000000..86015b4865 --- /dev/null +++ b/students/41689722.eulerlcs/5.settingfile/git cmd help.txt @@ -0,0 +1,43 @@ +open git server deretory +mkdir abc.git +cd abc.git + +run git bash + git --bare init --shared + +git clone +cd abc + +git config --global push. default simple +git push --set-upstream origin master +git push + +get remot branch list + git remote update + + +add deleted files + git rm + git rm $(git ls-files --deleted) + + +delete (remote) branch + git branch -d branch.abc + git push origin :branch.abc + + or + + git push --delete origin branch.abc + + +romote branch douki + git fecth --all --prune + +git log + git log --graph --pretty=format: + +// http://blog.toshimaru.net/git-log-graph/ + [alias] + lg = git log --graph --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit --date=relative + lga = git log --graph --all --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit --date=relative + \ No newline at end of file diff --git a/students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat b/students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat new file mode 100644 index 0000000000..ddb704e561 --- /dev/null +++ b/students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat @@ -0,0 +1,37 @@ +@echo off +setlocal ENABLEDELAYEDEXPANSION + +rem .* +:main + call :ini + + set path_root=d:\abc + set path_desc=pg.%yymmdd%.%hhmmss% + + call :copy_source "" + call :copy_source "" + + call :end + @echo on + +goto :eof +:copy_source + if %1=="" goto :eof + set file_name=%~1 + set file_name=!file_name:/=\! + @echo f | xcopy /r/y/s %path_root%\!file_name! %path_desc%\!file_name! + +goto :eof +:end + @echo. + @echo. + pause + +goto :eof +:ini + set self_path="%cd%" + set yyyymmdd=%date:~0,4%%date:~5,2%%date:~8,2% + set yymmdd=!yyyymmdd:~2,6! + set hhmmss=%time:~0,2%%time:~3,2%%time:~6,2% + if "!hhmmss:~0,1!" == " " set hhmmss=0!hhmmss:~1,7! +goto :eof diff --git a/students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat b/students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat new file mode 100644 index 0000000000..5189f9e130 --- /dev/null +++ b/students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat @@ -0,0 +1,37 @@ +@echo off +setlocal ENABLEDELAYEDEXPANSION + +:main + call :ini + cd /d E:\12.repolist\41689722.eulerlcs\2.code + call :del_resource + call :end + @echo on + +goto :eof +:del_resource + for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".settings"`) do rmdir /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".metadata"`) do rmdir /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/ad-h "target"`) do rmdir /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/ad-h "RemoteSystemsTempFiles"`) do rmdir /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".recommenders"`) do rmdir /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".apt_generated"`) do rmdir /s/q %%a + + for /f "usebackq delims==" %%a in (`dir /b/s/a-d-h ".classpath"`) do del /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/a-d-h ".project"`) do del /s/q %%a + for /f "usebackq delims==" %%a in (`dir /b/s/a-d-h ".factorypath"`) do del /s/q %%a + +goto :eof +:end + @echo. + @echo. + pause + +goto :eof +:ini + set self_path="%cd%" + set yyyymmdd=%date:~0,4%%date:~5,2%%date:~8,2% + set yymmdd=!yyyymmdd:~2,6! + set hhmmss=%time:~0,2%%time:~3,2%%time:~6,2% + if "!hhmmss:~0,1!" == " " set hhmmss=0!hhmmss:~1,7! +goto :eof From 1c6c8cadc5b7a47d0c3bd3e376c418e345c41faf Mon Sep 17 00:00:00 2001 From: eulerlcs Date: Sun, 18 Jun 2017 22:33:15 +0900 Subject: [PATCH 02/73] refactor --- .../2.code/jmr-01-aggregator/pom.xml | 2 - .../2.code/jmr-51-liuxin-question/pom.xml | 35 --- .../coderising/download/api/Connection.java | 28 -- .../download/api/ConnectionException.java | 5 - .../download/api/ConnectionManager.java | 11 - .../download/api/DownloadListener.java | 5 - .../download/core/DownloadThread.java | 21 -- .../download/core/FileDownloader.java | 68 ----- .../download/impl/ConnectionImpl.java | 26 -- .../download/impl/ConnectionManagerImpl.java | 15 -- .../coderising/jvm/attr/AttributeInfo.java | 19 -- .../com/coderising/jvm/attr/CodeAttr.java | 52 ---- .../coderising/jvm/attr/LineNumberTable.java | 46 ---- .../jvm/attr/LocalVariableItem.java | 49 ---- .../jvm/attr/LocalVariableTable.java | 25 -- .../coderising/jvm/attr/StackMapTable.java | 29 -- .../com/coderising/jvm/clz/AccessFlag.java | 26 -- .../com/coderising/jvm/clz/ClassFile.java | 100 ------- .../com/coderising/jvm/clz/ClassIndex.java | 22 -- .../coderising/jvm/constant/ClassInfo.java | 28 -- .../coderising/jvm/constant/ConstantInfo.java | 29 -- .../coderising/jvm/constant/ConstantPool.java | 28 -- .../coderising/jvm/constant/FieldRefInfo.java | 54 ---- .../jvm/constant/MethodRefInfo.java | 56 ---- .../jvm/constant/NameAndTypeInfo.java | 48 ---- .../jvm/constant/NullConstantInfo.java | 11 - .../coderising/jvm/constant/StringInfo.java | 28 -- .../com/coderising/jvm/constant/UTF8Info.java | 37 --- .../java/com/coderising/jvm/field/Field.java | 26 -- .../jvm/loader/ByteCodeIterator.java | 55 ---- .../jvm/loader/ClassFileLoader.java | 122 --------- .../jvm/loader/ClassFileParser.java | 146 ----------- .../com/coderising/jvm/method/Method.java | 48 ---- .../java/com/coderising/jvm/util/Util.java | 22 -- .../coderising/litestruts/LoginAction.java | 42 --- .../com/coderising/litestruts/Struts.java | 30 --- .../java/com/coderising/litestruts/View.java | 26 -- .../main/java/com/coding/basic/ArrayList.java | 33 --- .../main/java/com/coding/basic/ArrayUtil.java | 96 ------- .../java/com/coding/basic/BinaryTreeNode.java | 37 --- .../main/java/com/coding/basic/Iterator.java | 8 - .../java/com/coding/basic/LRUPageFrame.java | 50 ---- .../java/com/coding/basic/LinkedList.java | 126 --------- .../src/main/java/com/coding/basic/List.java | 13 - .../src/main/java/com/coding/basic/Queue.java | 19 -- .../java/com/coding/basic/stack/Stack.java | 26 -- .../com/coding/basic/stack/StackUtil.java | 54 ---- .../coding/basic/stack/expr/InfixExpr.java | 13 - .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 -- .../src/main/resources/struts.xml | 11 - .../download/core/FileDownloaderTest.java | 56 ---- .../jvm/loader/ClassFileloaderTest.java | 248 ------------------ .../com/coderising/jvm/loader/EmployeeV1.java | 30 --- .../com/coderising/litestruts/StrutsTest.java | 38 --- .../com/coding/basic/LRUPageFrameTest.java | 27 -- .../com/coding/basic/stack/StackUtilTest.java | 78 ------ .../basic/stack/expr/InfixExprTest.java | 45 ---- .../src/test/resources/.gitkeep | 0 .../2.code/jmr-52-liuxin-answer/pom.xml | 31 --- .../coderising/download/api/Connection.java | 28 -- .../download/api/ConnectionException.java | 8 - .../download/api/ConnectionManager.java | 11 - .../download/api/DownloadListener.java | 5 - .../download/core/DownloadThread.java | 50 ---- .../download/core/FileDownloader.java | 126 --------- .../download/impl/ConnectionImpl.java | 84 ------ .../download/impl/ConnectionManagerImpl.java | 15 -- .../coderising/litestruts/Configuration.java | 113 -------- .../litestruts/ConfigurationException.java | 21 -- .../coderising/litestruts/LoginAction.java | 42 --- .../coderising/litestruts/ReflectionUtil.java | 120 --------- .../com/coderising/litestruts/Struts.java | 56 ---- .../java/com/coderising/litestruts/View.java | 26 -- .../java/com/coding/basic/BinaryTreeNode.java | 37 --- .../main/java/com/coding/basic/Iterator.java | 8 - .../src/main/java/com/coding/basic/List.java | 13 - .../src/main/java/com/coding/basic/Queue.java | 19 -- .../com/coding/basic/array/ArrayList.java | 36 --- .../com/coding/basic/array/ArrayUtil.java | 96 ------- .../coding/basic/linklist/LRUPageFrame.java | 151 ----------- .../com/coding/basic/linklist/LinkedList.java | 129 --------- .../java/com/coding/basic/stack/Stack.java | 26 -- .../com/coding/basic/stack/StackUtil.java | 140 ---------- .../coding/basic/stack/expr/InfixExpr.java | 15 -- .../basic/stack/expr/InfixExprTest.java | 47 ---- .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 -- .../src/main/resources/struts.xml | 11 - .../download/api/ConnectionTest.java | 42 --- .../download/core/FileDownloaderTest.java | 56 ---- .../litestruts/ConfigurationTest.java | 46 ---- .../litestruts/ReflectionUtilTest.java | 104 -------- .../com/coderising/litestruts/StrutsTest.java | 37 --- .../basic/linklist/LRUPageFrameTest.java | 32 --- .../coding/basic/linklist/LinkedListTest.java | 197 -------------- .../com/coding/basic/stack/StackUtilTest.java | 78 ------ .../src/test/resources/.gitkeep | 0 98 files changed, 4516 deletions(-) delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/resources/.gitkeep diff --git a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml b/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml index 3edeb21d2e..78a5afbac0 100644 --- a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml +++ b/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml @@ -10,8 +10,6 @@ ../jmr-02-parent ../jmr-11-challenge - ../jmr-51-liuxin-question - ../jmr-52-liuxin-answer ../jmr-61-collection ../jmr-62-litestruts ../jmr-63-download diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml deleted file mode 100644 index dc562ded7e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/pom.xml +++ /dev/null @@ -1,35 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-51-liuxin-question - eulerlcs master java road copy from liuxin question - - - - org.apache.commons - commons-lang3 - - - org.apache.commons - commons-io - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java deleted file mode 100644 index 76dc0f3a40..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/Connection.java +++ /dev/null @@ -1,28 +0,0 @@ -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/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java deleted file mode 100644 index 1551a80b3d..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionException.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.coderising.download.api; - -public class ConnectionException extends Exception { - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java deleted file mode 100644 index 787984f170..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/ConnectionManager.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.coderising.download.api; - -public interface ConnectionManager { - /** - * 给定一个url , 打开一个连接 - * - * @param url - * @return - */ - public Connection open(String url) throws ConnectionException; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java deleted file mode 100644 index bf9807b307..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/api/DownloadListener.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.coderising.download.api; - -public interface DownloadListener { - public void notifyFinished(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java deleted file mode 100644 index ba94bee146..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/DownloadThread.java +++ /dev/null @@ -1,21 +0,0 @@ -package com.coderising.download.core; - -import com.coderising.download.api.Connection; - -public class DownloadThread extends Thread { - - Connection conn; - int startPos; - int endPos; - - public DownloadThread(Connection conn, int startPos, int endPos) { - - this.conn = conn; - this.startPos = startPos; - this.endPos = endPos; - } - - public void run() { - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java deleted file mode 100644 index 23ee19ab02..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/core/FileDownloader.java +++ /dev/null @@ -1,68 +0,0 @@ -package com.coderising.download.core; - -import com.coderising.download.api.Connection; -import com.coderising.download.api.ConnectionException; -import com.coderising.download.api.ConnectionManager; -import com.coderising.download.api.DownloadListener; - -public class FileDownloader { - - String url; - - DownloadListener listener; - - ConnectionManager cm; - - 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 { - - conn = cm.open(this.url); - - int length = conn.getContentLength(); - - new DownloadThread(conn, 0, length - 1).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/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java deleted file mode 100644 index 1831118927..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionImpl.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coderising.download.impl; - -import java.io.IOException; - -import com.coderising.download.api.Connection; - -public class ConnectionImpl implements Connection { - - @Override - public byte[] read(int startPos, int endPos) throws IOException { - - return null; - } - - @Override - public int getContentLength() { - - return 0; - } - - @Override - public void close() { - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java deleted file mode 100644 index 6585b835c4..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.coderising.download.impl; - -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 { - - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java deleted file mode 100644 index 3391da9616..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/AttributeInfo.java +++ /dev/null @@ -1,19 +0,0 @@ -package com.coderising.jvm.attr; - -public abstract class AttributeInfo { - public static final String CODE = "Code"; - public static final String CONST_VALUE = "ConstantValue"; - public static final String EXCEPTIONS = "Exceptions"; - public static final String LINE_NUM_TABLE = "LineNumberTable"; - public static final String LOCAL_VAR_TABLE = "LocalVariableTable"; - public static final String STACK_MAP_TABLE = "StackMapTable"; - int attrNameIndex; - int attrLen; - - public AttributeInfo(int attrNameIndex, int attrLen) { - - this.attrNameIndex = attrNameIndex; - this.attrLen = attrLen; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java deleted file mode 100644 index f7ed2f1297..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/CodeAttr.java +++ /dev/null @@ -1,52 +0,0 @@ -package com.coderising.jvm.attr; - -import com.coderising.jvm.clz.ClassFile; -import com.coderising.jvm.loader.ByteCodeIterator; - -public class CodeAttr extends AttributeInfo { - private int maxStack; - private int maxLocals; - private int codeLen; - private String code; - - public String getCode() { - return code; - } - - // private ByteCodeCommand[] cmds ; - // public ByteCodeCommand[] getCmds() { - // return cmds; - // } - private LineNumberTable lineNumTable; - private LocalVariableTable localVarTable; - private StackMapTable stackMapTable; - - public CodeAttr(int attrNameIndex, int attrLen, int maxStack, int maxLocals, int codeLen, - String code /* ByteCodeCommand[] cmds */) { - super(attrNameIndex, attrLen); - this.maxStack = maxStack; - this.maxLocals = maxLocals; - this.codeLen = codeLen; - this.code = code; - // this.cmds = cmds; - } - - public void setLineNumberTable(LineNumberTable t) { - this.lineNumTable = t; - } - - public void setLocalVariableTable(LocalVariableTable t) { - this.localVarTable = t; - } - - public static CodeAttr parse(ClassFile clzFile, ByteCodeIterator iter) { - - return null; - } - - private void setStackMapTable(StackMapTable t) { - this.stackMapTable = t; - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java deleted file mode 100644 index 71553b4fbb..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LineNumberTable.java +++ /dev/null @@ -1,46 +0,0 @@ -package com.coderising.jvm.attr; - -import java.util.ArrayList; -import java.util.List; - -import com.coderising.jvm.loader.ByteCodeIterator; - -public class LineNumberTable extends AttributeInfo { - List items = new ArrayList(); - - private static class LineNumberItem { - int startPC; - int lineNum; - - public int getStartPC() { - return startPC; - } - - public void setStartPC(int startPC) { - this.startPC = startPC; - } - - public int getLineNum() { - return lineNum; - } - - public void setLineNum(int lineNum) { - this.lineNum = lineNum; - } - } - - public void addLineNumberItem(LineNumberItem item) { - this.items.add(item); - } - - public LineNumberTable(int attrNameIndex, int attrLen) { - super(attrNameIndex, attrLen); - - } - - public static LineNumberTable parse(ByteCodeIterator iter) { - - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java deleted file mode 100644 index 9561e904a9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableItem.java +++ /dev/null @@ -1,49 +0,0 @@ -package com.coderising.jvm.attr; - -public class LocalVariableItem { - private int startPC; - private int length; - private int nameIndex; - private int descIndex; - private int index; - - public int getStartPC() { - return startPC; - } - - public void setStartPC(int startPC) { - this.startPC = startPC; - } - - public int getLength() { - return length; - } - - public void setLength(int length) { - this.length = length; - } - - public int getNameIndex() { - return nameIndex; - } - - public void setNameIndex(int nameIndex) { - this.nameIndex = nameIndex; - } - - public int getDescIndex() { - return descIndex; - } - - public void setDescIndex(int descIndex) { - this.descIndex = descIndex; - } - - public int getIndex() { - return index; - } - - public void setIndex(int index) { - this.index = index; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java deleted file mode 100644 index b8a3ccfa8f..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/LocalVariableTable.java +++ /dev/null @@ -1,25 +0,0 @@ -package com.coderising.jvm.attr; - -import java.util.ArrayList; -import java.util.List; - -import com.coderising.jvm.loader.ByteCodeIterator; - -public class LocalVariableTable extends AttributeInfo { - - List items = new ArrayList(); - - public LocalVariableTable(int attrNameIndex, int attrLen) { - super(attrNameIndex, attrLen); - } - - public static LocalVariableTable parse(ByteCodeIterator iter) { - - return null; - } - - private void addLocalVariableItem(LocalVariableItem item) { - this.items.add(item); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java deleted file mode 100644 index 14427e19ee..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/attr/StackMapTable.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.coderising.jvm.attr; - -import com.coderising.jvm.loader.ByteCodeIterator; - -public class StackMapTable extends AttributeInfo { - - private String originalCode; - - public StackMapTable(int attrNameIndex, int attrLen) { - super(attrNameIndex, attrLen); - } - - public static StackMapTable parse(ByteCodeIterator iter) { - int index = iter.nextU2ToInt(); - int len = iter.nextU4ToInt(); - StackMapTable t = new StackMapTable(index, len); - - // 后面的StackMapTable太过复杂, 不再处理, 只把原始的代码读进来保存 - String code = iter.nextUxToHexString(len); - t.setOriginalCode(code); - - return t; - } - - private void setOriginalCode(String code) { - this.originalCode = code; - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java deleted file mode 100644 index 2cc6092de0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/AccessFlag.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coderising.jvm.clz; - -public class AccessFlag { - private int flagValue; - - public AccessFlag(int value) { - this.flagValue = value; - } - - public int getFlagValue() { - return flagValue; - } - - public void setFlagValue(int flag) { - this.flagValue = flag; - } - - public boolean isPublicClass() { - return (this.flagValue & 0x0001) != 0; - } - - public boolean isFinalClass() { - return (this.flagValue & 0x0010) != 0; - } - -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java deleted file mode 100644 index ad5a7d71db..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassFile.java +++ /dev/null @@ -1,100 +0,0 @@ -package com.coderising.jvm.clz; - -import java.util.ArrayList; -import java.util.List; - -import com.coderising.jvm.constant.ClassInfo; -import com.coderising.jvm.constant.ConstantPool; -import com.coderising.jvm.field.Field; -import com.coderising.jvm.method.Method; - -public class ClassFile { - - private int minorVersion; - private int majorVersion; - - private AccessFlag accessFlag; - private ClassIndex clzIndex; - private ConstantPool pool; - private List fields = new ArrayList(); - private List methods = new ArrayList(); - - public ClassIndex getClzIndex() { - return clzIndex; - } - - public AccessFlag getAccessFlag() { - return accessFlag; - } - - public void setAccessFlag(AccessFlag accessFlag) { - this.accessFlag = accessFlag; - } - - public ConstantPool getConstantPool() { - return pool; - } - - public int getMinorVersion() { - return minorVersion; - } - - public void setMinorVersion(int minorVersion) { - this.minorVersion = minorVersion; - } - - public int getMajorVersion() { - return majorVersion; - } - - public void setMajorVersion(int majorVersion) { - this.majorVersion = majorVersion; - } - - public void setConstPool(ConstantPool pool) { - this.pool = pool; - - } - - public void setClassIndex(ClassIndex clzIndex) { - this.clzIndex = clzIndex; - } - - public void addField(Field f) { - this.fields.add(f); - } - - public List getFields() { - return this.fields; - } - - public void addMethod(Method m) { - this.methods.add(m); - } - - public List getMethods() { - return methods; - } - - public void print() { - - if (this.accessFlag.isPublicClass()) { - System.out.println("Access flag : public "); - } - System.out.println("Class Name:" + getClassName()); - - System.out.println("Super Class Name:" + getSuperClassName()); - - } - - private String getClassName() { - int thisClassIndex = this.clzIndex.getThisClassIndex(); - ClassInfo thisClass = (ClassInfo) this.getConstantPool().getConstantInfo(thisClassIndex); - return thisClass.getClassName(); - } - - private String getSuperClassName() { - ClassInfo superClass = (ClassInfo) this.getConstantPool().getConstantInfo(this.clzIndex.getSuperClassIndex()); - return superClass.getClassName(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java deleted file mode 100644 index 0212bc9fb3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/clz/ClassIndex.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.coderising.jvm.clz; - -public class ClassIndex { - private int thisClassIndex; - private int superClassIndex; - - public int getThisClassIndex() { - return thisClassIndex; - } - - public void setThisClassIndex(int thisClassIndex) { - this.thisClassIndex = thisClassIndex; - } - - public int getSuperClassIndex() { - return superClassIndex; - } - - public void setSuperClassIndex(int superClassIndex) { - this.superClassIndex = superClassIndex; - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java deleted file mode 100644 index 4b593e7347..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ClassInfo.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.coderising.jvm.constant; - -public class ClassInfo extends ConstantInfo { - private int type = ConstantInfo.CLASS_INFO; - private int utf8Index; - - public ClassInfo(ConstantPool pool) { - super(pool); - } - - public int getUtf8Index() { - return utf8Index; - } - - public void setUtf8Index(int utf8Index) { - this.utf8Index = utf8Index; - } - - public int getType() { - return type; - } - - public String getClassName() { - int index = getUtf8Index(); - UTF8Info utf8Info = (UTF8Info) constantPool.getConstantInfo(index); - return utf8Info.getValue(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java deleted file mode 100644 index 5ef8fbfef8..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantInfo.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.coderising.jvm.constant; - -public abstract class ConstantInfo { - public static final int UTF8_INFO = 1; - public static final int FLOAT_INFO = 4; - public static final int CLASS_INFO = 7; - public static final int STRING_INFO = 8; - public static final int FIELD_INFO = 9; - public static final int METHOD_INFO = 10; - public static final int NAME_AND_TYPE_INFO = 12; - protected ConstantPool constantPool; - - public ConstantInfo() { - } - - public ConstantInfo(ConstantPool pool) { - this.constantPool = pool; - } - - public abstract int getType(); - - public ConstantPool getConstantPool() { - return constantPool; - } - - public ConstantInfo getConstantInfo(int index) { - return this.constantPool.getConstantInfo(index); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java deleted file mode 100644 index 49ece7d089..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/ConstantPool.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.coderising.jvm.constant; - -import java.util.ArrayList; -import java.util.List; - -public class ConstantPool { - - private List constantInfos = new ArrayList(); - - public ConstantPool() { - } - - public void addConstantInfo(ConstantInfo info) { - this.constantInfos.add(info); - } - - public ConstantInfo getConstantInfo(int index) { - return this.constantInfos.get(index); - } - - public String getUTF8String(int index) { - return ((UTF8Info) this.constantInfos.get(index)).getValue(); - } - - public Object getSize() { - return this.constantInfos.size() - 1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java deleted file mode 100644 index 469a30b95e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/FieldRefInfo.java +++ /dev/null @@ -1,54 +0,0 @@ -package com.coderising.jvm.constant; - -public class FieldRefInfo extends ConstantInfo { - private int type = ConstantInfo.FIELD_INFO; - private int classInfoIndex; - private int nameAndTypeIndex; - - public FieldRefInfo(ConstantPool pool) { - super(pool); - } - - @Override - public int getType() { - return type; - } - - public int getClassInfoIndex() { - return classInfoIndex; - } - - public void setClassInfoIndex(int classInfoIndex) { - this.classInfoIndex = classInfoIndex; - } - - public int getNameAndTypeIndex() { - return nameAndTypeIndex; - } - - public void setNameAndTypeIndex(int nameAndTypeIndex) { - this.nameAndTypeIndex = nameAndTypeIndex; - } - - @Override - public String toString() { - NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); - return getClassName() + " : " + typeInfo.getName() + ":" + typeInfo.getTypeInfo() + "]"; - } - - public String getClassName() { - ClassInfo classInfo = (ClassInfo) this.getConstantInfo(this.getClassInfoIndex()); - UTF8Info utf8Info = (UTF8Info) this.getConstantInfo(classInfo.getUtf8Index()); - return utf8Info.getValue(); - } - - public String getFieldName() { - NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getName(); - } - - public String getFieldType() { - NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getTypeInfo(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java deleted file mode 100644 index 837e501f9f..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/MethodRefInfo.java +++ /dev/null @@ -1,56 +0,0 @@ -package com.coderising.jvm.constant; - -public class MethodRefInfo extends ConstantInfo { - private int type = ConstantInfo.METHOD_INFO; - - private int classInfoIndex; - private int nameAndTypeIndex; - - public MethodRefInfo(ConstantPool pool) { - super(pool); - } - - @Override - public int getType() { - return type; - } - - public int getClassInfoIndex() { - return classInfoIndex; - } - - public void setClassInfoIndex(int classInfoIndex) { - this.classInfoIndex = classInfoIndex; - } - - public int getNameAndTypeIndex() { - return nameAndTypeIndex; - } - - public void setNameAndTypeIndex(int nameAndTypeIndex) { - this.nameAndTypeIndex = nameAndTypeIndex; - } - - @Override - public String toString() { - return getClassName() + " : " + this.getMethodName() + " : " + this.getParamAndReturnType(); - } - - public String getClassName() { - ConstantPool pool = this.getConstantPool(); - ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(this.getClassInfoIndex()); - return clzInfo.getClassName(); - } - - public String getMethodName() { - ConstantPool pool = this.getConstantPool(); - NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getName(); - } - - public String getParamAndReturnType() { - ConstantPool pool = this.getConstantPool(); - NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getTypeInfo(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java deleted file mode 100644 index a792e2dc13..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NameAndTypeInfo.java +++ /dev/null @@ -1,48 +0,0 @@ -package com.coderising.jvm.constant; - -public class NameAndTypeInfo extends ConstantInfo { - public int type = ConstantInfo.NAME_AND_TYPE_INFO; - - private int index1; - private int index2; - - public NameAndTypeInfo(ConstantPool pool) { - super(pool); - } - - public int getIndex1() { - return index1; - } - - public void setIndex1(int index1) { - this.index1 = index1; - } - - public int getIndex2() { - return index2; - } - - public void setIndex2(int index2) { - this.index2 = index2; - } - - public int getType() { - return type; - } - - public String getName() { - ConstantPool pool = this.getConstantPool(); - UTF8Info utf8Info1 = (UTF8Info) pool.getConstantInfo(index1); - return utf8Info1.getValue(); - } - - public String getTypeInfo() { - ConstantPool pool = this.getConstantPool(); - UTF8Info utf8Info2 = (UTF8Info) pool.getConstantInfo(index2); - return utf8Info2.getValue(); - } - - public String toString() { - return "(" + getName() + "," + getTypeInfo() + ")"; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java deleted file mode 100644 index 6e4e3750c7..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/NullConstantInfo.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.coderising.jvm.constant; - -public class NullConstantInfo extends ConstantInfo { - public NullConstantInfo() { - } - - @Override - public int getType() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java deleted file mode 100644 index 3282aad968..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/StringInfo.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.coderising.jvm.constant; - -public class StringInfo extends ConstantInfo { - private int type = ConstantInfo.STRING_INFO; - private int index; - - public StringInfo(ConstantPool pool) { - super(pool); - } - - @Override - public int getType() { - return type; - } - - public int getIndex() { - return index; - } - - public void setIndex(int index) { - this.index = index; - } - - @Override - public String toString() { - return this.getConstantPool().getUTF8String(index); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java deleted file mode 100644 index dc4d0b0b64..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/constant/UTF8Info.java +++ /dev/null @@ -1,37 +0,0 @@ -package com.coderising.jvm.constant; - -public class UTF8Info extends ConstantInfo { - private int type = ConstantInfo.UTF8_INFO; - private int length; - private String value; - - public UTF8Info(ConstantPool pool) { - super(pool); - } - - public int getLength() { - return length; - } - - public void setLength(int length) { - this.length = length; - } - - @Override - public int getType() { - return type; - } - - @Override - public String toString() { - return "UTF8Info [type=" + type + ", length=" + length + ", value=" + value + ")]"; - } - - public String getValue() { - return value; - } - - public void setValue(String value) { - this.value = value; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java deleted file mode 100644 index 64742c6596..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/field/Field.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coderising.jvm.field; - -import com.coderising.jvm.constant.ConstantPool; -import com.coderising.jvm.loader.ByteCodeIterator; - -public class Field { - private int accessFlag; - private int nameIndex; - private int descriptorIndex; - - private ConstantPool pool; - - public Field(int accessFlag, int nameIndex, int descriptorIndex, ConstantPool pool) { - - this.accessFlag = accessFlag; - this.nameIndex = nameIndex; - this.descriptorIndex = descriptorIndex; - this.pool = pool; - } - - public static Field parse(ConstantPool pool, ByteCodeIterator iter) { - - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java deleted file mode 100644 index 3cc8ab6697..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ByteCodeIterator.java +++ /dev/null @@ -1,55 +0,0 @@ -package com.coderising.jvm.loader; - -import java.util.Arrays; - -import com.coderising.jvm.util.Util; - -public class ByteCodeIterator { - byte[] codes; - int pos = 0; - - ByteCodeIterator(byte[] codes) { - this.codes = codes; - } - - public byte[] getBytes(int len) { - if (pos + len >= codes.length) { - throw new ArrayIndexOutOfBoundsException(); - } - - byte[] data = Arrays.copyOfRange(codes, pos, pos + len); - pos += len; - return data; - } - - public int nextU1toInt() { - - return Util.byteToInt(new byte[] { codes[pos++] }); - } - - public int nextU2ToInt() { - return Util.byteToInt(new byte[] { codes[pos++], codes[pos++] }); - } - - public int nextU4ToInt() { - return Util.byteToInt(new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] }); - } - - public String nextU4ToHexString() { - return Util.byteToHexString((new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] })); - } - - public String nextUxToHexString(int len) { - byte[] tmp = new byte[len]; - - for (int i = 0; i < len; i++) { - tmp[i] = codes[pos++]; - } - return Util.byteToHexString(tmp).toLowerCase(); - - } - - public void back(int n) { - this.pos -= n; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java deleted file mode 100644 index 1af1946bb3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileLoader.java +++ /dev/null @@ -1,122 +0,0 @@ -package com.coderising.jvm.loader; - -import java.io.BufferedInputStream; -import java.io.ByteArrayOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.util.ArrayList; -import java.util.List; - -import org.apache.commons.io.IOUtils; -import org.apache.commons.lang3.StringUtils; - -import com.coderising.jvm.clz.ClassFile; - -public class ClassFileLoader { - - private List clzPaths = new ArrayList(); - - public byte[] readBinaryCode(String className) { - - className = className.replace('.', File.separatorChar) + ".class"; - - for (String path : this.clzPaths) { - - String clzFileName = path + File.separatorChar + className; - byte[] codes = loadClassFile(clzFileName); - if (codes != null) { - return codes; - } - } - - return null; - - } - - private byte[] loadClassFile(String clzFileName) { - - File f = new File(clzFileName); - - try { - - return IOUtils.toByteArray(new FileInputStream(f)); - - } catch (IOException e) { - e.printStackTrace(); - return null; - } - } - - public void addClassPath(String path) { - if (this.clzPaths.contains(path)) { - return; - } - - this.clzPaths.add(path); - - } - - public String getClassPath() { - return StringUtils.join(this.clzPaths, ";"); - } - - public ClassFile loadClass(String className) { - byte[] codes = this.readBinaryCode(className); - ClassFileParser parser = new ClassFileParser(); - return parser.parse(codes); - - } - - // ------------------------------backup------------------------ - public String getClassPath_V1() { - - StringBuffer buffer = new StringBuffer(); - for (int i = 0; i < this.clzPaths.size(); i++) { - buffer.append(this.clzPaths.get(i)); - if (i < this.clzPaths.size() - 1) { - buffer.append(";"); - } - } - return buffer.toString(); - } - - private byte[] loadClassFile_V1(String clzFileName) { - - BufferedInputStream bis = null; - - try { - - File f = new File(clzFileName); - - bis = new BufferedInputStream(new FileInputStream(f)); - - ByteArrayOutputStream bos = new ByteArrayOutputStream(); - - byte[] buffer = new byte[1024]; - int length = -1; - - while ((length = bis.read(buffer)) != -1) { - bos.write(buffer, 0, length); - } - - byte[] codes = bos.toByteArray(); - - return codes; - - } catch (IOException e) { - e.printStackTrace(); - - } finally { - if (bis != null) { - try { - bis.close(); - } catch (IOException e) { - e.printStackTrace(); - } - } - } - return null; - - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java deleted file mode 100644 index b32ca1926b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/loader/ClassFileParser.java +++ /dev/null @@ -1,146 +0,0 @@ -package com.coderising.jvm.loader; - -import java.io.UnsupportedEncodingException; - -import com.coderising.jvm.clz.AccessFlag; -import com.coderising.jvm.clz.ClassFile; -import com.coderising.jvm.clz.ClassIndex; -import com.coderising.jvm.constant.ClassInfo; -import com.coderising.jvm.constant.ConstantPool; -import com.coderising.jvm.constant.FieldRefInfo; -import com.coderising.jvm.constant.MethodRefInfo; -import com.coderising.jvm.constant.NameAndTypeInfo; -import com.coderising.jvm.constant.NullConstantInfo; -import com.coderising.jvm.constant.StringInfo; -import com.coderising.jvm.constant.UTF8Info; - -public class ClassFileParser { - - public ClassFile parse(byte[] codes) { - - ClassFile clzFile = new ClassFile(); - - ByteCodeIterator iter = new ByteCodeIterator(codes); - - String magicNumber = iter.nextU4ToHexString(); - - if (!"cafebabe".equals(magicNumber)) { - return null; - } - - clzFile.setMinorVersion(iter.nextU2ToInt()); - clzFile.setMajorVersion(iter.nextU2ToInt()); - - ConstantPool pool = parseConstantPool(iter); - clzFile.setConstPool(pool); - - AccessFlag flag = parseAccessFlag(iter); - clzFile.setAccessFlag(flag); - - ClassIndex clzIndex = parseClassInfex(iter); - clzFile.setClassIndex(clzIndex); - - parseInterfaces(iter); - - return clzFile; - } - - private AccessFlag parseAccessFlag(ByteCodeIterator iter) { - - AccessFlag flag = new AccessFlag(iter.nextU2ToInt()); - // System.out.println("Is public class: " + flag.isPublicClass()); - // System.out.println("Is final class : " + flag.isFinalClass()); - - return flag; - } - - private ClassIndex parseClassInfex(ByteCodeIterator iter) { - - int thisClassIndex = iter.nextU2ToInt(); - int superClassIndex = iter.nextU2ToInt(); - - ClassIndex clzIndex = new ClassIndex(); - - clzIndex.setThisClassIndex(thisClassIndex); - clzIndex.setSuperClassIndex(superClassIndex); - - return clzIndex; - - } - - private ConstantPool parseConstantPool(ByteCodeIterator iter) { - - int constPoolCount = iter.nextU2ToInt(); - - System.out.println("Constant Pool Count :" + constPoolCount); - - ConstantPool pool = new ConstantPool(); - - pool.addConstantInfo(new NullConstantInfo()); - - for (int i = 1; i <= constPoolCount - 1; i++) { - - int tag = iter.nextU1toInt(); - - if (tag == 7) { - // Class Info - int utf8Index = iter.nextU2ToInt(); - ClassInfo clzInfo = new ClassInfo(pool); - clzInfo.setUtf8Index(utf8Index); - - pool.addConstantInfo(clzInfo); - } else if (tag == 1) { - // UTF-8 String - int len = iter.nextU2ToInt(); - byte[] data = iter.getBytes(len); - String value = null; - try { - value = new String(data, "UTF-8"); - } catch (UnsupportedEncodingException e) { - e.printStackTrace(); - } - - UTF8Info utf8Str = new UTF8Info(pool); - utf8Str.setLength(len); - utf8Str.setValue(value); - pool.addConstantInfo(utf8Str); - } else if (tag == 8) { - StringInfo info = new StringInfo(pool); - info.setIndex(iter.nextU2ToInt()); - pool.addConstantInfo(info); - } else if (tag == 9) { - FieldRefInfo field = new FieldRefInfo(pool); - field.setClassInfoIndex(iter.nextU2ToInt()); - field.setNameAndTypeIndex(iter.nextU2ToInt()); - pool.addConstantInfo(field); - } else if (tag == 10) { - // MethodRef - MethodRefInfo method = new MethodRefInfo(pool); - method.setClassInfoIndex(iter.nextU2ToInt()); - method.setNameAndTypeIndex(iter.nextU2ToInt()); - pool.addConstantInfo(method); - } else if (tag == 12) { - // Name and Type Info - NameAndTypeInfo nameType = new NameAndTypeInfo(pool); - nameType.setIndex1(iter.nextU2ToInt()); - nameType.setIndex2(iter.nextU2ToInt()); - pool.addConstantInfo(nameType); - } else { - throw new RuntimeException("the constant pool tag " + tag + " has not been implemented yet."); - } - } - - System.out.println("Finished reading Constant pool "); - - return pool; - } - - private void parseInterfaces(ByteCodeIterator iter) { - int interfaceCount = iter.nextU2ToInt(); - - System.out.println("interfaceCount:" + interfaceCount); - - // TODO : 如果实现了interface, 这里需要解析 - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java deleted file mode 100644 index 690e71a8de..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/method/Method.java +++ /dev/null @@ -1,48 +0,0 @@ -package com.coderising.jvm.method; - -import com.coderising.jvm.attr.CodeAttr; -import com.coderising.jvm.clz.ClassFile; -import com.coderising.jvm.loader.ByteCodeIterator; - -public class Method { - - private int accessFlag; - private int nameIndex; - private int descriptorIndex; - - private CodeAttr codeAttr; - - private ClassFile clzFile; - - public ClassFile getClzFile() { - return clzFile; - } - - public int getNameIndex() { - return nameIndex; - } - - public int getDescriptorIndex() { - return descriptorIndex; - } - - public CodeAttr getCodeAttr() { - return codeAttr; - } - - public void setCodeAttr(CodeAttr code) { - this.codeAttr = code; - } - - public Method(ClassFile clzFile, int accessFlag, int nameIndex, int descriptorIndex) { - this.clzFile = clzFile; - this.accessFlag = accessFlag; - this.nameIndex = nameIndex; - this.descriptorIndex = descriptorIndex; - } - - public static Method parse(ClassFile clzFile, ByteCodeIterator iter) { - return null; - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java deleted file mode 100644 index 1f9e087bb9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/jvm/util/Util.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.coderising.jvm.util; - -public class Util { - public static int byteToInt(byte[] codes) { - String s1 = byteToHexString(codes); - return Integer.valueOf(s1, 16).intValue(); - } - - public static String byteToHexString(byte[] codes) { - StringBuffer buffer = new StringBuffer(); - for (int i = 0; i < codes.length; i++) { - byte b = codes[i]; - int value = b & 0xFF; - String strHex = Integer.toHexString(value); - if (strHex.length() < 2) { - strHex = "0" + strHex; - } - buffer.append(strHex); - } - return buffer.toString(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java deleted file mode 100644 index 5f41f42c62..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/LoginAction.java +++ /dev/null @@ -1,42 +0,0 @@ -package com.coderising.litestruts; - -/** - * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 - * - * @author liuxin - * - */ -public class LoginAction { - private String name; - private String password; - private String message; - - public String getName() { - return name; - } - - public String getPassword() { - return password; - } - - public String execute() { - if ("test".equals(name) && "1234".equals(password)) { - this.message = "login successful"; - return "success"; - } - this.message = "login failed,please check your user/pwd"; - return "fail"; - } - - public void setName(String name) { - this.name = name; - } - - public void setPassword(String password) { - this.password = password; - } - - public String getMessage() { - return this.message; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java deleted file mode 100644 index 5ad5ccb352..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/Struts.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.coderising.litestruts; - -import java.util.Map; - -public class Struts { - - public static View runAction(String actionName, Map parameters) { - - /* - * - * 0. 读取配置文件struts.xml - * - * 1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) - * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , - * "password"="1234") , 那就应该调用 setName和setPassword方法 - * - * 2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success" - * - * 3. 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 - * {"message": "登录成功"} , 放到View对象的parameters - * - * 4. 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, - * 放到View对象的jsp字段中。 - * - */ - - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java deleted file mode 100644 index f1e7fcfa19..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coderising/litestruts/View.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coderising.litestruts; - -import java.util.Map; - -public class View { - private String jsp; - private Map parameters; - - public String getJsp() { - return jsp; - } - - public View setJsp(String jsp) { - this.jsp = jsp; - return this; - } - - public Map getParameters() { - return parameters; - } - - public View setParameters(Map parameters) { - this.parameters = parameters; - return this; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java deleted file mode 100644 index 835e0311d1..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayList.java +++ /dev/null @@ -1,33 +0,0 @@ -package com.coding.basic; - -public class ArrayList implements List { - - private int size = 0; - - private Object[] elementData = new Object[100]; - - public void add(Object o) { - - } - - public void add(int index, Object o) { - - } - - public Object get(int index) { - return null; - } - - public Object remove(int index) { - return null; - } - - public int size() { - return -1; - } - - public Iterator iterator() { - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java deleted file mode 100644 index ed475b9433..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/ArrayUtil.java +++ /dev/null @@ -1,96 +0,0 @@ -package com.coding.basic; - -public class ArrayUtil { - - /** - * 给定一个整形数组a , 对该数组的值进行置换 例如: a = [7, 9 , 30, 3] , 置换后为 [3, 30, 9,7] 如果 a = - * [7, 9, 30, 3, 4] , 置换后为 [4,3, 30 , 9,7] - * - * @param origin - * @return - */ - public void reverseArray(int[] origin) { - - } - - /** - * 现在有如下的一个数组: int oldArr[]={1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5} - * 要求将以上数组中值为0的项去掉,将不为0的值存入一个新的数组,生成的新数组为: {1,3,4,5,6,6,5,4,7,6,7,5} - * - * @param oldArray - * @return - */ - - public int[] removeZero(int[] oldArray) { - return null; - } - - /** - * 给定两个已经排序好的整形数组, a1和a2 , 创建一个新的数组a3, 使得a3 包含a1和a2 的所有元素, 并且仍然是有序的 例如 a1 = - * [3, 5, 7,8] a2 = [4, 5, 6,7] 则 a3 为[3,4,5,6,7,8] , 注意: 已经消除了重复 - * - * @param array1 - * @param array2 - * @return - */ - - public int[] merge(int[] array1, int[] array2) { - return null; - } - - /** - * 把一个已经存满数据的数组 oldArray的容量进行扩展, 扩展后的新数据大小为oldArray.length + size - * 注意,老数组的元素在新数组中需要保持 例如 oldArray = [2,3,6] , size = 3,则返回的新数组为 - * [2,3,6,0,0,0] - * - * @param oldArray - * @param size - * @return - */ - public int[] grow(int[] oldArray, int size) { - return null; - } - - /** - * 斐波那契数列为:1,1,2,3,5,8,13,21...... ,给定一个最大值, 返回小于该值的数列 例如, max = 15 , - * 则返回的数组应该为 [1,1,2,3,5,8,13] max = 1, 则返回空数组 [] - * - * @param max - * @return - */ - public int[] fibonacci(int max) { - return null; - } - - /** - * 返回小于给定最大值max的所有素数数组 例如max = 23, 返回的数组为[2,3,5,7,11,13,17,19] - * - * @param max - * @return - */ - public int[] getPrimes(int max) { - return null; - } - - /** - * 所谓“完数”, 是指这个数恰好等于它的因子之和,例如6=1+2+3 给定一个最大值max, 返回一个数组, 数组中是小于max 的所有完数 - * - * @param max - * @return - */ - public int[] getPerfectNumbers(int max) { - return null; - } - - /** - * 用seperator 把数组 array给连接起来 例如array= [3,8,9], seperator = "-" 则返回值为"3-8-9" - * - * @param array - * @param s - * @return - */ - public String join(int[] array, String seperator) { - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java deleted file mode 100644 index 2f944d3b91..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/BinaryTreeNode.java +++ /dev/null @@ -1,37 +0,0 @@ -package com.coding.basic; - -public class BinaryTreeNode { - - private Object data; - private BinaryTreeNode left; - private BinaryTreeNode right; - - public Object getData() { - return data; - } - - public void setData(Object data) { - this.data = data; - } - - public BinaryTreeNode getLeft() { - return left; - } - - public void setLeft(BinaryTreeNode left) { - this.left = left; - } - - public BinaryTreeNode getRight() { - return right; - } - - public void setRight(BinaryTreeNode right) { - this.right = right; - } - - public BinaryTreeNode insert(Object o) { - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java deleted file mode 100644 index f30dfc8edf..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Iterator.java +++ /dev/null @@ -1,8 +0,0 @@ -package com.coding.basic; - -public interface Iterator { - public boolean hasNext(); - - public Object next(); - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java deleted file mode 100644 index 28a3314b0d..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LRUPageFrame.java +++ /dev/null @@ -1,50 +0,0 @@ -package com.coding.basic; - -/** - * 用双向链表实现LRU算法 - * - * @author liuxin - */ -public class LRUPageFrame { - private static class Node { - Node prev; - Node next; - int pageNum; - - Node() { - } - } - - private int capacity; - private Node first;// 链表头 - private Node last;// 链表尾 - - public LRUPageFrame(int capacity) { - this.capacity = capacity; - } - - /** - * 获取缓存中对象 - * - * @param key - * @return - */ - public void access(int pageNum) { - } - - @Override - public String toString() { - StringBuilder buffer = new StringBuilder(); - Node node = first; - while (node != null) { - buffer.append(node.pageNum); - - node = node.next; - if (node != null) { - buffer.append(","); - } - } - - return buffer.toString(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java deleted file mode 100644 index 4fe91d2c95..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/LinkedList.java +++ /dev/null @@ -1,126 +0,0 @@ -package com.coding.basic; - -public class LinkedList implements List { - - private Node head; - - public void add(Object o) { - - } - - public void add(int index, Object o) { - - } - - public Object get(int index) { - return null; - } - - public Object remove(int index) { - return null; - } - - public int size() { - return -1; - } - - public void addFirst(Object o) { - - } - - public void addLast(Object o) { - - } - - public Object removeFirst() { - return null; - } - - public Object removeLast() { - return null; - } - - public Iterator iterator() { - return null; - } - - private static class Node { - Object data; - Node next; - - } - - /** - * 把该链表逆置 例如链表为 3->7->10 , 逆置后变为 10->7->3 - */ - public void reverse() { - - } - - /** - * 删除一个单链表的前半部分 例如:list = 2->5->7->8 , 删除以后的值为 7->8 如果list = 2->5->7->8->10 - * ,删除以后的值为7,8,10 - * - */ - public void removeFirstHalf() { - - } - - /** - * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 - * - * @param i - * @param length - */ - public void remove(int i, int length) { - - } - - /** - * 假定当前链表和listB均包含已升序排列的整数 从当前链表中取出那些listB所指定的元素 例如当前链表 = - * 11->101->201->301->401->501->601->701 listB = 1->3->4->6 - * 返回的结果应该是[101,301,401,601] - * - * @param list - */ - public int[] getElements(LinkedList list) { - return null; - } - - /** - * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 从当前链表中中删除在listB中出现的元素 - * - * @param list - */ - - public void subtract(LinkedList list) { - - } - - /** - * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) - */ - public void removeDuplicateValues() { - - } - - /** - * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) - * - * @param min - * @param max - */ - public void removeRange(int min, int max) { - - } - - /** - * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) - * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 - * - * @param list - */ - public LinkedList intersection(LinkedList list) { - return null; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java deleted file mode 100644 index 03fa879b2e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/List.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.coding.basic; - -public interface List { - public void add(Object o); - - public void add(int index, Object o); - - public Object get(int index); - - public Object remove(int index); - - public int size(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java deleted file mode 100644 index b2908512c5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/Queue.java +++ /dev/null @@ -1,19 +0,0 @@ -package com.coding.basic; - -public class Queue { - - public void enQueue(Object o) { - } - - public Object deQueue() { - return null; - } - - public boolean isEmpty() { - return false; - } - - public int size() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java deleted file mode 100644 index b09c9b3d91..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/Stack.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coding.basic.stack; - -import com.coding.basic.ArrayList; - -public class Stack { - private ArrayList elementData = new ArrayList(); - - public void push(Object o) { - } - - public Object pop() { - return null; - } - - public Object peek() { - return null; - } - - public boolean isEmpty() { - return false; - } - - public int size() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java deleted file mode 100644 index de35c05449..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/StackUtil.java +++ /dev/null @@ -1,54 +0,0 @@ -package com.coding.basic.stack; - -import java.util.Stack; - -public class StackUtil { - /** - * 假设栈中的元素是Integer, 从栈顶到栈底是 : 5,4,3,2,1 调用该方法后, 元素次序变为: 1,2,3,4,5 - * 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 - */ - public static void reverse(Stack s) { - } - - public static void addToBottom(Stack s, Integer value) { - if (s.isEmpty()) { - s.push(value); - } else { - Integer top = s.pop(); - addToBottom(s, value); - s.push(top); - } - } - - /** - * 删除栈中的某个元素 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 - * - * @param o - */ - public static void remove(Stack s, Object o) { - - } - - /** - * 从栈顶取得len个元素, 原来的栈中元素保持不变 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, - * 可以使用另外一个栈来辅助 - * - * @param len - * @return - */ - public static Object[] getTop(Stack s, int len) { - return null; - } - - /** - * 字符串s 可能包含这些字符: ( ) [ ] { }, a,b,c... x,yz 使用堆栈检查字符串s中的括号是不是成对出现的。 例如s = - * "([e{d}f])" , 则该字符串中的括号是成对出现, 该方法返回true 如果 s = "([b{x]y})", - * 则该字符串中的括号不是成对出现的, 该方法返回false; - * - * @param s - * @return - */ - public static boolean isValidPairs(String s) { - return false; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java deleted file mode 100644 index 4f2cf4b03a..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/java/com/coding/basic/stack/expr/InfixExpr.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.coding.basic.stack.expr; - -public class InfixExpr { - String expr = null; - - public InfixExpr(String expr) { - this.expr = expr; - } - - public float evaluate() { - return 0.0f; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml deleted file mode 100644 index ff7623e6e1..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/main/resources/struts.xml +++ /dev/null @@ -1,11 +0,0 @@ - - - - /jsp/homepage.jsp - /jsp/showLogin.jsp - - - /jsp/welcome.jsp - /jsp/error.jsp - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java deleted file mode 100644 index 8e171cff93..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/download/core/FileDownloaderTest.java +++ /dev/null @@ -1,56 +0,0 @@ -package com.coderising.download.core; - -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://localhost:8080/test.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/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java deleted file mode 100644 index 6b78de3ddc..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/ClassFileloaderTest.java +++ /dev/null @@ -1,248 +0,0 @@ -package com.coderising.jvm.loader; - -import java.util.List; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -import com.coderising.jvm.clz.ClassFile; -import com.coderising.jvm.clz.ClassIndex; -import com.coderising.jvm.constant.ClassInfo; -import com.coderising.jvm.constant.ConstantPool; -import com.coderising.jvm.constant.MethodRefInfo; -import com.coderising.jvm.constant.NameAndTypeInfo; -import com.coderising.jvm.constant.UTF8Info; -import com.coderising.jvm.field.Field; -import com.coderising.jvm.method.Method; - -public class ClassFileloaderTest { - private static final String FULL_QUALIFIED_CLASS_NAME = "com/coderising/jvm/test/EmployeeV1"; - - static String path1 = "C:\\Users\\liuxin\\git\\coding2017\\liuxin\\mini-jvm\\bin"; - static String path2 = "C:\temp"; - - static ClassFile clzFile = null; - static { - ClassFileLoader loader = new ClassFileLoader(); - loader.addClassPath(path1); - String className = "com.coderising.jvm.test.EmployeeV1"; - - clzFile = loader.loadClass(className); - clzFile.print(); - } - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testClassPath() { - - ClassFileLoader loader = new ClassFileLoader(); - loader.addClassPath(path1); - loader.addClassPath(path2); - - String clzPath = loader.getClassPath(); - - Assert.assertEquals(path1 + ";" + path2, clzPath); - - } - - @Test - public void testClassFileLength() { - - ClassFileLoader loader = new ClassFileLoader(); - loader.addClassPath(path1); - - String className = "com.coderising.jvm.test.EmployeeV1"; - - byte[] byteCodes = loader.readBinaryCode(className); - - // 注意:这个字节数可能和你的JVM版本有关系, 你可以看看编译好的类到底有多大 - Assert.assertEquals(1056, byteCodes.length); - - } - - @Test - public void testMagicNumber() { - ClassFileLoader loader = new ClassFileLoader(); - loader.addClassPath(path1); - String className = "com.coderising.jvm.test.EmployeeV1"; - byte[] byteCodes = loader.readBinaryCode(className); - byte[] codes = new byte[] { byteCodes[0], byteCodes[1], byteCodes[2], byteCodes[3] }; - - String acctualValue = this.byteToHexString(codes); - - Assert.assertEquals("cafebabe", acctualValue); - } - - private String byteToHexString(byte[] codes) { - StringBuffer buffer = new StringBuffer(); - for (int i = 0; i < codes.length; i++) { - byte b = codes[i]; - int value = b & 0xFF; - String strHex = Integer.toHexString(value); - if (strHex.length() < 2) { - strHex = "0" + strHex; - } - buffer.append(strHex); - } - return buffer.toString(); - } - - /** - * ---------------------------------------------------------------------- - */ - - @Test - public void testVersion() { - - Assert.assertEquals(0, clzFile.getMinorVersion()); - Assert.assertEquals(52, clzFile.getMajorVersion()); - - } - - @Test - public void testConstantPool() { - - ConstantPool pool = clzFile.getConstantPool(); - - Assert.assertEquals(53, pool.getSize()); - - { - ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(1); - Assert.assertEquals(2, clzInfo.getUtf8Index()); - - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(2); - Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, utf8Info.getValue()); - } - { - ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(3); - Assert.assertEquals(4, clzInfo.getUtf8Index()); - - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(4); - Assert.assertEquals("java/lang/Object", utf8Info.getValue()); - } - { - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(5); - Assert.assertEquals("name", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(6); - Assert.assertEquals("Ljava/lang/String;", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(7); - Assert.assertEquals("age", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(8); - Assert.assertEquals("I", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(9); - Assert.assertEquals("", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(10); - Assert.assertEquals("(Ljava/lang/String;I)V", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(11); - Assert.assertEquals("Code", utf8Info.getValue()); - } - - { - MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(12); - Assert.assertEquals(3, methodRef.getClassInfoIndex()); - Assert.assertEquals(13, methodRef.getNameAndTypeIndex()); - } - - { - NameAndTypeInfo nameAndType = (NameAndTypeInfo) pool.getConstantInfo(13); - Assert.assertEquals(9, nameAndType.getIndex1()); - Assert.assertEquals(14, nameAndType.getIndex2()); - } - // 抽查几个吧 - { - MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(45); - Assert.assertEquals(1, methodRef.getClassInfoIndex()); - Assert.assertEquals(46, methodRef.getNameAndTypeIndex()); - } - - { - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(53); - Assert.assertEquals("EmployeeV1.java", utf8Info.getValue()); - } - } - - @Test - public void testClassIndex() { - - ClassIndex clzIndex = clzFile.getClzIndex(); - ClassInfo thisClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getThisClassIndex()); - ClassInfo superClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getSuperClassIndex()); - - Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, thisClassInfo.getClassName()); - Assert.assertEquals("java/lang/Object", superClassInfo.getClassName()); - } - - /** - * 下面是第三次JVM课应实现的测试用例 - */ - @Test - public void testReadFields() { - - List fields = clzFile.getFields(); - Assert.assertEquals(2, fields.size()); - { - Field f = fields.get(0); - Assert.assertEquals("name:Ljava/lang/String;", f.toString()); - } - { - Field f = fields.get(1); - Assert.assertEquals("age:I", f.toString()); - } - } - - @Test - public void testMethods() { - - List methods = clzFile.getMethods(); - ConstantPool pool = clzFile.getConstantPool(); - - { - Method m = methods.get(0); - assertMethodEquals(pool, m, "", "(Ljava/lang/String;I)V", "2ab7000c2a2bb5000f2a1cb50011b1"); - - } - { - Method m = methods.get(1); - assertMethodEquals(pool, m, "setName", "(Ljava/lang/String;)V", "2a2bb5000fb1"); - - } - { - Method m = methods.get(2); - assertMethodEquals(pool, m, "setAge", "(I)V", "2a1bb50011b1"); - } - { - Method m = methods.get(3); - assertMethodEquals(pool, m, "sayHello", "()V", "b2001c1222b60024b1"); - - } - { - Method m = methods.get(4); - assertMethodEquals(pool, m, "main", "([Ljava/lang/String;)V", "bb000159122b101db7002d4c2bb6002fb1"); - } - } - - private void assertMethodEquals(ConstantPool pool, Method m, String expectedName, String expectedDesc, - String expectedCode) { - String methodName = pool.getUTF8String(m.getNameIndex()); - String methodDesc = pool.getUTF8String(m.getDescriptorIndex()); - String code = m.getCodeAttr().getCode(); - Assert.assertEquals(expectedName, methodName); - Assert.assertEquals(expectedDesc, methodDesc); - Assert.assertEquals(expectedCode, code); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java deleted file mode 100644 index 2b80092ecb..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/jvm/loader/EmployeeV1.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.coderising.jvm.loader; - -public class EmployeeV1 { - - private String name; - private int age; - - public EmployeeV1(String name, int age) { - this.name = name; - this.age = age; - } - - public void setName(String name) { - this.name = name; - } - - public void setAge(int age) { - this.age = age; - } - - public void sayHello() { - System.out.println("Hello , this is class Employee "); - } - - public static void main(String[] args) { - EmployeeV1 p = new EmployeeV1("Andy", 29); - p.sayHello(); - - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java deleted file mode 100644 index f2426db6ea..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coderising/litestruts/StrutsTest.java +++ /dev/null @@ -1,38 +0,0 @@ -package com.coderising.litestruts; - -import java.util.HashMap; -import java.util.Map; - -import org.junit.Assert; -import org.junit.Test; - -public class StrutsTest { - - @Test - public void testLoginActionSuccess() { - - String actionName = "login"; - - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "1234"); - - View view = Struts.runAction(actionName, params); - - Assert.assertEquals("/jsp/homepage.jsp", view.getJsp()); - Assert.assertEquals("login successful", view.getParameters().get("message")); - } - - @Test - public void testLoginActionFailed() { - String actionName = "login"; - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "123456"); // 密码和预设的不一致 - - View view = Struts.runAction(actionName, params); - - Assert.assertEquals("/jsp/showLogin.jsp", view.getJsp()); - Assert.assertEquals("login failed,please check your user/pwd", view.getParameters().get("message")); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java deleted file mode 100644 index bc139cbe2d..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/LRUPageFrameTest.java +++ /dev/null @@ -1,27 +0,0 @@ -package com.coding.basic; - -import org.junit.Assert; -import org.junit.Test; - -public class LRUPageFrameTest { - @Test - public void testAccess() { - LRUPageFrame frame = new LRUPageFrame(3); - frame.access(7); - frame.access(0); - frame.access(1); - Assert.assertEquals("1,0,7", frame.toString()); - frame.access(2); - Assert.assertEquals("2,1,0", frame.toString()); - frame.access(0); - Assert.assertEquals("0,2,1", frame.toString()); - frame.access(0); - Assert.assertEquals("0,2,1", frame.toString()); - frame.access(3); - Assert.assertEquals("3,0,2", frame.toString()); - frame.access(0); - Assert.assertEquals("0,3,2", frame.toString()); - frame.access(4); - Assert.assertEquals("4,0,3", frame.toString()); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java deleted file mode 100644 index 5976823f36..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/StackUtilTest.java +++ /dev/null @@ -1,78 +0,0 @@ -package com.coding.basic.stack; - -import java.util.Stack; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class StackUtilTest { - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testAddToBottom() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - - StackUtil.addToBottom(s, 0); - - Assert.assertEquals("[0, 1, 2, 3]", s.toString()); - - } - - @Test - public void testReverse() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - s.push(4); - s.push(5); - Assert.assertEquals("[1, 2, 3, 4, 5]", s.toString()); - StackUtil.reverse(s); - Assert.assertEquals("[5, 4, 3, 2, 1]", s.toString()); - } - - @Test - public void testRemove() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - StackUtil.remove(s, 2); - Assert.assertEquals("[1, 3]", s.toString()); - } - - @Test - public void testGetTop() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - s.push(4); - s.push(5); - { - Object[] values = StackUtil.getTop(s, 3); - Assert.assertEquals(5, values[0]); - Assert.assertEquals(4, values[1]); - Assert.assertEquals(3, values[2]); - } - } - - @Test - public void testIsValidPairs() { - Assert.assertTrue(StackUtil.isValidPairs("([e{d}f])")); - Assert.assertFalse(StackUtil.isValidPairs("([b{x]y})")); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java deleted file mode 100644 index 2f03b3ac9a..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/java/com/coding/basic/stack/expr/InfixExprTest.java +++ /dev/null @@ -1,45 +0,0 @@ -package com.coding.basic.stack.expr; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class InfixExprTest { - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testEvaluate() { - // InfixExpr expr = new InfixExpr("300*20+12*5-20/4"); - { - InfixExpr expr = new InfixExpr("2+3*4+5"); - Assert.assertEquals(19.0, expr.evaluate(), 0.001f); - } - { - InfixExpr expr = new InfixExpr("3*20+12*5-40/2"); - Assert.assertEquals(100.0, expr.evaluate(), 0.001f); - } - - { - InfixExpr expr = new InfixExpr("3*20/2"); - Assert.assertEquals(30, expr.evaluate(), 0.001f); - } - - { - InfixExpr expr = new InfixExpr("20/2*3"); - Assert.assertEquals(30, expr.evaluate(), 0.001f); - } - - { - InfixExpr expr = new InfixExpr("10-30+50"); - Assert.assertEquals(30, expr.evaluate(), 0.001f); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-51-liuxin-question/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml deleted file mode 100644 index 80266b31de..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/pom.xml +++ /dev/null @@ -1,31 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-52-liuxin-answer - eulerlcs master java road copy from liuxin answer - - - - org.jdom - jdom2 - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java deleted file mode 100644 index 76dc0f3a40..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/Connection.java +++ /dev/null @@ -1,28 +0,0 @@ -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/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java deleted file mode 100644 index 4666b77756..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionException.java +++ /dev/null @@ -1,8 +0,0 @@ -package com.coderising.download.api; - -public class ConnectionException extends Exception { - public ConnectionException(Exception e) { - super(e); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java deleted file mode 100644 index 787984f170..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/ConnectionManager.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.coderising.download.api; - -public interface ConnectionManager { - /** - * 给定一个url , 打开一个连接 - * - * @param url - * @return - */ - public Connection open(String url) throws ConnectionException; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java deleted file mode 100644 index bf9807b307..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/api/DownloadListener.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.coderising.download.api; - -public interface DownloadListener { - public void notifyFinished(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java deleted file mode 100644 index faf849d975..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/DownloadThread.java +++ /dev/null @@ -1,50 +0,0 @@ -package com.coderising.download.core; - -import java.io.RandomAccessFile; -import java.util.concurrent.CyclicBarrier; - -import com.coderising.download.api.Connection; - -public class DownloadThread extends Thread { - - Connection conn; - int startPos; - int endPos; - CyclicBarrier barrier; - String localFile; - - public DownloadThread(Connection conn, int startPos, int endPos, String localFile, CyclicBarrier barrier) { - - this.conn = conn; - this.startPos = startPos; - this.endPos = endPos; - this.localFile = localFile; - this.barrier = barrier; - } - - public void run() { - - try { - System.out.println("Begin to read [" + startPos + "-" + endPos + "]"); - - byte[] data = conn.read(startPos, endPos); - - RandomAccessFile file = new RandomAccessFile(localFile, "rw"); - - file.seek(startPos); - - file.write(data); - - file.close(); - - conn.close(); - - barrier.await(); // 等待别的线程完成 - - } catch (Exception e) { - e.printStackTrace(); - - } - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java deleted file mode 100644 index b5831a72bd..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/core/FileDownloader.java +++ /dev/null @@ -1,126 +0,0 @@ -package com.coderising.download.core; - -import java.io.IOException; -import java.io.RandomAccessFile; -import java.util.concurrent.CyclicBarrier; - -import com.coderising.download.api.Connection; -import com.coderising.download.api.ConnectionManager; -import com.coderising.download.api.DownloadListener; - -public class FileDownloader { - - private String url; - private String localFile; - - DownloadListener listener; - - ConnectionManager cm; - - private static final int DOWNLOAD_TRHEAD_NUM = 3; - - public FileDownloader(String _url, String localFile) { - this.url = _url; - this.localFile = localFile; - - } - - 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方法 - - // 下面的代码是示例代码, 也就是说只有一个线程, 你需要改造成多线程的。 - - CyclicBarrier barrier = new CyclicBarrier(DOWNLOAD_TRHEAD_NUM, new Runnable() { - public void run() { - listener.notifyFinished(); - } - }); - - Connection conn = null; - try { - - conn = cm.open(this.url); - - int length = conn.getContentLength(); - - createPlaceHolderFile(this.localFile, length); - - int[][] ranges = allocateDownloadRange(DOWNLOAD_TRHEAD_NUM, length); - - for (int i = 0; i < DOWNLOAD_TRHEAD_NUM; i++) { - - DownloadThread thread = new DownloadThread(cm.open(url), ranges[i][0], ranges[i][1], localFile, - barrier); - - thread.start(); - } - - } catch (Exception e) { - e.printStackTrace(); - } finally { - if (conn != null) { - conn.close(); - } - } - - } - - private void createPlaceHolderFile(String fileName, int contentLen) throws IOException { - - RandomAccessFile file = new RandomAccessFile(fileName, "rw"); - - for (int i = 0; i < contentLen; i++) { - file.write(0); - } - - file.close(); - } - - private int[][] allocateDownloadRange(int threadNum, int contentLen) { - int[][] ranges = new int[threadNum][2]; - - int eachThreadSize = contentLen / threadNum;// 每个线程需要下载的文件大小 - int left = contentLen % threadNum;// 剩下的归最后一个线程来处理 - - for (int i = 0; i < threadNum; i++) { - - int startPos = i * eachThreadSize; - - int endPos = (i + 1) * eachThreadSize - 1; - - if ((i == (threadNum - 1))) { - endPos += left; - } - ranges[i][0] = startPos; - ranges[i][1] = endPos; - - } - - return ranges; - } - - 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/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java deleted file mode 100644 index d1aa121f75..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionImpl.java +++ /dev/null @@ -1,84 +0,0 @@ -package com.coderising.download.impl; - -import java.io.ByteArrayOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.net.HttpURLConnection; -import java.net.MalformedURLException; -import java.net.URL; -import java.net.URLConnection; -import java.util.Arrays; - -import com.coderising.download.api.Connection; -import com.coderising.download.api.ConnectionException; - -class ConnectionImpl implements Connection { - - URL url; - static final int BUFFER_SIZE = 1024; - - ConnectionImpl(String _url) throws ConnectionException { - try { - url = new URL(_url); - } catch (MalformedURLException e) { - throw new ConnectionException(e); - } - } - - @Override - public byte[] read(int startPos, int endPos) throws IOException { - - HttpURLConnection httpConn = (HttpURLConnection) url.openConnection(); - - httpConn.setRequestProperty("Range", "bytes=" + startPos + "-" + endPos); - - InputStream is = httpConn.getInputStream(); - - // is.skip(startPos); - - byte[] buff = new byte[BUFFER_SIZE]; - - int totalLen = endPos - startPos + 1; - - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - - while (baos.size() < totalLen) { - - int len = is.read(buff); - if (len < 0) { - break; - } - baos.write(buff, 0, len); - } - - if (baos.size() > totalLen) { - byte[] data = baos.toByteArray(); - return Arrays.copyOf(data, totalLen); - } - - return baos.toByteArray(); - } - - @Override - public int getContentLength() { - - URLConnection con; - try { - con = url.openConnection(); - - return con.getContentLength(); - - } catch (IOException e) { - e.printStackTrace(); - } - - return -1; - - } - - @Override - public void close() { - - } - -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java deleted file mode 100644 index 5e98063eaa..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/download/impl/ConnectionManagerImpl.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.coderising.download.impl; - -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 { - - return new ConnectionImpl(url); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java deleted file mode 100644 index 5b0f60c148..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Configuration.java +++ /dev/null @@ -1,113 +0,0 @@ -package com.coderising.litestruts; - -import java.io.IOException; -import java.io.InputStream; -import java.util.HashMap; -import java.util.Map; - -import org.jdom2.Document; -import org.jdom2.Element; -import org.jdom2.JDOMException; -import org.jdom2.input.SAXBuilder; - -public class Configuration { - - Map actions = new HashMap<>(); - - public Configuration(String fileName) { - - String packageName = this.getClass().getPackage().getName(); - - packageName = packageName.replace('.', '/'); - - InputStream is = this.getClass().getResourceAsStream("/" + packageName + "/" + fileName); - - parseXML(is); - - try { - is.close(); - } catch (IOException e) { - throw new ConfigurationException(e); - } - } - - private void parseXML(InputStream is) { - - SAXBuilder builder = new SAXBuilder(); - - try { - - Document doc = builder.build(is); - - Element root = doc.getRootElement(); - - for (Element actionElement : root.getChildren("action")) { - - String actionName = actionElement.getAttributeValue("name"); - String clzName = actionElement.getAttributeValue("class"); - - ActionConfig ac = new ActionConfig(actionName, clzName); - - for (Element resultElement : actionElement.getChildren("result")) { - - String resultName = resultElement.getAttributeValue("name"); - String viewName = resultElement.getText().trim(); - - ac.addViewResult(resultName, viewName); - - } - - this.actions.put(actionName, ac); - } - - } catch (JDOMException e) { - throw new ConfigurationException(e); - - } catch (IOException e) { - throw new ConfigurationException(e); - - } - - } - - public String getClassName(String action) { - ActionConfig ac = this.actions.get(action); - if (ac == null) { - return null; - } - return ac.getClassName(); - } - - public String getResultView(String action, String resultName) { - ActionConfig ac = this.actions.get(action); - if (ac == null) { - return null; - } - return ac.getViewName(resultName); - } - - private static class ActionConfig { - - String name; - String clzName; - Map viewResult = new HashMap<>(); - - public ActionConfig(String actionName, String clzName) { - this.name = actionName; - this.clzName = clzName; - } - - public String getClassName() { - return clzName; - } - - public void addViewResult(String name, String viewName) { - viewResult.put(name, viewName); - } - - public String getViewName(String resultName) { - return viewResult.get(resultName); - } - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java deleted file mode 100644 index 97e286827f..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ConfigurationException.java +++ /dev/null @@ -1,21 +0,0 @@ -package com.coderising.litestruts; - -import java.io.IOException; - -import org.jdom2.JDOMException; - -public class ConfigurationException extends RuntimeException { - - public ConfigurationException(String msg) { - super(msg); - } - - public ConfigurationException(JDOMException e) { - super(e); - } - - public ConfigurationException(IOException e) { - super(e); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java deleted file mode 100644 index 5f41f42c62..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/LoginAction.java +++ /dev/null @@ -1,42 +0,0 @@ -package com.coderising.litestruts; - -/** - * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 - * - * @author liuxin - * - */ -public class LoginAction { - private String name; - private String password; - private String message; - - public String getName() { - return name; - } - - public String getPassword() { - return password; - } - - public String execute() { - if ("test".equals(name) && "1234".equals(password)) { - this.message = "login successful"; - return "success"; - } - this.message = "login failed,please check your user/pwd"; - return "fail"; - } - - public void setName(String name) { - this.name = name; - } - - public void setPassword(String password) { - this.password = password; - } - - public String getMessage() { - return this.message; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java deleted file mode 100644 index 1ba13d5245..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/ReflectionUtil.java +++ /dev/null @@ -1,120 +0,0 @@ -package com.coderising.litestruts; - -import java.lang.reflect.InvocationTargetException; -import java.lang.reflect.Method; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -public class ReflectionUtil { - - public static List getSetterMethods(Class clz) { - - return getMethods(clz, "set"); - - } - - public static void setParameters(Object o, Map params) { - - List methods = getSetterMethods(o.getClass()); - - for (String name : params.keySet()) { - - String methodName = "set" + name; - - for (Method m : methods) { - - if (m.getName().equalsIgnoreCase(methodName)) { - try { - m.invoke(o, params.get(name)); - } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { - e.printStackTrace(); - } - } - } - } - - } - - public static List getGetterMethods(Class clz) { - return getMethods(clz, "get"); - } - - private static List getMethods(Class clz, String startWithName) { - - List methods = new ArrayList<>(); - - for (Method m : clz.getDeclaredMethods()) { - - if (m.getName().startsWith(startWithName)) { - - methods.add(m); - - } - - } - - return methods; - } - - public static Map getParamterMap(Object o) { - - Map params = new HashMap<>(); - - List methods = getGetterMethods(o.getClass()); - - for (Method m : methods) { - - String methodName = m.getName(); - String name = methodName.replaceFirst("get", "").toLowerCase(); - try { - Object value = m.invoke(o); - params.put(name, value); - } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { - - e.printStackTrace(); - } - } - - return params; - } - - //////////////////////// Backup /////////////////////////////////// - - public static List getGetterMethods_V1(Class clz) { - - List methods = new ArrayList<>(); - - for (Method m : clz.getDeclaredMethods()) { - - if (m.getName().startsWith("get")) { - - methods.add(m); - - } - - } - - return methods; - } - - public static List getSetterMethods_V1(Class clz) { - - List methods = new ArrayList<>(); - - for (Method m : clz.getDeclaredMethods()) { - - if (m.getName().startsWith("set")) { - - methods.add(m); - - } - - } - - return methods; - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java deleted file mode 100644 index b3fe556ebc..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/Struts.java +++ /dev/null @@ -1,56 +0,0 @@ -package com.coderising.litestruts; - -import java.lang.reflect.Method; -import java.util.Map; - -public class Struts { - private final static Configuration cfg = new Configuration("struts.xml"); - - public static View runAction(String actionName, Map parameters) { - /* - * - * 0. 读取配置文件struts.xml - * - * 1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) - * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , - * "password"="1234") , 那就应该调用 setName和setPassword方法 - * - * 2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success" - * - * 3. 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 - * {"message": "登录成功"} , 放到View对象的parameters - * - * 4. 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, - * 放到View对象的jsp字段中。 - * - */ - - String clzName = cfg.getClassName(actionName); - - if (clzName == null) { - return null; - } - - try { - Class clz = Class.forName(clzName); - Object action = clz.newInstance(); - - ReflectionUtil.setParameters(action, parameters); - - Method m = clz.getDeclaredMethod("execute"); - String resultName = (String) m.invoke(action); - - Map params = ReflectionUtil.getParamterMap(action); - String resultView = cfg.getResultView(actionName, resultName); - View view = new View(); - view.setParameters(params); - view.setJsp(resultView); - return view; - - } catch (Exception e) { - e.printStackTrace(); - } - - return null; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java deleted file mode 100644 index f1e7fcfa19..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coderising/litestruts/View.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coderising.litestruts; - -import java.util.Map; - -public class View { - private String jsp; - private Map parameters; - - public String getJsp() { - return jsp; - } - - public View setJsp(String jsp) { - this.jsp = jsp; - return this; - } - - public Map getParameters() { - return parameters; - } - - public View setParameters(Map parameters) { - this.parameters = parameters; - return this; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java deleted file mode 100644 index 2f944d3b91..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/BinaryTreeNode.java +++ /dev/null @@ -1,37 +0,0 @@ -package com.coding.basic; - -public class BinaryTreeNode { - - private Object data; - private BinaryTreeNode left; - private BinaryTreeNode right; - - public Object getData() { - return data; - } - - public void setData(Object data) { - this.data = data; - } - - public BinaryTreeNode getLeft() { - return left; - } - - public void setLeft(BinaryTreeNode left) { - this.left = left; - } - - public BinaryTreeNode getRight() { - return right; - } - - public void setRight(BinaryTreeNode right) { - this.right = right; - } - - public BinaryTreeNode insert(Object o) { - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java deleted file mode 100644 index f30dfc8edf..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Iterator.java +++ /dev/null @@ -1,8 +0,0 @@ -package com.coding.basic; - -public interface Iterator { - public boolean hasNext(); - - public Object next(); - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java deleted file mode 100644 index 03fa879b2e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/List.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.coding.basic; - -public interface List { - public void add(Object o); - - public void add(int index, Object o); - - public Object get(int index); - - public Object remove(int index); - - public int size(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java deleted file mode 100644 index b2908512c5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/Queue.java +++ /dev/null @@ -1,19 +0,0 @@ -package com.coding.basic; - -public class Queue { - - public void enQueue(Object o) { - } - - public Object deQueue() { - return null; - } - - public boolean isEmpty() { - return false; - } - - public int size() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java deleted file mode 100644 index 81dfe5bdfe..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayList.java +++ /dev/null @@ -1,36 +0,0 @@ -package com.coding.basic.array; - -import com.coding.basic.Iterator; -import com.coding.basic.List; - -public class ArrayList implements List { - - private int size = 0; - - private Object[] elementData = new Object[100]; - - public void add(Object o) { - - } - - public void add(int index, Object o) { - - } - - public Object get(int index) { - return null; - } - - public Object remove(int index) { - return null; - } - - public int size() { - return -1; - } - - public Iterator iterator() { - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java deleted file mode 100644 index 0e8e077db7..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/array/ArrayUtil.java +++ /dev/null @@ -1,96 +0,0 @@ -package com.coding.basic.array; - -public class ArrayUtil { - - /** - * 给定一个整形数组a , 对该数组的值进行置换 例如: a = [7, 9 , 30, 3] , 置换后为 [3, 30, 9,7] 如果 a = - * [7, 9, 30, 3, 4] , 置换后为 [4,3, 30 , 9,7] - * - * @param origin - * @return - */ - public void reverseArray(int[] origin) { - - } - - /** - * 现在有如下的一个数组: int oldArr[]={1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5} - * 要求将以上数组中值为0的项去掉,将不为0的值存入一个新的数组,生成的新数组为: {1,3,4,5,6,6,5,4,7,6,7,5} - * - * @param oldArray - * @return - */ - - public int[] removeZero(int[] oldArray) { - return null; - } - - /** - * 给定两个已经排序好的整形数组, a1和a2 , 创建一个新的数组a3, 使得a3 包含a1和a2 的所有元素, 并且仍然是有序的 例如 a1 = - * [3, 5, 7,8] a2 = [4, 5, 6,7] 则 a3 为[3,4,5,6,7,8] , 注意: 已经消除了重复 - * - * @param array1 - * @param array2 - * @return - */ - - public int[] merge(int[] array1, int[] array2) { - return null; - } - - /** - * 把一个已经存满数据的数组 oldArray的容量进行扩展, 扩展后的新数据大小为oldArray.length + size - * 注意,老数组的元素在新数组中需要保持 例如 oldArray = [2,3,6] , size = 3,则返回的新数组为 - * [2,3,6,0,0,0] - * - * @param oldArray - * @param size - * @return - */ - public int[] grow(int[] oldArray, int size) { - return null; - } - - /** - * 斐波那契数列为:1,1,2,3,5,8,13,21...... ,给定一个最大值, 返回小于该值的数列 例如, max = 15 , - * 则返回的数组应该为 [1,1,2,3,5,8,13] max = 1, 则返回空数组 [] - * - * @param max - * @return - */ - public int[] fibonacci(int max) { - return null; - } - - /** - * 返回小于给定最大值max的所有素数数组 例如max = 23, 返回的数组为[2,3,5,7,11,13,17,19] - * - * @param max - * @return - */ - public int[] getPrimes(int max) { - return null; - } - - /** - * 所谓“完数”, 是指这个数恰好等于它的因子之和,例如6=1+2+3 给定一个最大值max, 返回一个数组, 数组中是小于max 的所有完数 - * - * @param max - * @return - */ - public int[] getPerfectNumbers(int max) { - return null; - } - - /** - * 用seperator 把数组 array给连接起来 例如array= [3,8,9], seperator = "-" 则返回值为"3-8-9" - * - * @param array - * @param s - * @return - */ - public String join(int[] array, String seperator) { - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java deleted file mode 100644 index 305989d5de..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LRUPageFrame.java +++ /dev/null @@ -1,151 +0,0 @@ -package com.coding.basic.linklist; - -public class LRUPageFrame { - - private static class Node { - - Node prev; - Node next; - int pageNum; - - Node() { - } - } - - private int capacity; - - private int currentSize; - private Node first;// 链表头 - private Node last;// 链表尾 - - public LRUPageFrame(int capacity) { - this.currentSize = 0; - this.capacity = capacity; - - } - - /** - * 获取缓存中对象 - * - * @param key - * @return - */ - public void access(int pageNum) { - - Node node = find(pageNum); - // 在该队列中存在, 则提到队列头 - if (node != null) { - - moveExistingNodeToHead(node); - - } else { - - node = new Node(); - node.pageNum = pageNum; - - // 缓存容器是否已经超过大小. - if (currentSize >= capacity) { - removeLast(); - - } - - addNewNodetoHead(node); - - } - } - - private void addNewNodetoHead(Node node) { - - if (isEmpty()) { - - node.prev = null; - node.next = null; - first = node; - last = node; - - } else { - node.prev = null; - node.next = first; - first.prev = node; - first = node; - } - this.currentSize++; - } - - private Node find(int data) { - - Node node = first; - while (node != null) { - if (node.pageNum == data) { - return node; - } - node = node.next; - } - return null; - - } - - /** - * 删除链表尾部节点 表示 删除最少使用的缓存对象 - */ - private void removeLast() { - Node prev = last.prev; - prev.next = null; - last.prev = null; - last = prev; - this.currentSize--; - } - - /** - * 移动到链表头,表示这个节点是最新使用过的 - * - * @param node - */ - private void moveExistingNodeToHead(Node node) { - - if (node == first) { - - return; - } else if (node == last) { - // 当前节点是链表尾, 需要放到链表头 - Node prevNode = node.prev; - prevNode.next = null; - last.prev = null; - last = prevNode; - - } else { - // node 在链表的中间, 把node 的前后节点连接起来 - Node prevNode = node.prev; - prevNode.next = node.next; - - Node nextNode = node.next; - nextNode.prev = prevNode; - - } - - node.prev = null; - node.next = first; - first.prev = node; - first = node; - - } - - private boolean isEmpty() { - return (first == null) && (last == null); - } - - public String toString() { - StringBuilder buffer = new StringBuilder(); - Node node = first; - while (node != null) { - buffer.append(node.pageNum); - - node = node.next; - if (node != null) { - buffer.append(","); - } - } - return buffer.toString(); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java deleted file mode 100644 index 6c8b4a3315..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/linklist/LinkedList.java +++ /dev/null @@ -1,129 +0,0 @@ -package com.coding.basic.linklist; - -import com.coding.basic.Iterator; -import com.coding.basic.List; - -public class LinkedList implements List { - - private Node head; - - public void add(Object o) { - - } - - public void add(int index, Object o) { - - } - - public Object get(int index) { - return null; - } - - public Object remove(int index) { - return null; - } - - public int size() { - return -1; - } - - public void addFirst(Object o) { - - } - - public void addLast(Object o) { - - } - - public Object removeFirst() { - return null; - } - - public Object removeLast() { - return null; - } - - public Iterator iterator() { - return null; - } - - private static class Node { - Object data; - Node next; - - } - - /** - * 把该链表逆置 例如链表为 3->7->10 , 逆置后变为 10->7->3 - */ - public void reverse() { - - } - - /** - * 删除一个单链表的前半部分 例如:list = 2->5->7->8 , 删除以后的值为 7->8 如果list = 2->5->7->8->10 - * ,删除以后的值为7,8,10 - * - */ - public void removeFirstHalf() { - - } - - /** - * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 - * - * @param i - * @param length - */ - public void remove(int i, int length) { - - } - - /** - * 假定当前链表和listB均包含已升序排列的整数 从当前链表中取出那些listB所指定的元素 例如当前链表 = - * 11->101->201->301->401->501->601->701 listB = 1->3->4->6 - * 返回的结果应该是[101,301,401,601] - * - * @param list - */ - public int[] getElements(LinkedList list) { - return null; - } - - /** - * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 从当前链表中中删除在listB中出现的元素 - * - * @param list - */ - - public void subtract(LinkedList list) { - - } - - /** - * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) - */ - public void removeDuplicateValues() { - - } - - /** - * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) - * - * @param min - * @param max - */ - public void removeRange(int min, int max) { - - } - - /** - * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) - * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 - * - * @param list - */ - public LinkedList intersection(LinkedList list) { - return null; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java deleted file mode 100644 index 83b76cb872..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/Stack.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.coding.basic.stack; - -import com.coding.basic.array.ArrayList; - -public class Stack { - private ArrayList elementData = new ArrayList(); - - public void push(Object o) { - } - - public Object pop() { - return null; - } - - public Object peek() { - return null; - } - - public boolean isEmpty() { - return false; - } - - public int size() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java deleted file mode 100644 index 100bfc46a9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/StackUtil.java +++ /dev/null @@ -1,140 +0,0 @@ -package com.coding.basic.stack; - -import java.util.Stack; - -public class StackUtil { - - public static void bad_reverse(Stack s) { - if (s == null || s.isEmpty()) { - return; - } - Stack tmpStack = new Stack(); - while (!s.isEmpty()) { - tmpStack.push(s.pop()); - } - - s = tmpStack; - - } - - /** - * 假设栈中的元素是Integer, 从栈顶到栈底是 : 5,4,3,2,1 调用该方法后, 元素次序变为: 1,2,3,4,5 - * 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 - */ - public static void reverse(Stack s) { - if (s == null || s.isEmpty()) { - return; - } - Integer top = s.pop(); - reverse(s); - addToBottom(s, top); - - } - - public static void addToBottom(Stack s, Integer value) { - if (s.isEmpty()) { - s.push(value); - } else { - Integer top = s.pop(); - addToBottom(s, value); - s.push(top); - } - - } - - /** - * 删除栈中的某个元素 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 - * - * @param o - */ - public static void remove(Stack s, Object o) { - if (s == null || s.isEmpty()) { - return; - } - Stack tmpStack = new Stack(); - - while (!s.isEmpty()) { - Object value = s.pop(); - if (!value.equals(o)) { - tmpStack.push(value); - } - } - - while (!tmpStack.isEmpty()) { - s.push(tmpStack.pop()); - } - } - - /** - * 从栈顶取得len个元素, 原来的栈中元素保持不变 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, - * 可以使用另外一个栈来辅助 - * - * @param len - * @return - */ - public static Object[] getTop(Stack s, int len) { - - if (s == null || s.isEmpty() || s.size() < len || len <= 0) { - return null; - } - - Stack tmpStack = new Stack(); - int i = 0; - Object[] result = new Object[len]; - while (!s.isEmpty()) { - Object value = s.pop(); - tmpStack.push(value); - result[i++] = value; - if (i == len) { - break; - } - } - - return result; - } - - /** - * 字符串s 可能包含这些字符: ( ) [ ] { }, a,b,c... x,yz 使用堆栈检查字符串s中的括号是不是成对出现的。 例如s = - * "([e{d}f])" , 则该字符串中的括号是成对出现, 该方法返回true 如果 s = "([b{x]y})", - * 则该字符串中的括号不是成对出现的, 该方法返回false; - * - * @param s - * @return - */ - public static boolean isValidPairs(String s) { - - Stack stack = new Stack(); - for (int i = 0; i < s.length(); i++) { - char c = s.charAt(i); - - if (c == '(' || c == '[' || c == '{') { - - stack.push(c); - - } else if (c == ')') { - - char topChar = stack.pop(); - if (topChar != '(') { - return false; - } - - } else if (c == ']') { - - char topChar = stack.pop(); - if (topChar != '[') { - return false; - } - - } else if (c == '}') { - - char topChar = stack.pop(); - if (topChar != '{') { - return false; - } - - } - } - return stack.size() == 0; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java deleted file mode 100644 index 1a479c9b97..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExpr.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.coding.basic.stack.expr; - -public class InfixExpr { - String expr = null; - - public InfixExpr(String expr) { - this.expr = expr; - } - - public float evaluate() { - - return 0.0f; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java deleted file mode 100644 index feb20c7d5c..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/java/com/coding/basic/stack/expr/InfixExprTest.java +++ /dev/null @@ -1,47 +0,0 @@ -package com.coding.basic.stack.expr; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class InfixExprTest { - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testEvaluate() { - // InfixExpr expr = new InfixExpr("300*20+12*5-20/4"); - { - InfixExpr expr = new InfixExpr("2+3*4+5"); - Assert.assertEquals(19.0, expr.evaluate(), 0.001f); - } - { - InfixExpr expr = new InfixExpr("3*20+12*5-40/2"); - Assert.assertEquals(100.0, expr.evaluate(), 0.001f); - } - - { - InfixExpr expr = new InfixExpr("3*20/2"); - Assert.assertEquals(30, expr.evaluate(), 0.001f); - } - - { - InfixExpr expr = new InfixExpr("20/2*3"); - Assert.assertEquals(30, expr.evaluate(), 0.001f); - } - - { - InfixExpr expr = new InfixExpr("10-30+50"); - Assert.assertEquals(30, expr.evaluate(), 0.001f); - } - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml deleted file mode 100644 index e5d9aebba8..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/main/resources/struts.xml +++ /dev/null @@ -1,11 +0,0 @@ - - - - /jsp/homepage.jsp - /jsp/showLogin.jsp - - - /jsp/welcome.jsp - /jsp/error.jsp - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java deleted file mode 100644 index 5e4259bddf..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/api/ConnectionTest.java +++ /dev/null @@ -1,42 +0,0 @@ -package com.coderising.download.api; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -import com.coderising.download.impl.ConnectionManagerImpl; - -public class ConnectionTest { - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testContentLength() throws Exception { - ConnectionManager connMan = new ConnectionManagerImpl(); - Connection conn = connMan.open("http://www.hinews.cn/pic/0/13/91/26/13912621_821796.jpg"); - Assert.assertEquals(35470, conn.getContentLength()); - } - - @Test - public void testRead() throws Exception { - ConnectionManager connMan = new ConnectionManagerImpl(); - Connection conn = connMan.open("http://www.hinews.cn/pic/0/13/91/26/13912621_821796.jpg"); - - byte[] data = conn.read(0, 35469); - Assert.assertEquals(35470, data.length); - - data = conn.read(0, 1023); - Assert.assertEquals(1024, data.length); - - data = conn.read(1024, 2023); - Assert.assertEquals(1000, data.length); - - // 测试不充分,没有断言内容是否正确 - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java deleted file mode 100644 index 2631a1f90b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/download/core/FileDownloaderTest.java +++ /dev/null @@ -1,56 +0,0 @@ -package com.coderising.download.core; - -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://www.hinews.cn/pic/0/13/91/26/13912621_821796.jpg"; - - String url = "http://images2015.cnblogs.com/blog/610238/201604/610238-20160421154632101-286208268.png"; - - FileDownloader downloader = new FileDownloader(url, "c:\\coderising\\tmp\\test.jpg"); - - 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/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java deleted file mode 100644 index b8ab6c04b9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ConfigurationTest.java +++ /dev/null @@ -1,46 +0,0 @@ -package com.coderising.litestruts; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class ConfigurationTest { - - Configuration cfg = new Configuration("struts.xml"); - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testGetClassName() { - - String clzName = cfg.getClassName("login"); - Assert.assertEquals("com.coderising.litestruts.LoginAction", clzName); - - clzName = cfg.getClassName("logout"); - Assert.assertEquals("com.coderising.litestruts.LogoutAction", clzName); - } - - @Test - public void testGetResultView() { - String jsp = cfg.getResultView("login", "success"); - Assert.assertEquals("/jsp/homepage.jsp", jsp); - - jsp = cfg.getResultView("login", "fail"); - Assert.assertEquals("/jsp/showLogin.jsp", jsp); - - jsp = cfg.getResultView("logout", "success"); - Assert.assertEquals("/jsp/welcome.jsp", jsp); - - jsp = cfg.getResultView("logout", "error"); - Assert.assertEquals("/jsp/error.jsp", jsp); - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java deleted file mode 100644 index 4362ae0ac7..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/ReflectionUtilTest.java +++ /dev/null @@ -1,104 +0,0 @@ -package com.coderising.litestruts; - -import java.lang.reflect.Field; -import java.lang.reflect.Method; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.HashSet; -import java.util.List; -import java.util.Map; -import java.util.Set; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class ReflectionUtilTest { - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testGetSetterMethod() throws Exception { - - String name = "com.coderising.litestruts.LoginAction"; - Class clz = Class.forName(name); - List methods = ReflectionUtil.getSetterMethods(clz); - - Assert.assertEquals(2, methods.size()); - - List expectedNames = new ArrayList<>(); - expectedNames.add("setName"); - expectedNames.add("setPassword"); - - Set acctualNames = new HashSet<>(); - for (Method m : methods) { - acctualNames.add(m.getName()); - } - - Assert.assertTrue(acctualNames.containsAll(expectedNames)); - } - - @Test - public void testSetParameters() throws Exception { - String name = "com.coderising.litestruts.LoginAction"; - Class clz = Class.forName(name); - Object o = clz.newInstance(); - - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "1234"); - - ReflectionUtil.setParameters(o, params); - - Field f = clz.getDeclaredField("name"); - f.setAccessible(true); - Assert.assertEquals("test", f.get(o)); - - f = clz.getDeclaredField("password"); - f.setAccessible(true); - Assert.assertEquals("1234", f.get(o)); - } - - @Test - public void testGetGetterMethod() throws Exception { - String name = "com.coderising.litestruts.LoginAction"; - Class clz = Class.forName(name); - List methods = ReflectionUtil.getGetterMethods(clz); - - Assert.assertEquals(3, methods.size()); - - List expectedNames = new ArrayList<>(); - expectedNames.add("getMessage"); - expectedNames.add("getName"); - expectedNames.add("getPassword"); - - Set acctualNames = new HashSet<>(); - for (Method m : methods) { - acctualNames.add(m.getName()); - } - - Assert.assertTrue(acctualNames.containsAll(expectedNames)); - } - - @Test - public void testGetParamters() throws Exception { - String name = "com.coderising.litestruts.LoginAction"; - Class clz = Class.forName(name); - LoginAction action = (LoginAction) clz.newInstance(); - action.setName("test"); - action.setPassword("123456"); - - Map params = ReflectionUtil.getParamterMap(action); - - Assert.assertEquals(3, params.size()); - Assert.assertEquals(null, params.get("messaage")); - Assert.assertEquals("test", params.get("name")); - Assert.assertEquals("123456", params.get("password")); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java deleted file mode 100644 index 5174fc47f1..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coderising/litestruts/StrutsTest.java +++ /dev/null @@ -1,37 +0,0 @@ -package com.coderising.litestruts; - -import java.util.HashMap; -import java.util.Map; - -import org.junit.Assert; -import org.junit.Test; - -public class StrutsTest { - @Test - public void testLoginActionSuccess() { - - String actionName = "login"; - - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "1234"); - - View view = Struts.runAction(actionName, params); - - Assert.assertEquals("/jsp/homepage.jsp", view.getJsp()); - Assert.assertEquals("login successful", view.getParameters().get("message")); - } - - @Test - public void testLoginActionFailed() { - String actionName = "login"; - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "123456"); // 密码和预设的不一致 - - View view = Struts.runAction(actionName, params); - - Assert.assertEquals("/jsp/showLogin.jsp", view.getJsp()); - Assert.assertEquals("login failed,please check your user/pwd", view.getParameters().get("message")); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java deleted file mode 100644 index 47ef10e125..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LRUPageFrameTest.java +++ /dev/null @@ -1,32 +0,0 @@ -package com.coding.basic.linklist; - -import org.junit.Assert; -import org.junit.Test; - -public class LRUPageFrameTest { - - @Test - public void testAccess() { - LRUPageFrame frame = new LRUPageFrame(3); - frame.access(7); - frame.access(0); - frame.access(1); - Assert.assertEquals("1,0,7", frame.toString()); - frame.access(2); - Assert.assertEquals("2,1,0", frame.toString()); - frame.access(0); - Assert.assertEquals("0,2,1", frame.toString()); - frame.access(0); - Assert.assertEquals("0,2,1", frame.toString()); - frame.access(3); - Assert.assertEquals("3,0,2", frame.toString()); - frame.access(0); - Assert.assertEquals("0,3,2", frame.toString()); - frame.access(4); - Assert.assertEquals("4,0,3", frame.toString()); - frame.access(5); - Assert.assertEquals("5,4,0", frame.toString()); - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java deleted file mode 100644 index 39a1b3f3e0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/linklist/LinkedListTest.java +++ /dev/null @@ -1,197 +0,0 @@ -package com.coding.basic.linklist; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class LinkedListTest { - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testReverse() { - LinkedList l = new LinkedList(); - - Assert.assertEquals("[]", l.toString()); - - l.add(1); - l.reverse(); - Assert.assertEquals("[1]", l.toString()); - - l.add(2); - l.add(3); - l.add(4); - - l.reverse(); - Assert.assertEquals("[4,3,2,1]", l.toString()); - } - - @Test - public void testRemoveFirstHalf() { - { - LinkedList linkedList = new LinkedList(); - linkedList.add(1); - linkedList.add(2); - linkedList.add(3); - linkedList.add(4); - linkedList.removeFirstHalf(); - Assert.assertEquals("[3,4]", linkedList.toString()); - } - { - LinkedList linkedList = new LinkedList(); - linkedList.add(1); - linkedList.add(2); - linkedList.add(3); - linkedList.add(4); - linkedList.add(5); - linkedList.removeFirstHalf(); - Assert.assertEquals("[3,4,5]", linkedList.toString()); - } - } - - @Test - public void testRemoveIntInt() { - { - LinkedList linkedList = new LinkedList(); - linkedList.add(1); - linkedList.add(2); - linkedList.add(3); - linkedList.add(4); - linkedList.remove(0, 2); - Assert.assertEquals("[3,4]", linkedList.toString()); - } - { - LinkedList linkedList = new LinkedList(); - linkedList.add(1); - linkedList.add(2); - linkedList.add(3); - linkedList.add(4); - linkedList.remove(3, 2); - Assert.assertEquals("[1,2,3]", linkedList.toString()); - } - { - LinkedList linkedList = new LinkedList(); - linkedList.add(1); - linkedList.add(2); - linkedList.add(3); - linkedList.add(4); - linkedList.remove(2, 2); - Assert.assertEquals("[1,2]", linkedList.toString()); - } - } - - @Test - public void testGetElements() { - LinkedList linkedList = new LinkedList(); - linkedList.add(11); - linkedList.add(101); - linkedList.add(201); - linkedList.add(301); - linkedList.add(401); - linkedList.add(501); - linkedList.add(601); - linkedList.add(701); - LinkedList list = new LinkedList(); - list.add(1); - list.add(3); - list.add(4); - list.add(6); - Assert.assertArrayEquals(new int[] { 101, 301, 401, 601 }, linkedList.getElements(list)); - } - - @Test - public void testSubtract() { - LinkedList list1 = new LinkedList(); - list1.add(101); - list1.add(201); - list1.add(301); - list1.add(401); - list1.add(501); - list1.add(601); - list1.add(701); - - LinkedList list2 = new LinkedList(); - - list2.add(101); - list2.add(201); - list2.add(301); - list2.add(401); - list2.add(501); - - list1.subtract(list2); - - Assert.assertEquals("[601,701]", list1.toString()); - } - - @Test - public void testRemoveDuplicateValues() { - LinkedList list = new LinkedList(); - list.add(1); - list.add(1); - list.add(2); - list.add(2); - list.add(3); - list.add(5); - list.add(5); - list.add(6); - list.removeDuplicateValues(); - - Assert.assertEquals("[1,2,3,5,6]", list.toString()); - } - - @Test - public void testRemoveRange() { - { - LinkedList linkedList = new LinkedList(); - - linkedList.add(11); - linkedList.add(12); - linkedList.add(13); - linkedList.add(14); - linkedList.add(16); - linkedList.add(16); - linkedList.add(19); - - linkedList.removeRange(10, 19); - Assert.assertEquals("[19]", linkedList.toString()); - } - - { - LinkedList linkedList = new LinkedList(); - - linkedList.add(11); - linkedList.add(12); - linkedList.add(13); - linkedList.add(14); - linkedList.add(16); - linkedList.add(16); - linkedList.add(19); - - linkedList.removeRange(10, 14); - Assert.assertEquals("[14,16,16,19]", linkedList.toString()); - } - } - - @Test - public void testIntersection() { - LinkedList list1 = new LinkedList(); - list1.add(1); - list1.add(6); - list1.add(7); - - LinkedList list2 = new LinkedList(); - list2.add(2); - list2.add(5); - list2.add(6); - - LinkedList newList = list1.intersection(list2); - Assert.assertEquals("[6]", newList.toString()); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java deleted file mode 100644 index 5976823f36..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/java/com/coding/basic/stack/StackUtilTest.java +++ /dev/null @@ -1,78 +0,0 @@ -package com.coding.basic.stack; - -import java.util.Stack; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -public class StackUtilTest { - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - } - - @Test - public void testAddToBottom() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - - StackUtil.addToBottom(s, 0); - - Assert.assertEquals("[0, 1, 2, 3]", s.toString()); - - } - - @Test - public void testReverse() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - s.push(4); - s.push(5); - Assert.assertEquals("[1, 2, 3, 4, 5]", s.toString()); - StackUtil.reverse(s); - Assert.assertEquals("[5, 4, 3, 2, 1]", s.toString()); - } - - @Test - public void testRemove() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - StackUtil.remove(s, 2); - Assert.assertEquals("[1, 3]", s.toString()); - } - - @Test - public void testGetTop() { - Stack s = new Stack(); - s.push(1); - s.push(2); - s.push(3); - s.push(4); - s.push(5); - { - Object[] values = StackUtil.getTop(s, 3); - Assert.assertEquals(5, values[0]); - Assert.assertEquals(4, values[1]); - Assert.assertEquals(3, values[2]); - } - } - - @Test - public void testIsValidPairs() { - Assert.assertTrue(StackUtil.isValidPairs("([e{d}f])")); - Assert.assertFalse(StackUtil.isValidPairs("([b{x]y})")); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-52-liuxin-answer/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 From 3f84999c2816fe5592a7f8964092f89d7903f38f Mon Sep 17 00:00:00 2001 From: thomas_young Date: Mon, 19 Jun 2017 23:36:47 +0800 Subject: [PATCH 03/73] =?UTF-8?q?=E7=AC=AC=E4=B8=80=E6=AC=A1=E4=BD=9C?= =?UTF-8?q?=E4=B8=9A=20init2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- liuxin/ood/ood-assignment/pom.xml | 13 +++++++++++++ .../java/com/coderising/ood/srp/PromotionMail.java | 2 +- 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/liuxin/ood/ood-assignment/pom.xml b/liuxin/ood/ood-assignment/pom.xml index cac49a5328..9a28365d2a 100644 --- a/liuxin/ood/ood-assignment/pom.xml +++ b/liuxin/ood/ood-assignment/pom.xml @@ -10,6 +10,19 @@ ood-assignment http://maven.apache.org + + + + org.apache.maven.plugins + maven-compiler-plugin + + 1.8 + 1.8 + + + + + UTF-8 diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java index 781587a846..9d07330831 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -35,7 +35,7 @@ public class PromotionMail { public static void main(String[] args) throws Exception { - File f = new File("C:\\coderising\\workspace_ds\\ood-example\\src\\product_promotion.txt"); + File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt"); boolean emailDebug = false; PromotionMail pe = new PromotionMail(f, emailDebug); From eae3b01de2c0008744b412dbf1fa254879d7c628 Mon Sep 17 00:00:00 2001 From: GUK0 <1685605435@qq.com> Date: Tue, 20 Jun 2017 10:13:54 +0800 Subject: [PATCH 04/73] =?UTF-8?q?=E6=8F=90=E4=BA=A4=E4=BD=9C=E4=B8=9A?= =?UTF-8?q?=EF=BC=8C=E5=B0=86=E5=8F=91=E9=80=81=E9=82=AE=E4=BB=B6=E7=9A=84?= =?UTF-8?q?=E4=BD=9C=E4=B8=9A=E6=8B=86=E5=88=86=E6=88=903=E4=B8=AA?= =?UTF-8?q?=E7=B1=BB=E3=80=82=E5=B8=8C=E6=9C=9B=E8=80=81=E5=B8=88=E7=9C=8B?= =?UTF-8?q?=E7=9C=8B=E6=98=AF=E5=90=A6=E5=90=88=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/247565311/week00/Configuration.java | 19 +++ .../247565311/week00/ConfigurationKeys.java | 6 + students/247565311/week00/DBUtil.java | 21 +++ students/247565311/week00/MailUtil.java | 14 ++ students/247565311/week00/PromotionMail.java | 136 ++++++++++++++++++ .../247565311/week00/product_promotion.txt | 5 + 6 files changed, 201 insertions(+) create mode 100644 students/247565311/week00/Configuration.java create mode 100644 students/247565311/week00/ConfigurationKeys.java create mode 100644 students/247565311/week00/DBUtil.java create mode 100644 students/247565311/week00/MailUtil.java create mode 100644 students/247565311/week00/PromotionMail.java create mode 100644 students/247565311/week00/product_promotion.txt diff --git a/students/247565311/week00/Configuration.java b/students/247565311/week00/Configuration.java new file mode 100644 index 0000000000..66f989efd0 --- /dev/null +++ b/students/247565311/week00/Configuration.java @@ -0,0 +1,19 @@ +package week00; +import java.util.HashMap; +import java.util.Map; +public class Configuration { + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * Ӧ�ô������ļ����� ���������Ϊֱ�Ӵ�һ��map ��ȥ�� + * @param key + * @return + */ + public String getProperty(String key) { + return configurations.get(key); + } +} diff --git a/students/247565311/week00/ConfigurationKeys.java b/students/247565311/week00/ConfigurationKeys.java new file mode 100644 index 0000000000..10da9ce88c --- /dev/null +++ b/students/247565311/week00/ConfigurationKeys.java @@ -0,0 +1,6 @@ +package week00; +public class ConfigurationKeys { + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; +} diff --git a/students/247565311/week00/DBUtil.java b/students/247565311/week00/DBUtil.java new file mode 100644 index 0000000000..903bdef223 --- /dev/null +++ b/students/247565311/week00/DBUtil.java @@ -0,0 +1,21 @@ +package week00; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +public class DBUtil { + /** + * Ӧ�ô����ݿ���� ���Ǽ�Ϊֱ�����ɡ� + * @param sql + * @return + */ + public static List> query(String sql){ + List> userList = new ArrayList>(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com"); + userList.add(userInfo); + } + return userList; + } +} diff --git a/students/247565311/week00/MailUtil.java b/students/247565311/week00/MailUtil.java new file mode 100644 index 0000000000..01e6e32fc8 --- /dev/null +++ b/students/247565311/week00/MailUtil.java @@ -0,0 +1,14 @@ +package week00; + +public class MailUtil { + public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, + boolean debug) { + //��װ����һ���ʼ� + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + } +} diff --git a/students/247565311/week00/PromotionMail.java b/students/247565311/week00/PromotionMail.java new file mode 100644 index 0000000000..a1e079f571 --- /dev/null +++ b/students/247565311/week00/PromotionMail.java @@ -0,0 +1,136 @@ +package week00; +import java.io.BufferedReader; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.FileReader; +import java.io.IOException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +class ProductMessage{ + public String productID; + public String productDesc; + public ProductMessage(String id,String desc){ + productID = id; + productDesc = desc; + } +} +class ProductMessageIter{ + BufferedReader reader = null; + boolean loadFileSuccess = false,readFinished = false; + public ProductMessageIter(File socFile){ + try { + reader = new BufferedReader(new FileReader(socFile)); + } catch (FileNotFoundException e) { + e.printStackTrace(); + return; + } + loadFileSuccess = true; + } + public boolean hasNext(){ + if(!loadFileSuccess || readFinished) return false; + try { + reader.mark(10); + String lineMsg = reader.readLine(); + reader.reset(); + if(lineMsg.equals("")) { + readFinished = true; + reader.close(); + return false; + } + } catch (IOException e) { + e.printStackTrace(); + } + return true; + } + public ProductMessage next(){ + String lineMsg=null; + try { + lineMsg = reader.readLine(); + } catch (IOException e) { + e.printStackTrace(); + } + if(lineMsg == null) return null; + String [] msgs = lineMsg.split(" "); + ProductMessage msg = new ProductMessage(msgs[0],msgs[1]); + System.out.println("��ƷID = " + msgs[0]); + System.out.println("��Ʒ���� = " + msgs[1]); + return msg; + } +} +class EMailSender{ + String fromAddress = null; + String smtpHost = null; + String altSmtpHost = null; + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + public EMailSender(){ + Configuration config = new Configuration(); + smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + } + // �����ʼ����ݣ��ɹ����ɻᷢ���ʼ� + public void configureAndSendEMail(HashMap userInfo,ProductMessage prdMsg,boolean debug) throws IOException + { + String toAddress = "",subject = "",message = ""; + toAddress = (String) userInfo.get(EMAIL_KEY); + if (toAddress.length() > 0) { + String name = (String) userInfo.get(NAME_KEY); + subject = "����ע�IJ�Ʒ������"; + message = "�𾴵� "+name+", ����ע�IJ�Ʒ " + prdMsg.productDesc + " �����ˣ���ӭ����!" ; + System.out.println("��ʼ�����ʼ�"); + sendEMail(toAddress,subject,message,debug); + }else { + System.out.println("û���ʼ�����"); + } + } + // ����֪ͨ�ʼ� + void sendEMail(String toAddress,String subject,String message,boolean debug) throws IOException + { + boolean sendSucceed = false; + try + { + if (toAddress.length() > 0){ + MailUtil.sendEmail(toAddress, fromAddress, subject, message, smtpHost, debug); + sendSucceed = true; + } + } + catch (Exception e) {} + if(!sendSucceed){ + try { + MailUtil.sendEmail(toAddress, fromAddress, subject, message, altSmtpHost, debug); + } catch (Exception e2) + { + System.out.println("ͨ������ SMTP�����������ʼ�ʧ��: " + e2.getMessage()); + } + } + } +} +public class PromotionMail { + public static void main(String[] args) throws Exception { + File f = new File("J:\\gitstore\\coding2017\\students\\247565311\\week00\\product_promotion.txt"); + boolean emailDebug = false; + PromotionMail pe = new PromotionMail(f, emailDebug); + } + // ���̿��� + public PromotionMail(File file, boolean mailDebug) throws Exception { + ProductMessageIter iter = new ProductMessageIter(file);//��ȡ�����ļ��� �ļ���ֻ��һ���ÿո������ ���� P8756 iPhone8 + while(iter.hasNext()){ + ProductMessage prdMsg = iter.next(); + List> userInfos = loadMailingList(prdMsg); + for(HashMap user : userInfos){ + new EMailSender().configureAndSendEMail(user,prdMsg,mailDebug); + } + } + } + // ��ȡ�û������б� + protected List> loadMailingList(ProductMessage prdMsg) throws Exception { + String sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + prdMsg.productID +"' " + + "and send_mail=1 "; + System.out.println("�����û��б���..."); + return DBUtil.query(sendMailQuery); + } +} diff --git a/students/247565311/week00/product_promotion.txt b/students/247565311/week00/product_promotion.txt new file mode 100644 index 0000000000..e98aea9f01 --- /dev/null +++ b/students/247565311/week00/product_promotion.txt @@ -0,0 +1,5 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 + From 12d576619b8e2c1a6ba4ea27af7d5af5334ed941 Mon Sep 17 00:00:00 2001 From: fengdzh Date: Tue, 20 Jun 2017 10:26:02 +0800 Subject: [PATCH 05/73] readme --- students/281918307 | 1 + 1 file changed, 1 insertion(+) create mode 100644 students/281918307 diff --git a/students/281918307 b/students/281918307 new file mode 100644 index 0000000000..8178c76d62 --- /dev/null +++ b/students/281918307 @@ -0,0 +1 @@ +readme From 8a6bb2b216c54f1cd752d21d84ffdd3e130a6b2c Mon Sep 17 00:00:00 2001 From: fengdz Date: Tue, 20 Jun 2017 10:34:32 +0800 Subject: [PATCH 06/73] =?UTF-8?q?=E5=88=A0=E9=99=A4=E6=96=87=E4=BB=B6?= =?UTF-8?q?=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/281918307 | 1 - 1 file changed, 1 deletion(-) delete mode 100644 students/281918307 diff --git a/students/281918307 b/students/281918307 deleted file mode 100644 index 8178c76d62..0000000000 --- a/students/281918307 +++ /dev/null @@ -1 +0,0 @@ -readme From 09b0045aae10d3662fd218787278785116cbc52c Mon Sep 17 00:00:00 2001 From: fengdz Date: Tue, 20 Jun 2017 10:37:51 +0800 Subject: [PATCH 07/73] =?UTF-8?q?=E5=88=9D=E5=A7=8B=E5=8C=96=E5=88=9B?= =?UTF-8?q?=E5=BB=BA=E6=96=87=E4=BB=B6=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/281918307/readme.md | 1 + 1 file changed, 1 insertion(+) create mode 100644 students/281918307/readme.md diff --git a/students/281918307/readme.md b/students/281918307/readme.md new file mode 100644 index 0000000000..ea786ff2cf --- /dev/null +++ b/students/281918307/readme.md @@ -0,0 +1 @@ +readme \ No newline at end of file From 80fb48c5042731f2e6cfc8be1349007f86d168a2 Mon Sep 17 00:00:00 2001 From: Ken-W-P-Huang Date: Tue, 20 Jun 2017 11:36:49 +0800 Subject: [PATCH 08/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E6=AC=A1=E4=BD=9C?= =?UTF-8?q?=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/395860968/OCP/AbstractNotifier.java | 10 ++++++++++ students/395860968/OCP/ConsoleUtil.java | 11 +++++++++++ students/395860968/OCP/DateFormatter.java | 13 +++++++++++++ students/395860968/OCP/DateUtil.java | 10 ++++++++++ students/395860968/OCP/Formatter.java | 10 ++++++++++ students/395860968/OCP/Logger.java | 15 +++++++++++++++ students/395860968/OCP/MailUtil.java | 11 +++++++++++ students/395860968/OCP/Main.java | 17 +++++++++++++++++ students/395860968/OCP/SMSUtil.java | 10 ++++++++++ .../{ood-assignment => SRP}/Configuration.java | 0 .../ConfigurationKeys.java | 0 .../{ood-assignment => SRP}/DBUtil.java | 0 .../{ood-assignment => SRP}/FileUtil.java | 0 .../{ood-assignment => SRP}/MailUtil.java | 0 .../{ood-assignment => SRP}/Product.java | 0 .../{ood-assignment => SRP}/PromotionMail.java | 0 .../product_promotion.txt | 0 students/395860968/{ood-assignment => SRP}/src | 0 18 files changed, 107 insertions(+) create mode 100644 students/395860968/OCP/AbstractNotifier.java create mode 100644 students/395860968/OCP/ConsoleUtil.java create mode 100644 students/395860968/OCP/DateFormatter.java create mode 100644 students/395860968/OCP/DateUtil.java create mode 100644 students/395860968/OCP/Formatter.java create mode 100644 students/395860968/OCP/Logger.java create mode 100644 students/395860968/OCP/MailUtil.java create mode 100644 students/395860968/OCP/Main.java create mode 100644 students/395860968/OCP/SMSUtil.java rename students/395860968/{ood-assignment => SRP}/Configuration.java (100%) rename students/395860968/{ood-assignment => SRP}/ConfigurationKeys.java (100%) rename students/395860968/{ood-assignment => SRP}/DBUtil.java (100%) rename students/395860968/{ood-assignment => SRP}/FileUtil.java (100%) rename students/395860968/{ood-assignment => SRP}/MailUtil.java (100%) rename students/395860968/{ood-assignment => SRP}/Product.java (100%) rename students/395860968/{ood-assignment => SRP}/PromotionMail.java (100%) rename students/395860968/{ood-assignment => SRP}/product_promotion.txt (100%) rename students/395860968/{ood-assignment => SRP}/src (100%) diff --git a/students/395860968/OCP/AbstractNotifier.java b/students/395860968/OCP/AbstractNotifier.java new file mode 100644 index 0000000000..4aaffa4dc3 --- /dev/null +++ b/students/395860968/OCP/AbstractNotifier.java @@ -0,0 +1,10 @@ +package com.company; + +/** + * Created by kenhuang on 2017/6/20. + */ +public abstract class AbstractNotifier { + public void send(String logMsg) { + + } +} diff --git a/students/395860968/OCP/ConsoleUtil.java b/students/395860968/OCP/ConsoleUtil.java new file mode 100644 index 0000000000..e7a1e5e0ad --- /dev/null +++ b/students/395860968/OCP/ConsoleUtil.java @@ -0,0 +1,11 @@ +package com.company; + +/** + * Created by kenhuang on 2017/6/20. + */ +public class ConsoleUtil extends AbstractNotifier { + public void send(String logMsg) { + // TODO Auto-generated method stub + System.out.println("Console send: " + logMsg); + } +} diff --git a/students/395860968/OCP/DateFormatter.java b/students/395860968/OCP/DateFormatter.java new file mode 100644 index 0000000000..37719ae800 --- /dev/null +++ b/students/395860968/OCP/DateFormatter.java @@ -0,0 +1,13 @@ +package com.company; + +/** + * Created by kenhuang on 2017/6/20. + */ +public class DateFormatter extends Formatter { + @Override + public String formatMessage(String msg) { + String txtDate = DateUtil.getCurrentDateAsString(); + return txtDate + " : " + msg; + + } +} diff --git a/students/395860968/OCP/DateUtil.java b/students/395860968/OCP/DateUtil.java new file mode 100644 index 0000000000..5d0e77a475 --- /dev/null +++ b/students/395860968/OCP/DateUtil.java @@ -0,0 +1,10 @@ +package com.company; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return "20170101"; + } + +} diff --git a/students/395860968/OCP/Formatter.java b/students/395860968/OCP/Formatter.java new file mode 100644 index 0000000000..453d2a98d9 --- /dev/null +++ b/students/395860968/OCP/Formatter.java @@ -0,0 +1,10 @@ +package com.company; + +/** + * Created by kenhuang on 2017/6/20. + */ +public class Formatter { + public String formatMessage(String msg) { + return msg; + } +} diff --git a/students/395860968/OCP/Logger.java b/students/395860968/OCP/Logger.java new file mode 100644 index 0000000000..29b4396cb4 --- /dev/null +++ b/students/395860968/OCP/Logger.java @@ -0,0 +1,15 @@ +package com.company; + +public class Logger { + private AbstractNotifier notifier; + private Formatter formatter; + public Logger(Formatter formatter, AbstractNotifier notifier){ + this.formatter = formatter; + this.notifier = notifier; + } + public void log(String msg){ + String logMsg = this.formatter.formatMessage(msg); + notifier.send(logMsg); + } +} + diff --git a/students/395860968/OCP/MailUtil.java b/students/395860968/OCP/MailUtil.java new file mode 100644 index 0000000000..3b38eb1630 --- /dev/null +++ b/students/395860968/OCP/MailUtil.java @@ -0,0 +1,11 @@ +package com.company; + +public class MailUtil extends AbstractNotifier { + + @Override + public void send(String logMsg) { + // TODO Auto-generated method stub + System.out.println("Mail send: " + logMsg); + } + +} diff --git a/students/395860968/OCP/Main.java b/students/395860968/OCP/Main.java new file mode 100644 index 0000000000..cee3424004 --- /dev/null +++ b/students/395860968/OCP/Main.java @@ -0,0 +1,17 @@ +package com.company; + +public class Main { + + public static void main(String[] args) { + // write your code here + ConsoleUtil consoleUtil = new ConsoleUtil(); + Formatter formatter = new Formatter(); + Logger logger = new Logger(formatter,consoleUtil); + logger.log("abc"); + MailUtil mailUtil = new MailUtil(); + DateFormatter dateformatter = new DateFormatter(); + Logger logger2 = new Logger(dateformatter,mailUtil); + logger2.log("efg"); + + } +} diff --git a/students/395860968/OCP/SMSUtil.java b/students/395860968/OCP/SMSUtil.java new file mode 100644 index 0000000000..1bd29a0613 --- /dev/null +++ b/students/395860968/OCP/SMSUtil.java @@ -0,0 +1,10 @@ +package com.company; + +public class SMSUtil extends AbstractNotifier { + + public void send(String logMsg) { + // TODO Auto-generated method stub + System.out.println("SMS send: " + logMsg); + } + +} diff --git a/students/395860968/ood-assignment/Configuration.java b/students/395860968/SRP/Configuration.java similarity index 100% rename from students/395860968/ood-assignment/Configuration.java rename to students/395860968/SRP/Configuration.java diff --git a/students/395860968/ood-assignment/ConfigurationKeys.java b/students/395860968/SRP/ConfigurationKeys.java similarity index 100% rename from students/395860968/ood-assignment/ConfigurationKeys.java rename to students/395860968/SRP/ConfigurationKeys.java diff --git a/students/395860968/ood-assignment/DBUtil.java b/students/395860968/SRP/DBUtil.java similarity index 100% rename from students/395860968/ood-assignment/DBUtil.java rename to students/395860968/SRP/DBUtil.java diff --git a/students/395860968/ood-assignment/FileUtil.java b/students/395860968/SRP/FileUtil.java similarity index 100% rename from students/395860968/ood-assignment/FileUtil.java rename to students/395860968/SRP/FileUtil.java diff --git a/students/395860968/ood-assignment/MailUtil.java b/students/395860968/SRP/MailUtil.java similarity index 100% rename from students/395860968/ood-assignment/MailUtil.java rename to students/395860968/SRP/MailUtil.java diff --git a/students/395860968/ood-assignment/Product.java b/students/395860968/SRP/Product.java similarity index 100% rename from students/395860968/ood-assignment/Product.java rename to students/395860968/SRP/Product.java diff --git a/students/395860968/ood-assignment/PromotionMail.java b/students/395860968/SRP/PromotionMail.java similarity index 100% rename from students/395860968/ood-assignment/PromotionMail.java rename to students/395860968/SRP/PromotionMail.java diff --git a/students/395860968/ood-assignment/product_promotion.txt b/students/395860968/SRP/product_promotion.txt similarity index 100% rename from students/395860968/ood-assignment/product_promotion.txt rename to students/395860968/SRP/product_promotion.txt diff --git a/students/395860968/ood-assignment/src b/students/395860968/SRP/src similarity index 100% rename from students/395860968/ood-assignment/src rename to students/395860968/SRP/src From 5fd8ae3b07b89c74373e7294924ca8fa8151e6d7 Mon Sep 17 00:00:00 2001 From: fengdz Date: Tue, 20 Jun 2017 11:50:43 +0800 Subject: [PATCH 09/73] =?UTF-8?q?=E5=88=9D=E5=A7=8B=E5=8C=96=E5=8C=85?= =?UTF-8?q?=E7=BB=93=E6=9E=84=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/281918307/.gitignore | 153 ++++++++++++++++++ students/281918307/ood-ocp/pom.xml | 32 ++++ .../main/java/com/ood/ocp/Application.java | 14 ++ .../src/main/resources/log4j.properties | 8 + students/281918307/pom.xml | 52 ++++++ students/281918307/readme.md | 3 +- 6 files changed, 261 insertions(+), 1 deletion(-) create mode 100644 students/281918307/.gitignore create mode 100644 students/281918307/ood-ocp/pom.xml create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java create mode 100644 students/281918307/ood-ocp/src/main/resources/log4j.properties create mode 100644 students/281918307/pom.xml diff --git a/students/281918307/.gitignore b/students/281918307/.gitignore new file mode 100644 index 0000000000..15a7d78fcb --- /dev/null +++ b/students/281918307/.gitignore @@ -0,0 +1,153 @@ +/target/ +/.idea +/*.iml +/**/*.iml +/.setting +/*.project +.DS_Store +thrid-chongwu/.DS_Store +thrid-chongwu/src/.DS_Store +thrid-chongwu/src/main/.DS_Store +thrid-chongwu/src/main/assembly/.DS_Store +thrid-chongwu/src/main/resources/.DS_Store +thrid-chongwu/src/main/resources/templates/.DS_Store +thrid-chongwu/src/main/webapp/ +thrid-chongwu/src/test/ +thrid-chongwu/target/ +### Java template +# Compiled class file +*.class + +# Log file +*.log + +# BlueJ files +*.ctxt + +# Mobile Tools for Java (J2ME) +.mtj.tmp/ + +# Package Files # +*.jar +*.war +*.ear +*.zip +*.tar.gz +*.rar + +# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml +hs_err_pid* +### JetBrains template +# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio and Webstorm +# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839 + +# User-specific stuff: +.idea/**/workspace.xml +.idea/**/tasks.xml +.idea/dictionaries + +# Sensitive or high-churn files: +.idea/**/dataSources/ +.idea/**/dataSources.ids +.idea/**/dataSources.xml +.idea/**/dataSources.local.xml +.idea/**/sqlDataSources.xml +.idea/**/dynamic.xml +.idea/**/uiDesigner.xml + +# Gradle: +.idea/**/gradle.xml +.idea/**/libraries + +# Mongo Explorer plugin: +.idea/**/mongoSettings.xml + +## File-based project format: +*.iws + +## Plugin-specific files: + +# IntelliJ +/out/ + +# mpeltonen/sbt-idea plugin +.idea_modules/ + +# JIRA plugin +atlassian-ide-plugin.xml + +# Crashlytics plugin (for Android Studio and IntelliJ) +com_crashlytics_export_strings.xml +crashlytics.properties +crashlytics-build.properties +fabric.properties +### macOS template +*.DS_Store +.AppleDouble +.LSOverride + +# Icon must end with two \r +Icon + + +# Thumbnails +._* + +# Files that might appear in the root of a volume +.DocumentRevisions-V100 +.fseventsd +.Spotlight-V100 +.TemporaryItems +.Trashes +.VolumeIcon.icns +.com.apple.timemachine.donotpresent + +# Directories potentially created on remote AFP share +.AppleDB +.AppleDesktop +Network Trash Folder +Temporary Items +.apdisk +### Windows template +# Windows thumbnail cache files +Thumbs.db +ehthumbs.db +ehthumbs_vista.db + +# Folder config file +Desktop.ini + +# Recycle Bin used on file shares +$RECYCLE.BIN/ + +# Windows Installer files +*.cab +*.msi +*.msm +*.msp + +# Windows shortcuts +*.lnk +### Archives template +# It's better to unpack these files and commit the raw source because +# git has its own built in compression methods. +*.7z +*.gz +*.bzip +*.bz2 +*.xz +*.lzma + +#packing-only formats +*.iso +*.tar + +#package management formats +*.dmg +*.xpi +*.gem +*.egg +*.deb +*.rpm +### SVN template +.svn/ diff --git a/students/281918307/ood-ocp/pom.xml b/students/281918307/ood-ocp/pom.xml new file mode 100644 index 0000000000..9daf351b12 --- /dev/null +++ b/students/281918307/ood-ocp/pom.xml @@ -0,0 +1,32 @@ + + + 4.0.0 + + + com.ood + ood-application + 1.0.0-SNAPSHOT + ../pom.xml + + + ood-ocp + jar + + + + + junit + junit + test + + + log4j + log4j + + + + + + \ No newline at end of file diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java new file mode 100644 index 0000000000..843af308ec --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java @@ -0,0 +1,14 @@ +package com.ood.ocp; + +import org.apache.log4j.Logger; + +/** + * Created by ajaxfeng on 2017/6/20. + */ +public class Application { + static final Logger logger = Logger.getLogger(Application.class); + + public static void main(String [] args) { + logger.error("Application running ..."); + } +} diff --git a/students/281918307/ood-ocp/src/main/resources/log4j.properties b/students/281918307/ood-ocp/src/main/resources/log4j.properties new file mode 100644 index 0000000000..508df51466 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/resources/log4j.properties @@ -0,0 +1,8 @@ +log4j.rootLogger=debug, stdout + +log4j.appender.stdout=org.apache.log4j.ConsoleAppender +log4j.appender.stdout.layout=org.apache.log4j.PatternLayout +log4j.appender.stdout.layout.ConversionPattern=%-d{yyyy-MM-dd HH:mm:ss} [ %t:%r ] - [ %p ] %l - %m%n + +# Third party loggers + log4j.logger.com.ood=debug diff --git a/students/281918307/pom.xml b/students/281918307/pom.xml new file mode 100644 index 0000000000..9b7eac3299 --- /dev/null +++ b/students/281918307/pom.xml @@ -0,0 +1,52 @@ + + + 4.0.0 + + com.ood + ood-application + pom + 1.0.0-SNAPSHOT + + + ood-ocp + + + + + UTF-8 + 1.8 + + + + + + + junit + junit + 4.12 + test + + + + log4j + log4j + 1.2.16 + + + org.slf4j + slf4j-api + 1.6.1 + + + org.slf4j + slf4j-log4j12 + 1.6.1 + + + + + + + \ No newline at end of file diff --git a/students/281918307/readme.md b/students/281918307/readme.md index ea786ff2cf..fdf99a9b89 100644 --- a/students/281918307/readme.md +++ b/students/281918307/readme.md @@ -1 +1,2 @@ -readme \ No newline at end of file +ood application + From 104ac6a7712cf556cca47e88c2a0bb2823f48325 Mon Sep 17 00:00:00 2001 From: fengdz Date: Tue, 20 Jun 2017 11:56:38 +0800 Subject: [PATCH 10/73] =?UTF-8?q?=E5=A2=9E=E5=8A=A0ocp=E3=80=81srp=20modul?= =?UTF-8?q?e?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/281918307/ood-srp/pom.xml | 31 +++++++++++++++++++ .../main/java/com/ood/srp/Application.java | 14 +++++++++ .../src/main/resources/log4j.properties | 8 +++++ students/281918307/pom.xml | 1 + 4 files changed, 54 insertions(+) create mode 100644 students/281918307/ood-srp/pom.xml create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java create mode 100644 students/281918307/ood-srp/src/main/resources/log4j.properties diff --git a/students/281918307/ood-srp/pom.xml b/students/281918307/ood-srp/pom.xml new file mode 100644 index 0000000000..cfd98a73b1 --- /dev/null +++ b/students/281918307/ood-srp/pom.xml @@ -0,0 +1,31 @@ + + + 4.0.0 + + + com.ood + ood-application + 1.0.0-SNAPSHOT + ../pom.xml + + + ood-srp + jar + + + + + junit + junit + test + + + log4j + log4j + + + + + \ No newline at end of file diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java new file mode 100644 index 0000000000..f8b7fdd190 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java @@ -0,0 +1,14 @@ +package com.ood.srp; + +import org.apache.log4j.Logger; + +/** + * Created by ajaxfeng on 2017/6/20. + */ +public class Application { + static final Logger logger = Logger.getLogger(Application.class); + + public static void main(String [] args) { + logger.error("Application running ..."); + } +} diff --git a/students/281918307/ood-srp/src/main/resources/log4j.properties b/students/281918307/ood-srp/src/main/resources/log4j.properties new file mode 100644 index 0000000000..508df51466 --- /dev/null +++ b/students/281918307/ood-srp/src/main/resources/log4j.properties @@ -0,0 +1,8 @@ +log4j.rootLogger=debug, stdout + +log4j.appender.stdout=org.apache.log4j.ConsoleAppender +log4j.appender.stdout.layout=org.apache.log4j.PatternLayout +log4j.appender.stdout.layout.ConversionPattern=%-d{yyyy-MM-dd HH:mm:ss} [ %t:%r ] - [ %p ] %l - %m%n + +# Third party loggers + log4j.logger.com.ood=debug diff --git a/students/281918307/pom.xml b/students/281918307/pom.xml index 9b7eac3299..cfbb6af460 100644 --- a/students/281918307/pom.xml +++ b/students/281918307/pom.xml @@ -11,6 +11,7 @@ ood-ocp + ood-srp From 899f5296ce91dff60f08c15932a1c0553816096a Mon Sep 17 00:00:00 2001 From: johnChnia Date: Tue, 20 Jun 2017 14:38:09 +0800 Subject: [PATCH 11/73] =?UTF-8?q?=E5=AE=8C=E6=88=90ocp=E4=BD=9C=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/com/coderising/ood/ocp/DateUtil.java | 13 ++++++++++++ .../com/coderising/ood/ocp/FormatByDate.java | 12 +++++++++++ .../com/coderising/ood/ocp/FormatByRaw.java | 11 ++++++++++ .../com/coderising/ood/ocp/FormatLog.java | 9 ++++++++ .../java/com/coderising/ood/ocp/Logger.java | 21 +++++++++++++++++++ .../java/com/coderising/ood/ocp/MailUtil.java | 12 +++++++++++ .../java/com/coderising/ood/ocp/README.md | 4 ++++ .../java/com/coderising/ood/ocp/SMSUtil.java | 11 ++++++++++ .../java/com/coderising/ood/ocp/SendLog.java | 8 +++++++ .../com/coderising/ood/ocp/SendLogByMail.java | 11 ++++++++++ .../coderising/ood/ocp/SendLogByPrint.java | 11 ++++++++++ .../com/coderising/ood/ocp/SendLogBySMS.java | 11 ++++++++++ .../java/com/coderising/ood/srp/README.md | 4 ++++ 13 files changed, 138 insertions(+) create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByDate.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByRaw.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatLog.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/README.md create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLog.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByMail.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByPrint.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogBySMS.java create mode 100644 students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/srp/README.md diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..ba80f9de7d --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,13 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} \ No newline at end of file diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByDate.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByDate.java new file mode 100644 index 0000000000..8fcc9464cf --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByDate.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class FormatByDate implements FormatLog { + @Override + public String format(String msg) { + String txtDate = DateUtil.getCurrentDateAsString(); + return txtDate + ": " + msg; + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByRaw.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByRaw.java new file mode 100644 index 0000000000..7f66cf725f --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatByRaw.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class FormatByRaw implements FormatLog { + @Override + public String format(String msg) { + return msg; + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatLog.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatLog.java new file mode 100644 index 0000000000..6349f02b13 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/FormatLog.java @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public interface FormatLog { + + String format(String msg); +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..e107cfd906 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,21 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class Logger { + private FormatLog formatLog; + private SendLog sendLog; + + public Logger(FormatLog f, SendLog s) { + this.formatLog = f; + this.sendLog = s; + } + + public void log(String msg) { + + String logMsg = formatLog.format(msg); + sendLog.send(logMsg); + + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..42657a6066 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/README.md b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/README.md new file mode 100644 index 0000000000..35b2240cbd --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/README.md @@ -0,0 +1,4 @@ +ocp(开闭原则): +一个软件实体如类、模块和函数应该对扩展开放,对修改关闭。 + + diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..3b2add666c --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class SMSUtil { + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLog.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLog.java new file mode 100644 index 0000000000..e9a2ed4c30 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLog.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public interface SendLog { + void send(String msg); +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByMail.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByMail.java new file mode 100644 index 0000000000..047aab0bd9 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByMail.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class SendLogByMail implements SendLog { + @Override + public void send(String msg) { + MailUtil.send(msg); + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByPrint.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByPrint.java new file mode 100644 index 0000000000..86be0bc442 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogByPrint.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class SendLogByPrint implements SendLog { + @Override + public void send(String msg) { + System.out.println(msg); + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogBySMS.java b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogBySMS.java new file mode 100644 index 0000000000..0898cb2f27 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SendLogBySMS.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by john on 2017/6/20. + */ +public class SendLogBySMS implements SendLog { + @Override + public void send(String msg) { + SMSUtil.send(msg); + } +} diff --git a/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/srp/README.md b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/srp/README.md new file mode 100644 index 0000000000..34afa8edb8 --- /dev/null +++ b/students/315863321/ood/ood-assignment/src/main/java/com/coderising/ood/srp/README.md @@ -0,0 +1,4 @@ +srp(单一职责原则): +应该有且仅有一个原因引起类的变更,也就是接口或类和职责的关系是一一对应的。 + + From b1d7d953e51a74e51acd4c753596554e77b53e8a Mon Sep 17 00:00:00 2001 From: Tony-Hu Date: Tue, 20 Jun 2017 00:33:30 -0700 Subject: [PATCH 12/73] SRP --- students/370677080/ood-assignment/pom.xml | 37 +++++++ .../coderising/ood/srp/DO/ProductDetail.java | 26 +++++ .../com/coderising/ood/srp/DO/UserInfo.java | 29 ++++++ .../com/coderising/ood/srp/PromotionMail.java | 43 ++++++++ .../com/coderising/ood/srp/util/DBUtil.java | 38 ++++++++ .../com/coderising/ood/srp/util/FileUtil.java | 49 ++++++++++ .../com/coderising/ood/srp/util/MailUtil.java | 97 +++++++++++++++++++ students/370677080/ood-assignment/test.txt | 5 + 8 files changed, 324 insertions(+) create mode 100644 students/370677080/ood-assignment/pom.xml create mode 100644 students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/ProductDetail.java create mode 100644 students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/UserInfo.java create mode 100644 students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/DBUtil.java create mode 100644 students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java create mode 100644 students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java create mode 100644 students/370677080/ood-assignment/test.txt diff --git a/students/370677080/ood-assignment/pom.xml b/students/370677080/ood-assignment/pom.xml new file mode 100644 index 0000000000..d1ed73a0bf --- /dev/null +++ b/students/370677080/ood-assignment/pom.xml @@ -0,0 +1,37 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + org.jetbrains + annotations-java5 + RELEASE + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + diff --git a/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/ProductDetail.java b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/ProductDetail.java new file mode 100644 index 0000000000..7b3041a000 --- /dev/null +++ b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/ProductDetail.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp.DO; + +/** + * 产品信息数据类。 + * @since 06.18.2017 + */ +public class ProductDetail { + private String id; + private String description; + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } +} diff --git a/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/UserInfo.java b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/UserInfo.java new file mode 100644 index 0000000000..14eff3c68a --- /dev/null +++ b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/DO/UserInfo.java @@ -0,0 +1,29 @@ +package com.coderising.ood.srp.DO; + +/** + * 用户数据类。 + * @since 06.18.2017 + */ +public class UserInfo { + private String name; + private String email; + private String productDesc; + + public UserInfo(String name, String email, String productDesc){ + this.name = name; + this.email = email; + this.productDesc = productDesc; + } + + public String getName() { + return name; + } + + public String getEmail() { + return email; + } + + public String getProductDesc() { + return productDesc; + } +} diff --git a/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..2ec66a4d47 --- /dev/null +++ b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,43 @@ +package com.coderising.ood.srp; + +import com.coderising.ood.srp.DO.ProductDetail; +import com.coderising.ood.srp.DO.UserInfo; +import com.coderising.ood.srp.util.DBUtil; +import com.coderising.ood.srp.util.FileUtil; +import com.coderising.ood.srp.util.MailUtil; + +import java.io.FileNotFoundException; +import java.util.List; + +/** + * 程序入口点。 + * @since 06.19.2017 + */ +public class PromotionMail { + + public static void main(String[] args){ + final String FILE_PATH = "test.txt"; + FileUtil fileUtil; + + //尝试打开促销文件 + try { + fileUtil = new FileUtil(FILE_PATH); + } catch (FileNotFoundException e){ + System.out.println("促销文件打开失败,请确认文件路径!"); + return; + } + + sendAllEMails(fileUtil); + + fileUtil.close(); + } + + + private static void sendAllEMails(FileUtil fileUtil){ + while (fileUtil.hasNext()) { + ProductDetail productDetail = fileUtil.getNextProduct(); + List usersList = DBUtil.query(productDetail); + MailUtil.sendEmails(usersList); + } + } +} diff --git a/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/DBUtil.java b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/DBUtil.java new file mode 100644 index 0000000000..e1e0012855 --- /dev/null +++ b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/DBUtil.java @@ -0,0 +1,38 @@ +package com.coderising.ood.srp.util; +import com.coderising.ood.srp.DO.ProductDetail; +import com.coderising.ood.srp.DO.UserInfo; + +import java.util.*; + +/** + * 数据库操作类。 + * 管理数据库连接,查询等操作。 + * @since 06.19.2017 + */ +public class DBUtil { + + //TODO 此处添加数据库连接信息 + + + /** + * 应该从数据库读, 但是简化为直接生成。 + * 给一个产品详情,返回一个Array List记载所有订阅该产品的用户信息(名字,邮箱,订阅的产品名称)。 + * @param productDetail 传产品详情。产品id用来查询数据库。产品名称用于和用户信息绑定 + * @return 返回数据库中所有的查询到的结果。 + */ + public static List query(ProductDetail productDetail){ + if (productDetail == null || productDetail.getId() == null) + return new ArrayList<>(); + + String sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productDetail.getId() +"' " + + "and send_mail=1 "; + //假装用sendMilQuery查了数据库,生成了userList作为查询结果 + List userList = new ArrayList<>(); + for (int i = 1; i <= 3; i++) { + UserInfo newInfo = new UserInfo("User" + i,"aa@bb.com", productDetail.getDescription()); + userList.add(newInfo); + } + return userList; + } +} diff --git a/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java new file mode 100644 index 0000000000..991f81a537 --- /dev/null +++ b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java @@ -0,0 +1,49 @@ +package com.coderising.ood.srp.util; + + +import com.coderising.ood.srp.DO.ProductDetail; + +import java.io.File; +import java.io.FileNotFoundException; +import java.util.Scanner; + +/** + * 文件操作类。 + * 负责文件句柄的维护。 + * 此类会打开促销文件,促销文件默认按照: + * "id" 空格 "产品名称" + * 进行存储,每行一条促销信息。 + * @since 06.19.2017 + */ +public class FileUtil { + private Scanner scanner; + + + public FileUtil(String filePath) throws FileNotFoundException { + scanner = new Scanner(new File(filePath)); + } + + public ProductDetail getNextProduct(){ + String wholeInfo; + ProductDetail nextProduct = new ProductDetail(); + wholeInfo = scanner.nextLine(); + + String[] splitInfo = wholeInfo.split(" "); + if (splitInfo.length < 2) + return nextProduct; + + //促销文件按照 - "id" 空格 "产品名称" 进行记录的 + nextProduct.setId(splitInfo[0]); + nextProduct.setDescription(splitInfo[1]); + + return nextProduct; + } + + public boolean hasNext(){ + return scanner.hasNextLine(); + } + + public void close(){ + scanner.close(); + } +} diff --git a/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java new file mode 100644 index 0000000000..065286d4f9 --- /dev/null +++ b/students/370677080/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java @@ -0,0 +1,97 @@ +package com.coderising.ood.srp.util; + +import com.coderising.ood.srp.DO.UserInfo; + +import java.util.List; + + +/** + * 邮件发送类。 + * 管理邮箱连接,发送等操作。 + * @since 06.19.2017 + */ +public class MailUtil { + + /** + * SMTP连接失败异常。 + * 可用getMessage()获得异常内容。 + */ + public static class SMTPConnectionFailedException extends Throwable{ + public SMTPConnectionFailedException(String message){ + super(message); + } + } + + /** + * 主SMTP服务器地址 + */ + public static final String SMTP_SERVER = "smtp.163.com"; + + /** + * 备用SMTP服务器地址 + */ + public static final String ALT_SMTP_SERVER = "smtp1.163.com"; + + /** + * 以哪个邮箱地址发送给用户 + */ + public static final String EMAIL_ADMIN = "admin@company.com"; + + + /** + * 邮件发送操作。 + * 将降价促销邮件逐个发送给用户信息表中对应的用户。 + * 捕获SMTPConnectionFailedException。提示手动发送。并继续发送下一封邮件。 + * @param usersList 用户信息表。包含用户姓名,邮箱和订阅产品名称。 + */ + public static void sendEmails(List usersList){ + if (usersList == null) { + System.out.println("没有邮件发送"); + return; + } + + for (UserInfo info : usersList){ + if (!info.getEmail().isEmpty()) { + String emailInfo = generatePromotionEmail(info); + try { + sendPromotionEmail(emailInfo); + } catch (SMTPConnectionFailedException e){ + System.out.println("SMTP主副服务器连接失败,请手动发送以下邮件: \n"); + System.out.println(e.getMessage()); + } + } + } + } + + /** + * 假装在发邮件。默认使用主SMTP发送,若发送失败则使用备用SMTP发送。 + * 仍然失败,则抛出SMTPConnectFailException异常。 + * @param emailInfo 要发送的邮件内容 + * @throws SMTPConnectionFailedException 若主副SMTP服务器均连接失败,抛出异常。异常中包含完整的发送失败的邮件内容。可通过getMessage()方法获得邮件内容。 + */ + private static void sendPromotionEmail(String emailInfo) throws SMTPConnectionFailedException{ + //默认以SMTP_SERVER 发送 + //如果发送失败以ALT_SMTP_SERVER 重新发送 + //如果还失败,throw new SMTPConnectionFailedException(emailInfo). + } + + /** + * 根据用户信息生成促销邮件内容。 + * @param userInfo 用户信息。 + * @return 返回生成的邮件。 + */ + private static String generatePromotionEmail(UserInfo userInfo){ + StringBuilder buffer = new StringBuilder(); + + buffer.append("From:").append(EMAIL_ADMIN).append("\n"); + buffer.append("To:").append(userInfo.getEmail()).append("\n"); + buffer.append("Subject:").append("您关注的产品降价了").append("\n"); + buffer.append("Content:").append("尊敬的").append(userInfo.getName()); + buffer.append(", 您关注的产品 ").append(userInfo.getProductDesc()); + buffer.append(" 降价了,欢迎购买!").append("\n"); + + System.out.println(buffer.toString()); + + return buffer.toString(); + } +} diff --git a/students/370677080/ood-assignment/test.txt b/students/370677080/ood-assignment/test.txt new file mode 100644 index 0000000000..cb2d21edc4 --- /dev/null +++ b/students/370677080/ood-assignment/test.txt @@ -0,0 +1,5 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 +p123 From c0972747432c9672b62658ebf453a2069bdb0474 Mon Sep 17 00:00:00 2001 From: "wangxg922@chinaunincom.cn" Date: Tue, 20 Jun 2017 15:49:03 +0800 Subject: [PATCH 13/73] =?UTF-8?q?Signed-off-by:=20=E4=B8=A4=E6=AC=A1ood?= =?UTF-8?q?=E4=BD=9C=E4=B8=9A=E6=8F=90=E4=BA=A4996108220@qq.com?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/com/coderising/ood/ocp/DateUtil.java | 11 +++ .../src/com/coderising/ood/ocp/EmailLog.java | 11 +++ .../src/com/coderising/ood/ocp/LogMethod.java | 6 ++ .../src/com/coderising/ood/ocp/LogType.java | 6 ++ .../src/com/coderising/ood/ocp/Logger.java | 19 +++++ .../src/com/coderising/ood/ocp/MailUtil.java | 10 +++ .../src/com/coderising/ood/ocp/PrintLog.java | 11 +++ .../src/com/coderising/ood/ocp/RawLog.java | 10 +++ .../coderising/ood/ocp/RawLogWithData.java | 12 +++ .../src/com/coderising/ood/ocp/SMSUtil.java | 10 +++ .../src/com/coderising/ood/ocp/SmsLog.java | 10 +++ .../coderising/ood/ocp/good/Formatter.java | 7 ++ .../ood/ocp/good/FormatterFactory.java | 13 ++++ .../ood/ocp/good/HtmlFormatter.java | 11 +++ .../com/coderising/ood/ocp/good/Logger.java | 18 +++++ .../coderising/ood/ocp/good/RawFormatter.java | 11 +++ .../com/coderising/ood/ocp/good/Sender.java | 7 ++ .../com/coderising/ood/srp/Configuration.java | 23 ++++++ .../coderising/ood/srp/ConfigurationKeys.java | 9 +++ .../src/com/coderising/ood/srp/DBUtil.java | 38 ++++++++++ .../src/com/coderising/ood/srp/MailUtil.java | 74 +++++++++++++++++++ .../com/coderising/ood/srp/ProductUtil.java | 39 ++++++++++ .../com/coderising/ood/srp/PromotionMail.java | 49 ++++++++++++ .../coderising/ood/srp/product_promotion.txt | 4 + 24 files changed, 419 insertions(+) create mode 100644 students/996108220/src/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/EmailLog.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/LogMethod.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/LogType.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/Logger.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/PrintLog.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/RawLog.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/RawLogWithData.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/SmsLog.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/good/Formatter.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/good/FormatterFactory.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/good/HtmlFormatter.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/good/Logger.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/good/RawFormatter.java create mode 100644 students/996108220/src/com/coderising/ood/ocp/good/Sender.java create mode 100644 students/996108220/src/com/coderising/ood/srp/Configuration.java create mode 100644 students/996108220/src/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/996108220/src/com/coderising/ood/srp/DBUtil.java create mode 100644 students/996108220/src/com/coderising/ood/srp/MailUtil.java create mode 100644 students/996108220/src/com/coderising/ood/srp/ProductUtil.java create mode 100644 students/996108220/src/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/996108220/src/com/coderising/ood/srp/product_promotion.txt diff --git a/students/996108220/src/com/coderising/ood/ocp/DateUtil.java b/students/996108220/src/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..13369f5684 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/EmailLog.java b/students/996108220/src/com/coderising/ood/ocp/EmailLog.java new file mode 100644 index 0000000000..20eb93ac9d --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/EmailLog.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class EmailLog implements LogMethod{ + int method = 1; + @Override + public void logBehavior(String logMsg) { + + MailUtil.send(logMsg); + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/LogMethod.java b/students/996108220/src/com/coderising/ood/ocp/LogMethod.java new file mode 100644 index 0000000000..69677d8c89 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/LogMethod.java @@ -0,0 +1,6 @@ +package com.coderising.ood.ocp; + +public interface LogMethod { + int method = 0; + public abstract void logBehavior(String logMsg); +} diff --git a/students/996108220/src/com/coderising/ood/ocp/LogType.java b/students/996108220/src/com/coderising/ood/ocp/LogType.java new file mode 100644 index 0000000000..bd6de81087 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/LogType.java @@ -0,0 +1,6 @@ +package com.coderising.ood.ocp; + +public interface LogType { + int type = 0; + public abstract String getLogMsg(String msg) ; +} diff --git a/students/996108220/src/com/coderising/ood/ocp/Logger.java b/students/996108220/src/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..e0105f9b23 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,19 @@ +package com.coderising.ood.ocp; + +public class Logger { + + public LogType logType; + public LogMethod logMethod; + + public Logger(LogType logType, LogMethod logMethod){ + this.logType = logType; + this.logMethod = logMethod; + } + public void log(String msg){ + + String logMsg = logType.getLogMsg(msg); + logMethod.logBehavior(logMsg); + + } +} + diff --git a/students/996108220/src/com/coderising/ood/ocp/MailUtil.java b/students/996108220/src/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..59d77649a2 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/PrintLog.java b/students/996108220/src/com/coderising/ood/ocp/PrintLog.java new file mode 100644 index 0000000000..b2391ecd52 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/PrintLog.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class PrintLog implements LogMethod{ + int method = 3; + @Override + public void logBehavior(String logMsg) { + System.out.println(logMsg); + + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/RawLog.java b/students/996108220/src/com/coderising/ood/ocp/RawLog.java new file mode 100644 index 0000000000..0ac45244c8 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/RawLog.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class RawLog implements LogType{ + int type = 1; + @Override + public String getLogMsg(String msg) { + return msg; + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/RawLogWithData.java b/students/996108220/src/com/coderising/ood/ocp/RawLogWithData.java new file mode 100644 index 0000000000..280fb3b54f --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/RawLogWithData.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +public class RawLogWithData implements LogType{ + int type = 2; + @Override + public String getLogMsg(String msg) { + String txtDate = DateUtil.getCurrentDateAsString(); + String logMsg = txtDate + ": " + msg; + return logMsg; + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/SMSUtil.java b/students/996108220/src/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..fab4cd01b7 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/SmsLog.java b/students/996108220/src/com/coderising/ood/ocp/SmsLog.java new file mode 100644 index 0000000000..e61938d844 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/SmsLog.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SmsLog implements LogMethod{ + int method = 2; + @Override + public void logBehavior(String logMsg) { + SMSUtil.send(logMsg); + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/good/Formatter.java b/students/996108220/src/com/coderising/ood/ocp/good/Formatter.java new file mode 100644 index 0000000000..b6e2ccbc16 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/good/Formatter.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp.good; + +public interface Formatter { + + String format(String msg); + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/good/FormatterFactory.java b/students/996108220/src/com/coderising/ood/ocp/good/FormatterFactory.java new file mode 100644 index 0000000000..3c2009a674 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/good/FormatterFactory.java @@ -0,0 +1,13 @@ +package com.coderising.ood.ocp.good; + +public class FormatterFactory { + public static Formatter createFormatter(int type){ + if(type == 1){ + return new RawFormatter(); + } + if (type == 2){ + return new HtmlFormatter(); + } + return null; + } +} diff --git a/students/996108220/src/com/coderising/ood/ocp/good/HtmlFormatter.java b/students/996108220/src/com/coderising/ood/ocp/good/HtmlFormatter.java new file mode 100644 index 0000000000..3d375f5acc --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/good/HtmlFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.good; + +public class HtmlFormatter implements Formatter { + + @Override + public String format(String msg) { + + return null; + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/good/Logger.java b/students/996108220/src/com/coderising/ood/ocp/good/Logger.java new file mode 100644 index 0000000000..f206472d0d --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/good/Logger.java @@ -0,0 +1,18 @@ +package com.coderising.ood.ocp.good; + +public class Logger { + + private Formatter formatter; + private Sender sender; + + public Logger(Formatter formatter,Sender sender){ + this.formatter = formatter; + this.sender = sender; + } + public void log(String msg){ + sender.send(formatter.format(msg)) ; + } + + +} + diff --git a/students/996108220/src/com/coderising/ood/ocp/good/RawFormatter.java b/students/996108220/src/com/coderising/ood/ocp/good/RawFormatter.java new file mode 100644 index 0000000000..7f1cb4ae30 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/good/RawFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.good; + +public class RawFormatter implements Formatter { + + @Override + public String format(String msg) { + + return null; + } + +} diff --git a/students/996108220/src/com/coderising/ood/ocp/good/Sender.java b/students/996108220/src/com/coderising/ood/ocp/good/Sender.java new file mode 100644 index 0000000000..aaa46c1fb7 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/ocp/good/Sender.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp.good; + +public interface Sender { + + void send(String msg); + +} diff --git a/students/996108220/src/com/coderising/ood/srp/Configuration.java b/students/996108220/src/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..f328c1816a --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/996108220/src/com/coderising/ood/srp/ConfigurationKeys.java b/students/996108220/src/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..8695aed644 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/996108220/src/com/coderising/ood/srp/DBUtil.java b/students/996108220/src/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..683ce1712e --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,38 @@ +package com.coderising.ood.srp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + static ProductUtil productUtil=new ProductUtil(); + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com"); + userList.add(userInfo); + } + + return userList; + } + protected static List loadMailingList() throws Exception { + + String sendMailQuery = LoadQuery(); + return DBUtil.query(sendMailQuery); + } + protected static String LoadQuery() throws Exception { + String productID = productUtil.getProductID(); + System.out.println("loadQuery set"); + return "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + } +} diff --git a/students/996108220/src/com/coderising/ood/srp/MailUtil.java b/students/996108220/src/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..38ad395d83 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,74 @@ +package com.coderising.ood.srp; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Map; + +public class MailUtil { + + private static Configuration config=new Configuration(); ; + private static ProductUtil productUtil = new ProductUtil(); + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + protected static void sendEmail(String userName,String toAddress,String smtpHost,Boolean debug) throws IOException + { + String subject = "您关注的产品降价了"; + String message = "尊敬的 "+userName+", 您关注的产品 " + productUtil.getProductDesc() + " 降价了,欢迎购买!" ; + String fromAddress=config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer); + } + + + + private static void sendEmail(String userName,String toAddress,Boolean debug) { + try + { + String smtpHost=config.getProperty(ConfigurationKeys.SMTP_SERVER); + sendEmail( userName,toAddress,smtpHost, debug); + } + catch (Exception e) + { + + try { + String altSmtpHost=config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + sendEmail( userName,toAddress,altSmtpHost, debug); + + } catch (Exception e2) + { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + } + } + + protected static void sendEMails(boolean debug,List mailingList) throws IOException + { + + System.out.println("开始发送邮件"); + + + if (mailingList != null) { + Iterator iter = mailingList.iterator(); + while (iter.hasNext()) { + HashMap userInfo = (HashMap)iter.next(); + String userName = userInfo.get(NAME_KEY); + String toAddress = userInfo.get(EMAIL_KEY); + sendEmail( userName, toAddress, debug); + } + } + + else { + System.out.println("没有邮件发送"); + } + + } + + +} diff --git a/students/996108220/src/com/coderising/ood/srp/ProductUtil.java b/students/996108220/src/com/coderising/ood/srp/ProductUtil.java new file mode 100644 index 0000000000..be40fd203c --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/ProductUtil.java @@ -0,0 +1,39 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; + +public class ProductUtil { + private String productConfigPath="D:\\JavaCoding\\students\\996108220\\src" + + "\\com\\coderising\\ood\\srp\\product_promotion.txt"; + + private String[] readFile() throws IOException // @02C + { + File file=new File(productConfigPath); + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" ");; + return data; + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + public String getProductID() throws IOException { + String[] data= readFile(); + return data[0]; + } + + public String getProductDesc() throws IOException { + String[] data= readFile(); + return data[1]; + } + +} diff --git a/students/996108220/src/com/coderising/ood/srp/PromotionMail.java b/students/996108220/src/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..2795a54b2a --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,49 @@ + package com.coderising.ood.srp; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Map; + +public class PromotionMail { + + //读取用户信息 + + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + + public static void main(String[] args) throws Exception { + + boolean emailDebug = false; + PromotionMail pe = new PromotionMail(); + List userInfo = DBUtil.loadMailingList(); + List mailingList = pe.filterUserInfo(userInfo); + MailUtil.sendEMails(emailDebug, mailingList); + } + + + + + protected List filterUserInfo(List userList) throws IOException + { + + if (userList != null) { + Iterator iter = userList.iterator(); + while (iter.hasNext()) { + HashMap userInfo = (HashMap)iter.next(); + String userName = userInfo.get(NAME_KEY); + String toAddress = userInfo.get(EMAIL_KEY); + if (toAddress.length() <= 0) + userInfo.remove(userInfo); + } + } + return userList; + + } + + + + +} diff --git a/students/996108220/src/com/coderising/ood/srp/product_promotion.txt b/students/996108220/src/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..0c0124cc61 --- /dev/null +++ b/students/996108220/src/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From c795b439753c8a8805c6c55f6557aa10c43a327d Mon Sep 17 00:00:00 2001 From: zhizx Date: Tue, 20 Jun 2017 18:11:48 +0800 Subject: [PATCH 14/73] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E6=8F=90=E4=BA=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/919442958/README.md | 1 + 1 file changed, 1 insertion(+) create mode 100644 students/919442958/README.md diff --git a/students/919442958/README.md b/students/919442958/README.md new file mode 100644 index 0000000000..60472c8281 --- /dev/null +++ b/students/919442958/README.md @@ -0,0 +1 @@ +这是919442958的作业。 \ No newline at end of file From 6a71fd336dddb0944256090a25d011fcd922f837 Mon Sep 17 00:00:00 2001 From: fengdz Date: Tue, 20 Jun 2017 18:35:12 +0800 Subject: [PATCH 15/73] =?UTF-8?q?=E5=88=9B=E5=BB=BA=E8=B4=A3=E4=BB=BB?= =?UTF-8?q?=E5=8C=85=EF=BC=8C=E6=8E=A5=E5=8F=A3=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/281918307/ood-srp/pom.xml | 58 +++++++++-- .../main/java/com/ood/srp/Application.java | 18 ++-- .../java/com/ood/srp/file/FileService.java | 18 ++++ .../java/com/ood/srp/mail/Configuration.java | 23 +++++ .../com/ood/srp/mail/ConfigurationKeys.java | 9 ++ .../java/com/ood/srp/mail/MailService.java | 8 ++ .../com/ood/srp/product/ProductDetail.java | 26 +++++ .../ood/srp/product/ProductDetailService.java | 9 ++ .../ood/srp/promotion/PromotionService.java | 31 ++++++ .../main/java/com/ood/srp/user/UserInfo.java | 29 ++++++ .../com/ood/srp/user/UserInfoService.java | 9 ++ .../main/java/com/ood/srp/util/DBUtil.java | 43 ++++++++ .../main/java/com/ood/srp/util/FileUtil.java | 50 ++++++++++ .../main/java/com/ood/srp/util/MailUtil.java | 97 +++++++++++++++++++ .../src/main/resources/application.properties | 2 + students/281918307/pom.xml | 27 ++++++ 16 files changed, 443 insertions(+), 14 deletions(-) create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java create mode 100644 students/281918307/ood-srp/src/main/resources/application.properties diff --git a/students/281918307/ood-srp/pom.xml b/students/281918307/ood-srp/pom.xml index cfd98a73b1..13db2a5ad0 100644 --- a/students/281918307/ood-srp/pom.xml +++ b/students/281918307/ood-srp/pom.xml @@ -14,18 +14,62 @@ ood-srp jar - + + + + org.springframework.boot + spring-boot-starter-web + - junit - junit - test + org.springframework.boot + spring-boot-starter-test + + + org.springframework.boot + spring-boot-starter-freemarker + + - log4j - log4j + org.springframework.boot + spring-boot-starter-data-redis + + + + + org.springframework.boot + spring-boot-devtools + provided + true + + + org.apache.tomcat.embed + tomcat-embed-core - + + + + org.springframework.boot + spring-boot-maven-plugin + + com.dajia.customization.Application + -Dfile.encoding=${project.build.sourceEncoding} + + true + + + + + repackage + + + + + + + + \ No newline at end of file diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java index f8b7fdd190..bc76120dd9 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/Application.java @@ -1,14 +1,18 @@ package com.ood.srp; -import org.apache.log4j.Logger; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.boot.context.properties.EnableConfigurationProperties; +import org.springframework.context.annotation.ComponentScan; /** - * Created by ajaxfeng on 2017/6/20. + * Created by ajaxfeng on 2017/4/28. */ +@SpringBootApplication +@EnableConfigurationProperties +@ComponentScan("com.ood.srp") public class Application { - static final Logger logger = Logger.getLogger(Application.class); - - public static void main(String [] args) { - logger.error("Application running ..."); + public static void main(String[] args) throws Exception { + SpringApplication.run(Application.class, args); } -} +} \ No newline at end of file diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java new file mode 100644 index 0000000000..301bb6d845 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java @@ -0,0 +1,18 @@ +package com.ood.srp.file; + +import java.io.File; +import java.util.List; + +/** + * 读取文件内容 + * Created by ajaxfeng on 2017/6/20. + */ +public interface FileService { + + /** + * 读取文件内容,放到List内 + * @param file + * @return + */ + List readFile(File file); +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java new file mode 100644 index 0000000000..48ea71dec5 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java @@ -0,0 +1,23 @@ +package com.ood.srp.mail; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java new file mode 100644 index 0000000000..74cc19304a --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.ood.srp.mail; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java new file mode 100644 index 0000000000..55ddcffc56 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java @@ -0,0 +1,8 @@ +package com.ood.srp.mail; + +/** + * Created by ajaxfeng on 2017/6/20. + */ +public interface MailService { + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java new file mode 100644 index 0000000000..edcce88eee --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java @@ -0,0 +1,26 @@ +package com.ood.srp.product; + +/** + * 产品信息数据类。 + * @since 06.18.2017 + */ +public class ProductDetail { + private String id; + private String description; + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java new file mode 100644 index 0000000000..1bc54a563a --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java @@ -0,0 +1,9 @@ +package com.ood.srp.product; + +/** + * 产品信息 + * Created by ajaxfeng on 2017/6/20. + */ +public interface ProductDetailService { + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java new file mode 100644 index 0000000000..9ce8a39fe0 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java @@ -0,0 +1,31 @@ +package com.ood.srp.promotion; + +import com.ood.srp.product.ProductDetail; +import com.ood.srp.user.UserInfo; + +import java.util.List; + +/** + * 促销处理类 + * Created by ajaxfeng on 2017/6/20. + */ +public interface PromotionService { + /** + * 获取产品信息 + * @return + */ + List getPromotionProduct(); + + /** + * 获取用户信息 + * @return + */ + List getPromotionUserInfo(); + + /** + * 发送促销信息 + * @return + */ + List sendPromotionInfo(); + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java new file mode 100644 index 0000000000..65cc00ea39 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java @@ -0,0 +1,29 @@ +package com.ood.srp.user; + +/** + * 用户数据类。 + * @since 06.18.2017 + */ +public class UserInfo { + private String name; + private String email; + private String productDesc; + + public UserInfo(String name, String email, String productDesc){ + this.name = name; + this.email = email; + this.productDesc = productDesc; + } + + public String getName() { + return name; + } + + public String getEmail() { + return email; + } + + public String getProductDesc() { + return productDesc; + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java new file mode 100644 index 0000000000..e828597d4d --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java @@ -0,0 +1,9 @@ +package com.ood.srp.user; + +/** + * 用户逻辑 + * Created by ajaxfeng on 2017/6/20. + */ +public interface UserInfoService { + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java new file mode 100644 index 0000000000..820bbb5dcf --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java @@ -0,0 +1,43 @@ +package com.ood.srp.util; + + +import com.ood.srp.product.ProductDetail; +import com.ood.srp.user.UserInfo; + +import java.util.ArrayList; +import java.util.List; + +/** + * 数据库操作类。 + * 管理数据库连接,查询等操作。 + * + * @since 06.19.2017 + */ +public class DBUtil { + + //TODO 此处添加数据库连接信息 + + + /** + * 应该从数据库读, 但是简化为直接生成。 + * 给一个产品详情,返回一个Array List记载所有订阅该产品的用户信息(名字,邮箱,订阅的产品名称)。 + * + * @param productDetail 传产品详情。产品id用来查询数据库。产品名称用于和用户信息绑定 + * @return 返回数据库中所有的查询到的结果。 + */ + public static List query(ProductDetail productDetail) { + if (productDetail == null || productDetail.getId() == null) + return new ArrayList<>(); + + String sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productDetail.getId() + "' " + + "and send_mail=1 "; + //假装用sendMilQuery查了数据库,生成了userList作为查询结果 + List userList = new ArrayList<>(); + for (int i = 1; i <= 3; i++) { + UserInfo newInfo = new UserInfo("User" + i, "aa@bb.com", productDetail.getDescription()); + userList.add(newInfo); + } + return userList; + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java new file mode 100644 index 0000000000..060ef0287a --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java @@ -0,0 +1,50 @@ +package com.ood.srp.util; + + + +import com.ood.srp.product.ProductDetail; + +import java.io.File; +import java.io.FileNotFoundException; +import java.util.Scanner; + +/** + * 文件操作类。 + * 负责文件句柄的维护。 + * 此类会打开促销文件,促销文件默认按照: + * "id" 空格 "产品名称" + * 进行存储,每行一条促销信息。 + * @since 06.19.2017 + */ +public class FileUtil { + private Scanner scanner; + + + public FileUtil(String filePath) throws FileNotFoundException { + scanner = new Scanner(new File(filePath)); + } + + public ProductDetail getNextProduct(){ + String wholeInfo; + ProductDetail nextProduct = new ProductDetail(); + wholeInfo = scanner.nextLine(); + + String[] splitInfo = wholeInfo.split(" "); + if (splitInfo.length < 2) + return nextProduct; + + //促销文件按照 - "id" 空格 "产品名称" 进行记录的 + nextProduct.setId(splitInfo[0]); + nextProduct.setDescription(splitInfo[1]); + + return nextProduct; + } + + public boolean hasNext(){ + return scanner.hasNextLine(); + } + + public void close(){ + scanner.close(); + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java new file mode 100644 index 0000000000..2f3463e1d8 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java @@ -0,0 +1,97 @@ +package com.ood.srp.util; + + +import com.ood.srp.user.UserInfo; + +import java.util.List; + +/** + * 邮件发送类。 + * 管理邮箱连接,发送等操作。 + * @since 06.19.2017 + */ +public class MailUtil { + + /** + * SMTP连接失败异常。 + * 可用getMessage()获得异常内容。 + */ + public static class SMTPConnectionFailedException extends Throwable{ + public SMTPConnectionFailedException(String message){ + super(message); + } + } + + /** + * 主SMTP服务器地址 + */ + public static final String SMTP_SERVER = "smtp.163.com"; + + /** + * 备用SMTP服务器地址 + */ + public static final String ALT_SMTP_SERVER = "smtp1.163.com"; + + /** + * 以哪个邮箱地址发送给用户 + */ + public static final String EMAIL_ADMIN = "admin@company.com"; + + + /** + * 邮件发送操作。 + * 将降价促销邮件逐个发送给用户信息表中对应的用户。 + * 捕获SMTPConnectionFailedException。提示手动发送。并继续发送下一封邮件。 + * @param usersList 用户信息表。包含用户姓名,邮箱和订阅产品名称。 + */ + public static void sendEmails(List usersList){ + if (usersList == null) { + System.out.println("没有邮件发送"); + return; + } + + for (UserInfo info : usersList){ + if (!info.getEmail().isEmpty()) { + String emailInfo = generatePromotionEmail(info); + try { + sendPromotionEmail(emailInfo); + } catch (SMTPConnectionFailedException e){ + System.out.println("SMTP主副服务器连接失败,请手动发送以下邮件: \n"); + System.out.println(e.getMessage()); + } + } + } + } + + /** + * 假装在发邮件。默认使用主SMTP发送,若发送失败则使用备用SMTP发送。 + * 仍然失败,则抛出SMTPConnectFailException异常。 + * @param emailInfo 要发送的邮件内容 + * @throws SMTPConnectionFailedException 若主副SMTP服务器均连接失败,抛出异常。异常中包含完整的发送失败的邮件内容。可通过getMessage()方法获得邮件内容。 + */ + private static void sendPromotionEmail(String emailInfo) throws SMTPConnectionFailedException{ + //默认以SMTP_SERVER 发送 + //如果发送失败以ALT_SMTP_SERVER 重新发送 + //如果还失败,throw new SMTPConnectionFailedException(emailInfo). + } + + /** + * 根据用户信息生成促销邮件内容。 + * @param userInfo 用户信息。 + * @return 返回生成的邮件。 + */ + private static String generatePromotionEmail(UserInfo userInfo){ + StringBuilder buffer = new StringBuilder(); + + buffer.append("From:").append(EMAIL_ADMIN).append("\n"); + buffer.append("To:").append(userInfo.getEmail()).append("\n"); + buffer.append("Subject:").append("您关注的产品降价了").append("\n"); + buffer.append("Content:").append("尊敬的").append(userInfo.getName()); + buffer.append(", 您关注的产品 ").append(userInfo.getProductDesc()); + buffer.append(" 降价了,欢迎购买!").append("\n"); + + System.out.println(buffer.toString()); + + return buffer.toString(); + } +} diff --git a/students/281918307/ood-srp/src/main/resources/application.properties b/students/281918307/ood-srp/src/main/resources/application.properties new file mode 100644 index 0000000000..a7e97d369d --- /dev/null +++ b/students/281918307/ood-srp/src/main/resources/application.properties @@ -0,0 +1,2 @@ +server.port=8080 +spring.application.name=ood-srp diff --git a/students/281918307/pom.xml b/students/281918307/pom.xml index cfbb6af460..61717fdeb7 100644 --- a/students/281918307/pom.xml +++ b/students/281918307/pom.xml @@ -15,14 +15,41 @@ + + + aliyun maven + http://maven.aliyun.com/nexus/content/groups/public + + + maven.nuxeo.org + http://maven.nuxeo.org/nexus/content/groups/public/ + + + + + UTF-8 + 1.8 + UTF-8 + 1.5.3.RELEASE + + + + + org.springframework.boot + spring-boot-dependencies + ${spring.boot.version} + pom + import + + junit junit From 5d605f40ceb1e9e25847b0164a8da74618cd701b Mon Sep 17 00:00:00 2001 From: mac_ck Date: Tue, 20 Jun 2017 21:58:21 +0800 Subject: [PATCH 16/73] finish srp and ocp homework --- students/471398827/ood-assignment/pom.xml | 32 +++++++++ .../java/com/coderising/ood/ocp/Config.java | 12 ++++ .../com/coderising/ood/ocp/DateMessage.java | 11 ++++ .../java/com/coderising/ood/ocp/DateUtil.java | 10 +++ .../java/com/coderising/ood/ocp/ILog.java | 8 +++ .../java/com/coderising/ood/ocp/IMessage.java | 8 +++ .../com/coderising/ood/ocp/LogFactory.java | 25 +++++++ .../java/com/coderising/ood/ocp/Logger.java | 22 +++++++ .../java/com/coderising/ood/ocp/MailUtil.java | 10 +++ .../coderising/ood/ocp/MessageFactory.java | 20 ++++++ .../com/coderising/ood/ocp/PrintUtil.java | 11 ++++ .../com/coderising/ood/ocp/RawMessage.java | 11 ++++ .../java/com/coderising/ood/ocp/SMSUtil.java | 11 ++++ .../com/coderising/ood/srp/Configuration.java | 26 ++++++++ .../coderising/ood/srp/ConfigurationKeys.java | 10 +++ .../java/com/coderising/ood/srp/DBUtil.java | 25 +++++++ .../java/com/coderising/ood/srp/Mail.java | 18 +++++ .../java/com/coderising/ood/srp/MailUtil.java | 53 +++++++++++++++ .../java/com/coderising/ood/srp/Message.java | 65 +++++++++++++++++++ .../java/com/coderising/ood/srp/Product.java | 33 ++++++++++ .../coderising/ood/srp/ProductFactory.java | 36 ++++++++++ .../com/coderising/ood/srp/PromotionMail.java | 51 +++++++++++++++ .../java/com/coderising/ood/srp/User.java | 32 +++++++++ .../coderising/ood/srp/product_promotion.txt | 4 ++ 24 files changed, 544 insertions(+) create mode 100644 students/471398827/ood-assignment/pom.xml create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt diff --git a/students/471398827/ood-assignment/pom.xml b/students/471398827/ood-assignment/pom.xml new file mode 100644 index 0000000000..cac49a5328 --- /dev/null +++ b/students/471398827/ood-assignment/pom.xml @@ -0,0 +1,32 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java new file mode 100644 index 0000000000..13520f693c --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class Config { + public static final int RAW_LOG = 1; + public static final int RAW_LOG_WITH_DATE = 2; + public static final int EMAIL_LOG = 1; + public static final int SMS_LOG = 2; + public static final int PRINT_LOG = 3; +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java new file mode 100644 index 0000000000..cac875e053 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class DateMessage implements IMessage{ + @Override + public String getMessage(String msg) { + return DateUtil.getCurrentDateAsString() + msg; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..e9d919c378 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return "date : 8/20 "; + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java new file mode 100644 index 0000000000..40a34666b8 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public interface ILog { + public void printLog(String msg); +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java new file mode 100644 index 0000000000..2ec8103863 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public interface IMessage { + public String getMessage(String msg); +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java new file mode 100644 index 0000000000..8ba78c7b1d --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java @@ -0,0 +1,25 @@ +package com.coderising.ood.ocp; + +import com.coderising.ood.srp.Mail; + +/** + * Created by szf on 6/20/17. + */ +public class LogFactory { + + static ILog produce(int logMethod) { + ILog log = null; + switch (logMethod) { + case Config.EMAIL_LOG: + log = new MailUtil(); + break; + case Config.SMS_LOG: + log = new SMSUtil(); + break; + case Config.PRINT_LOG: + log = new PrintUtil(); + break; + } + return log; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..c0579975de --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,22 @@ +package com.coderising.ood.ocp; + +public class Logger { + ILog myLog; + IMessage myMessage; + + public Logger(int logType, int logMethod){ + myMessage = MessageFactory.produce(logType); + myLog = LogFactory.produce(logMethod); + } + public void log(String msg){ + + myLog.printLog(myMessage.getMessage(msg)); + + } + + public static void main(String[] args) { + Logger logger = new Logger(Config.RAW_LOG_WITH_DATE, Config.EMAIL_LOG); + logger.log("this is a log message"); + } +} + diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..76d830742a --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil implements ILog{ + + @Override + public void printLog(String msg) { + msg = "Mail..." + "\n" + msg; + System.out.println(msg); + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java new file mode 100644 index 0000000000..10faf8f6d0 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java @@ -0,0 +1,20 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class MessageFactory { + + static IMessage produce(int messageType) { + IMessage msg = null; + switch (messageType) { + case Config.RAW_LOG: + msg = new RawMessage(); + break; + case Config.RAW_LOG_WITH_DATE: + msg = new DateMessage(); + break; + } + return msg; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java new file mode 100644 index 0000000000..4e337a3d42 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class PrintUtil implements ILog{ + @Override + public void printLog(String msg) { + System.out.println(msg); + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java new file mode 100644 index 0000000000..0d6c48a796 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class RawMessage implements IMessage{ + @Override + public String getMessage(String msg) { + return msg; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..c85286a465 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class SMSUtil implements ILog{ + + @Override + public void printLog(String msg) { + msg = "SMS..." + "\n" + msg; + System.out.println(msg); + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..bd0db32d2a --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static boolean MAIL_DEBUG = false; + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + configurations.put(ConfigurationKeys.FILE_PATH, "/Users/szf/git/coding2017/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public static String getProperty(String key) { + + return configurations.get(key); + + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..d4acd3240f --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,10 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + public static final String FILE_PATH = "file.path"; + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..140d505a65 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + String userName = "User" + i; + String email = "aa@bb.com"; + User user = new User(userName, email); + userList.add(user); + } + + return userList; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java new file mode 100644 index 0000000000..231947248d --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java @@ -0,0 +1,18 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class Mail { + private String host; + + public Mail(String host) { + this.host = host; + } + + public boolean send(Message msg) throws Exception { + System.out.println("Host: " + this.host); + msg.print(); + return true; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..502a7d96f0 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,53 @@ +package com.coderising.ood.srp; + +public class MailUtil { + private static Mail firstSMPTHost, secondSMPTHost; + + static { + String host1 = Configuration.getProperty(ConfigurationKeys.SMTP_SERVER); + String host2 = Configuration.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + firstSMPTHost = new Mail(host1); + secondSMPTHost = new Mail(host2); + } + + + public static void sendEmail(Message msg) throws Exception{ + //假装发了一封邮件 + + if (msg != null) { + + System.out.println("开始发送邮件"); + + if (msg.checkFormat()) { + + System.out.println("发送邮件..."); + + try { + + firstSMPTHost.send(msg); + + System.out.println("发送邮件成功"); + + } catch (Exception e) { + try { + + secondSMPTHost.send(msg); + + } catch (Exception e2) { + + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + + } + } + } else { + + System.out.println("邮件格式不对"); + + } + } else { + + System.out.println("没有邮件发送"); + + } + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java new file mode 100644 index 0000000000..a0a16d2756 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java @@ -0,0 +1,65 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class Message { + private String toAddress; + private String fromAddress; + private String subject; + private String message; + + public Message(String toAddress, String fromAddress, String subject, String message) { + this.toAddress = toAddress; + this.fromAddress = fromAddress; + this.subject = subject; + this.message = message; + } + + public void print() { + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + } + + public boolean checkFormat() { + return true; + } + + public String getToAddress() { + + return toAddress; + } + + public void setToAddress(String toAddress) { + this.toAddress = toAddress; + } + + public String getFromAddress() { + return fromAddress; + } + + public void setFromAddress(String fromAddress) { + this.fromAddress = fromAddress; + } + + public String getSubject() { + return subject; + } + + public void setSubject(String subject) { + this.subject = subject; + } + + public String getMessage() { + return message; + } + + public void setMessage(String message) { + this.message = message; + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java new file mode 100644 index 0000000000..5662ace67d --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java @@ -0,0 +1,33 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class Product { + public String getProductId() { + return productId; + } + + public Product(String productId, String productDesc) { + this.productId = productId; + this.productDesc = productDesc; + } + + public Product() { + } + + public void setProductId(String productId) { + this.productId = productId; + } + + public String getProductDesc() { + return productDesc; + } + + public void setProductDesc(String productDesc) { + this.productDesc = productDesc; + } + + private String productId; + private String productDesc; +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java new file mode 100644 index 0000000000..f7366c27e4 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java @@ -0,0 +1,36 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +/** + * Created by szf on 6/20/17. + */ +public class ProductFactory { + List getNewProdcuts(File file) throws IOException { + BufferedReader br = null; + List newProducts = new ArrayList<>(); + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + Product product = new Product(data[0], data[1]); + newProducts.add(product); + + System.out.println("产品ID = " + product.getProductId() + "\n"); + System.out.println("产品描述 = " + product.getProductDesc() + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + return newProducts; + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..fa90f9a539 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,51 @@ +package com.coderising.ood.srp; +import java.io.File; +import java.util.List; + +public class PromotionMail { + + + public static void main(String[] args) throws Exception { + + PromotionMail pe = new PromotionMail(); + + } + + + public PromotionMail() throws Exception { + + if (Configuration.MAIL_DEBUG) { + System.out.println("debugging..."); + } + + ProductFactory factory = new ProductFactory(); + + File file = new File(Configuration.getProperty(ConfigurationKeys.FILE_PATH)); + List products = factory.getNewProdcuts(file); + + String productID = "1"; + String sql = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + List users = DBUtil.query(sql); + + + for (User user : users) { + for (Product product : products) { + + String to_address = user.getEmail(); + String from_address = Configuration.getProperty(ConfigurationKeys.EMAIL_ADMIN); + String subject = "您关注的产品降价了"; + String message = "尊敬的 "+ user.getName() + ", 您关注的产品 " + product.getProductDesc() + " 降价了,欢迎购买!" ; + + Message msg = new Message(to_address, from_address, subject, message); + + MailUtil.sendEmail(msg); + } + + } + } + + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java new file mode 100644 index 0000000000..225f98b727 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java @@ -0,0 +1,32 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class User { + private String Name; + + public User(String name, String email) { + Name = name; + Email = email; + } + + public String getName() { + + return Name; + } + + public void setName(String name) { + Name = name; + } + + public String getEmail() { + return Email; + } + + public void setEmail(String email) { + Email = email; + } + + private String Email; +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..0c0124cc61 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From ded54f42b79548eba9c956c76598f9e2ccaf6c89 Mon Sep 17 00:00:00 2001 From: mac_ck Date: Tue, 20 Jun 2017 21:58:21 +0800 Subject: [PATCH 17/73] finish srp and ocp homework --- students/471398827/ood-assignment/pom.xml | 32 +++++++++ .../java/com/coderising/ood/ocp/Config.java | 12 ++++ .../com/coderising/ood/ocp/DateMessage.java | 11 ++++ .../java/com/coderising/ood/ocp/DateUtil.java | 10 +++ .../java/com/coderising/ood/ocp/ILog.java | 8 +++ .../java/com/coderising/ood/ocp/IMessage.java | 8 +++ .../com/coderising/ood/ocp/LogFactory.java | 25 +++++++ .../java/com/coderising/ood/ocp/Logger.java | 22 +++++++ .../java/com/coderising/ood/ocp/MailUtil.java | 10 +++ .../coderising/ood/ocp/MessageFactory.java | 20 ++++++ .../com/coderising/ood/ocp/PrintUtil.java | 11 ++++ .../com/coderising/ood/ocp/RawMessage.java | 11 ++++ .../java/com/coderising/ood/ocp/SMSUtil.java | 11 ++++ .../com/coderising/ood/srp/Configuration.java | 26 ++++++++ .../coderising/ood/srp/ConfigurationKeys.java | 10 +++ .../java/com/coderising/ood/srp/DBUtil.java | 25 +++++++ .../java/com/coderising/ood/srp/Mail.java | 18 +++++ .../java/com/coderising/ood/srp/MailUtil.java | 53 +++++++++++++++ .../java/com/coderising/ood/srp/Message.java | 65 +++++++++++++++++++ .../java/com/coderising/ood/srp/Product.java | 33 ++++++++++ .../coderising/ood/srp/ProductFactory.java | 36 ++++++++++ .../com/coderising/ood/srp/PromotionMail.java | 51 +++++++++++++++ .../java/com/coderising/ood/srp/User.java | 32 +++++++++ .../coderising/ood/srp/product_promotion.txt | 4 ++ 24 files changed, 544 insertions(+) create mode 100644 students/471398827/ood-assignment/pom.xml create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java create mode 100644 students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt diff --git a/students/471398827/ood-assignment/pom.xml b/students/471398827/ood-assignment/pom.xml new file mode 100644 index 0000000000..cac49a5328 --- /dev/null +++ b/students/471398827/ood-assignment/pom.xml @@ -0,0 +1,32 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java new file mode 100644 index 0000000000..13520f693c --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Config.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class Config { + public static final int RAW_LOG = 1; + public static final int RAW_LOG_WITH_DATE = 2; + public static final int EMAIL_LOG = 1; + public static final int SMS_LOG = 2; + public static final int PRINT_LOG = 3; +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java new file mode 100644 index 0000000000..cac875e053 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateMessage.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class DateMessage implements IMessage{ + @Override + public String getMessage(String msg) { + return DateUtil.getCurrentDateAsString() + msg; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..e9d919c378 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return "date : 8/20 "; + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java new file mode 100644 index 0000000000..40a34666b8 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/ILog.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public interface ILog { + public void printLog(String msg); +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java new file mode 100644 index 0000000000..2ec8103863 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/IMessage.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public interface IMessage { + public String getMessage(String msg); +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java new file mode 100644 index 0000000000..8ba78c7b1d --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/LogFactory.java @@ -0,0 +1,25 @@ +package com.coderising.ood.ocp; + +import com.coderising.ood.srp.Mail; + +/** + * Created by szf on 6/20/17. + */ +public class LogFactory { + + static ILog produce(int logMethod) { + ILog log = null; + switch (logMethod) { + case Config.EMAIL_LOG: + log = new MailUtil(); + break; + case Config.SMS_LOG: + log = new SMSUtil(); + break; + case Config.PRINT_LOG: + log = new PrintUtil(); + break; + } + return log; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..c0579975de --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,22 @@ +package com.coderising.ood.ocp; + +public class Logger { + ILog myLog; + IMessage myMessage; + + public Logger(int logType, int logMethod){ + myMessage = MessageFactory.produce(logType); + myLog = LogFactory.produce(logMethod); + } + public void log(String msg){ + + myLog.printLog(myMessage.getMessage(msg)); + + } + + public static void main(String[] args) { + Logger logger = new Logger(Config.RAW_LOG_WITH_DATE, Config.EMAIL_LOG); + logger.log("this is a log message"); + } +} + diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..76d830742a --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil implements ILog{ + + @Override + public void printLog(String msg) { + msg = "Mail..." + "\n" + msg; + System.out.println(msg); + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java new file mode 100644 index 0000000000..10faf8f6d0 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/MessageFactory.java @@ -0,0 +1,20 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class MessageFactory { + + static IMessage produce(int messageType) { + IMessage msg = null; + switch (messageType) { + case Config.RAW_LOG: + msg = new RawMessage(); + break; + case Config.RAW_LOG_WITH_DATE: + msg = new DateMessage(); + break; + } + return msg; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java new file mode 100644 index 0000000000..4e337a3d42 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/PrintUtil.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class PrintUtil implements ILog{ + @Override + public void printLog(String msg) { + System.out.println(msg); + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java new file mode 100644 index 0000000000..0d6c48a796 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/RawMessage.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +/** + * Created by szf on 6/20/17. + */ +public class RawMessage implements IMessage{ + @Override + public String getMessage(String msg) { + return msg; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..c85286a465 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class SMSUtil implements ILog{ + + @Override + public void printLog(String msg) { + msg = "SMS..." + "\n" + msg; + System.out.println(msg); + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..bd0db32d2a --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static boolean MAIL_DEBUG = false; + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + configurations.put(ConfigurationKeys.FILE_PATH, "/Users/szf/git/coding2017/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public static String getProperty(String key) { + + return configurations.get(key); + + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..d4acd3240f --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,10 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + public static final String FILE_PATH = "file.path"; + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..140d505a65 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + String userName = "User" + i; + String email = "aa@bb.com"; + User user = new User(userName, email); + userList.add(user); + } + + return userList; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java new file mode 100644 index 0000000000..231947248d --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Mail.java @@ -0,0 +1,18 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class Mail { + private String host; + + public Mail(String host) { + this.host = host; + } + + public boolean send(Message msg) throws Exception { + System.out.println("Host: " + this.host); + msg.print(); + return true; + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..502a7d96f0 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,53 @@ +package com.coderising.ood.srp; + +public class MailUtil { + private static Mail firstSMPTHost, secondSMPTHost; + + static { + String host1 = Configuration.getProperty(ConfigurationKeys.SMTP_SERVER); + String host2 = Configuration.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + firstSMPTHost = new Mail(host1); + secondSMPTHost = new Mail(host2); + } + + + public static void sendEmail(Message msg) throws Exception{ + //假装发了一封邮件 + + if (msg != null) { + + System.out.println("开始发送邮件"); + + if (msg.checkFormat()) { + + System.out.println("发送邮件..."); + + try { + + firstSMPTHost.send(msg); + + System.out.println("发送邮件成功"); + + } catch (Exception e) { + try { + + secondSMPTHost.send(msg); + + } catch (Exception e2) { + + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + + } + } + } else { + + System.out.println("邮件格式不对"); + + } + } else { + + System.out.println("没有邮件发送"); + + } + } +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java new file mode 100644 index 0000000000..a0a16d2756 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Message.java @@ -0,0 +1,65 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class Message { + private String toAddress; + private String fromAddress; + private String subject; + private String message; + + public Message(String toAddress, String fromAddress, String subject, String message) { + this.toAddress = toAddress; + this.fromAddress = fromAddress; + this.subject = subject; + this.message = message; + } + + public void print() { + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + } + + public boolean checkFormat() { + return true; + } + + public String getToAddress() { + + return toAddress; + } + + public void setToAddress(String toAddress) { + this.toAddress = toAddress; + } + + public String getFromAddress() { + return fromAddress; + } + + public void setFromAddress(String fromAddress) { + this.fromAddress = fromAddress; + } + + public String getSubject() { + return subject; + } + + public void setSubject(String subject) { + this.subject = subject; + } + + public String getMessage() { + return message; + } + + public void setMessage(String message) { + this.message = message; + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java new file mode 100644 index 0000000000..5662ace67d --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/Product.java @@ -0,0 +1,33 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class Product { + public String getProductId() { + return productId; + } + + public Product(String productId, String productDesc) { + this.productId = productId; + this.productDesc = productDesc; + } + + public Product() { + } + + public void setProductId(String productId) { + this.productId = productId; + } + + public String getProductDesc() { + return productDesc; + } + + public void setProductDesc(String productDesc) { + this.productDesc = productDesc; + } + + private String productId; + private String productDesc; +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java new file mode 100644 index 0000000000..f7366c27e4 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/ProductFactory.java @@ -0,0 +1,36 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +/** + * Created by szf on 6/20/17. + */ +public class ProductFactory { + List getNewProdcuts(File file) throws IOException { + BufferedReader br = null; + List newProducts = new ArrayList<>(); + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + Product product = new Product(data[0], data[1]); + newProducts.add(product); + + System.out.println("产品ID = " + product.getProductId() + "\n"); + System.out.println("产品描述 = " + product.getProductDesc() + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + return newProducts; + } + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..fa90f9a539 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,51 @@ +package com.coderising.ood.srp; +import java.io.File; +import java.util.List; + +public class PromotionMail { + + + public static void main(String[] args) throws Exception { + + PromotionMail pe = new PromotionMail(); + + } + + + public PromotionMail() throws Exception { + + if (Configuration.MAIL_DEBUG) { + System.out.println("debugging..."); + } + + ProductFactory factory = new ProductFactory(); + + File file = new File(Configuration.getProperty(ConfigurationKeys.FILE_PATH)); + List products = factory.getNewProdcuts(file); + + String productID = "1"; + String sql = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + List users = DBUtil.query(sql); + + + for (User user : users) { + for (Product product : products) { + + String to_address = user.getEmail(); + String from_address = Configuration.getProperty(ConfigurationKeys.EMAIL_ADMIN); + String subject = "您关注的产品降价了"; + String message = "尊敬的 "+ user.getName() + ", 您关注的产品 " + product.getProductDesc() + " 降价了,欢迎购买!" ; + + Message msg = new Message(to_address, from_address, subject, message); + + MailUtil.sendEmail(msg); + } + + } + } + + +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java new file mode 100644 index 0000000000..225f98b727 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/User.java @@ -0,0 +1,32 @@ +package com.coderising.ood.srp; + +/** + * Created by szf on 6/20/17. + */ +public class User { + private String Name; + + public User(String name, String email) { + Name = name; + Email = email; + } + + public String getName() { + + return Name; + } + + public void setName(String name) { + Name = name; + } + + public String getEmail() { + return Email; + } + + public void setEmail(String email) { + Email = email; + } + + private String Email; +} diff --git a/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..0c0124cc61 --- /dev/null +++ b/students/471398827/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From 2729efd262313688e2a6590be016a8942358d66b Mon Sep 17 00:00:00 2001 From: thomas_young Date: Tue, 20 Jun 2017 23:05:25 +0800 Subject: [PATCH 18/73] =?UTF-8?q?=E5=88=9B=E5=BB=BA=E8=87=AA=E5=B7=B1?= =?UTF-8?q?=E7=9A=84=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/812350401/pom.xml | 45 ++++ .../java/com/coderising/ood/ocp/DateUtil.java | 10 + .../java/com/coderising/ood/ocp/Logger.java | 38 ++++ .../java/com/coderising/ood/ocp/MailUtil.java | 10 + .../java/com/coderising/ood/ocp/SMSUtil.java | 10 + .../com/coderising/ood/srp/Configuration.java | 23 ++ .../coderising/ood/srp/ConfigurationKeys.java | 9 + .../java/com/coderising/ood/srp/DBUtil.java | 25 +++ .../com/coderising/ood/srp/EmailParam.java | 8 + .../java/com/coderising/ood/srp/MailUtil.java | 18 ++ .../com/coderising/ood/srp/PromotionMail.java | 199 ++++++++++++++++++ .../coderising/ood/srp/product_promotion.txt | 4 + 12 files changed, 399 insertions(+) create mode 100644 students/812350401/pom.xml create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt diff --git a/students/812350401/pom.xml b/students/812350401/pom.xml new file mode 100644 index 0000000000..9a28365d2a --- /dev/null +++ b/students/812350401/pom.xml @@ -0,0 +1,45 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + + + org.apache.maven.plugins + maven-compiler-plugin + + 1.8 + 1.8 + + + + + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..0d0d01098f --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java b/students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..aca173e665 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,38 @@ +package com.coderising.ood.ocp; + +public class Logger { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + int type = 0; + int method = 0; + + public Logger(int logType, int logMethod){ + this.type = logType; + this.method = logMethod; + } + public void log(String msg){ + + String logMsg = msg; + + if(this.type == RAW_LOG){ + logMsg = msg; + } else if(this.type == RAW_LOG_WITH_DATE){ + String txtDate = DateUtil.getCurrentDateAsString(); + logMsg = txtDate + ": " + msg; + } + + if(this.method == EMAIL_LOG){ + MailUtil.send(logMsg); + } else if(this.method == SMS_LOG){ + SMSUtil.send(logMsg); + } else if(this.method == PRINT_LOG){ + System.out.println(logMsg); + } + } +} + diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..59d77649a2 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..fab4cd01b7 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java b/students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..f328c1816a --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..8695aed644 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..fee83a770d --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com" + i); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java b/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java new file mode 100644 index 0000000000..934ff2139b --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java @@ -0,0 +1,8 @@ +package com.coderising.ood.srp; + +/** + * Created by thomas_young on 20/6/2017. + */ +public class EmailParam { + protected String smtpHost = null; +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..9f9e749af7 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,18 @@ +package com.coderising.ood.srp; + +public class MailUtil { + + public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, + boolean debug) { + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + + } + + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..b359f3aa6f --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,199 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.io.Serializable; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; + +public class PromotionMail { + + + protected String sendMailQuery = null; + + + protected String smtpHost = null; + protected String altSmtpHost = null; + protected String fromAddress = null; + protected String toAddress = null; + protected String subject = null; + protected String message = null; + + protected String productID = null; + protected String productDesc = null; + + private static Configuration config; + + + + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + + public static void main(String[] args) throws Exception { + + File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + boolean emailDebug = false; + + PromotionMail pe = new PromotionMail(f, emailDebug); + + } + + + public PromotionMail(File file, boolean mailDebug) throws Exception { + + //读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 + readFile(file); + + + config = new Configuration(); + + setSMTPHost(); + setAltSMTPHost(); + + + setFromAddress(); + + + setLoadQuery(); + + sendEMails(mailDebug, loadMailingList()); + + + } + + + + + protected void setProductID(String productID) + { + this.productID = productID; + + } + + protected String getproductID() + { + return productID; + } + + protected void setLoadQuery() throws Exception { + + sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + + System.out.println("loadQuery set"); + } + + + protected void setSMTPHost() + { + smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + } + + + protected void setAltSMTPHost() + { + altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + + } + + + protected void setFromAddress() + { + fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + } + + protected void setMessage(HashMap userInfo) throws IOException + { + + String name = (String) userInfo.get(NAME_KEY); + + subject = "您关注的产品降价了"; + message = "尊敬的 "+name+", 您关注的产品 " + productDesc + " 降价了,欢迎购买!" ; + + + + } + + + protected void readFile(File file) throws IOException // @02C + { + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + setProductID(data[0]); + setProductDesc(data[1]); + + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + private void setProductDesc(String desc) { + this.productDesc = desc; + } + + + protected void configureEMail(HashMap userInfo) throws IOException + { + toAddress = (String) userInfo.get(EMAIL_KEY); + if (toAddress.length() > 0) + setMessage(userInfo); + } + + protected List loadMailingList() throws Exception { + return DBUtil.query(this.sendMailQuery); + } + + + protected void sendEMails(boolean debug, List mailingList) throws IOException + { + + System.out.println("开始发送邮件"); + + + if (mailingList != null) { + Iterator iter = mailingList.iterator(); + while (iter.hasNext()) { + configureEMail((HashMap) iter.next()); + try + { + if (toAddress.length() > 0) + MailUtil.sendEmail(toAddress, fromAddress, subject, message, smtpHost, debug); + } + catch (Exception e) + { + + try { + MailUtil.sendEmail(toAddress, fromAddress, subject, message, altSmtpHost, debug); + + } catch (Exception e2) + { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + } + } + + + } + + else { + System.out.println("没有邮件发送"); + + } + + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..0c0124cc61 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From 79ec6e023a56f625b50caddb9ddecb3722633c30 Mon Sep 17 00:00:00 2001 From: yangzhm Date: Wed, 21 Jun 2017 08:09:00 +0800 Subject: [PATCH 19/73] push base source for SRP --- students/495232796/OOD/ood-assignment/pom.xml | 32 +++ .../com/coderising/ood/srp/Configuration.java | 23 ++ .../coderising/ood/srp/ConfigurationKeys.java | 9 + .../java/com/coderising/ood/srp/DBUtil.java | 25 +++ .../java/com/coderising/ood/srp/MailUtil.java | 18 ++ .../com/coderising/ood/srp/PromotionMail.java | 199 ++++++++++++++++++ .../coderising/ood/srp/product_promotion.txt | 4 + 7 files changed, 310 insertions(+) create mode 100644 students/495232796/OOD/ood-assignment/pom.xml create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt diff --git a/students/495232796/OOD/ood-assignment/pom.xml b/students/495232796/OOD/ood-assignment/pom.xml new file mode 100644 index 0000000000..cac49a5328 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/pom.xml @@ -0,0 +1,32 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..f328c1816a --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..8695aed644 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..82e9261d18 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com"); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..9f9e749af7 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,18 @@ +package com.coderising.ood.srp; + +public class MailUtil { + + public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, + boolean debug) { + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + + } + + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..781587a846 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,199 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.io.Serializable; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; + +public class PromotionMail { + + + protected String sendMailQuery = null; + + + protected String smtpHost = null; + protected String altSmtpHost = null; + protected String fromAddress = null; + protected String toAddress = null; + protected String subject = null; + protected String message = null; + + protected String productID = null; + protected String productDesc = null; + + private static Configuration config; + + + + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + + public static void main(String[] args) throws Exception { + + File f = new File("C:\\coderising\\workspace_ds\\ood-example\\src\\product_promotion.txt"); + boolean emailDebug = false; + + PromotionMail pe = new PromotionMail(f, emailDebug); + + } + + + public PromotionMail(File file, boolean mailDebug) throws Exception { + + //读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 + readFile(file); + + + config = new Configuration(); + + setSMTPHost(); + setAltSMTPHost(); + + + setFromAddress(); + + + setLoadQuery(); + + sendEMails(mailDebug, loadMailingList()); + + + } + + + + + protected void setProductID(String productID) + { + this.productID = productID; + + } + + protected String getproductID() + { + return productID; + } + + protected void setLoadQuery() throws Exception { + + sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + + System.out.println("loadQuery set"); + } + + + protected void setSMTPHost() + { + smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + } + + + protected void setAltSMTPHost() + { + altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + + } + + + protected void setFromAddress() + { + fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + } + + protected void setMessage(HashMap userInfo) throws IOException + { + + String name = (String) userInfo.get(NAME_KEY); + + subject = "您关注的产品降价了"; + message = "尊敬的 "+name+", 您关注的产品 " + productDesc + " 降价了,欢迎购买!" ; + + + + } + + + protected void readFile(File file) throws IOException // @02C + { + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + setProductID(data[0]); + setProductDesc(data[1]); + + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + private void setProductDesc(String desc) { + this.productDesc = desc; + } + + + protected void configureEMail(HashMap userInfo) throws IOException + { + toAddress = (String) userInfo.get(EMAIL_KEY); + if (toAddress.length() > 0) + setMessage(userInfo); + } + + protected List loadMailingList() throws Exception { + return DBUtil.query(this.sendMailQuery); + } + + + protected void sendEMails(boolean debug, List mailingList) throws IOException + { + + System.out.println("开始发送邮件"); + + + if (mailingList != null) { + Iterator iter = mailingList.iterator(); + while (iter.hasNext()) { + configureEMail((HashMap) iter.next()); + try + { + if (toAddress.length() > 0) + MailUtil.sendEmail(toAddress, fromAddress, subject, message, smtpHost, debug); + } + catch (Exception e) + { + + try { + MailUtil.sendEmail(toAddress, fromAddress, subject, message, altSmtpHost, debug); + + } catch (Exception e2) + { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + } + } + + + } + + else { + System.out.println("没有邮件发送"); + + } + + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From c63b5810ff94645b478d452cf092849a78062ed0 Mon Sep 17 00:00:00 2001 From: yangzhm Date: Wed, 21 Jun 2017 11:16:55 +0800 Subject: [PATCH 20/73] modify project structure according to SRP rule --- .../ood/srp => config}/product_promotion.txt | 0 ...ConfigurationKeys.java => CommonKeys.java} | 5 +- .../com/coderising/ood/srp/Configuration.java | 6 +- .../java/com/coderising/ood/srp/DBUtil.java | 4 +- .../java/com/coderising/ood/srp/MailAddr.java | 42 ++++ .../java/com/coderising/ood/srp/MailMsg.java | 19 ++ .../java/com/coderising/ood/srp/MailUtil.java | 14 +- .../com/coderising/ood/srp/ProductInfo.java | 49 +++++ .../com/coderising/ood/srp/PromotionMail.java | 194 ++++-------------- 9 files changed, 165 insertions(+), 168 deletions(-) rename students/495232796/OOD/ood-assignment/{src/main/java/com/coderising/ood/srp => config}/product_promotion.txt (100%) rename students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/{ConfigurationKeys.java => CommonKeys.java} (63%) create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailAddr.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailMsg.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ProductInfo.java diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/495232796/OOD/ood-assignment/config/product_promotion.txt similarity index 100% rename from students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt rename to students/495232796/OOD/ood-assignment/config/product_promotion.txt diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/CommonKeys.java similarity index 63% rename from students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java rename to students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/CommonKeys.java index 8695aed644..2980cc40ca 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/CommonKeys.java @@ -1,9 +1,10 @@ package com.coderising.ood.srp; -public class ConfigurationKeys { +public class CommonKeys { public static final String SMTP_SERVER = "smtp.server"; public static final String ALT_SMTP_SERVER = "alt.smtp.server"; public static final String EMAIL_ADMIN = "email.admin"; - + public static final String NAME_KEY = "NAME"; + public static final String EMAIL_KEY = "EMAIL"; } diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java index f328c1816a..13cc1b5890 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java @@ -6,9 +6,9 @@ public class Configuration { static Map configurations = new HashMap<>(); static{ - configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); - configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); - configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + configurations.put(CommonKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(CommonKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(CommonKeys.EMAIL_ADMIN, "admin@company.com"); } /** * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java index 82e9261d18..ff8215b4d2 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java @@ -15,8 +15,8 @@ public static List query(String sql){ List userList = new ArrayList(); for (int i = 1; i <= 3; i++) { HashMap userInfo = new HashMap(); - userInfo.put("NAME", "User" + i); - userInfo.put("EMAIL", "aa@bb.com"); + userInfo.put(CommonKeys.NAME_KEY, "User" + i); + userInfo.put(CommonKeys.EMAIL_KEY, "aa@bb.com"); userList.add(userInfo); } diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailAddr.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailAddr.java new file mode 100644 index 0000000000..239166dd11 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailAddr.java @@ -0,0 +1,42 @@ +package com.coderising.ood.srp; + +public class MailAddr { + protected String smtpHost = null; + protected String altSmtpHost = null; + protected String fromAddress = null; + protected String toAddress = null; + + public MailAddr(Configuration config) { + reloadconfig(config); + } + + public void reloadconfig(Configuration config) { + smtpHost = config.getProperty(CommonKeys.SMTP_SERVER); + altSmtpHost = config.getProperty(CommonKeys.ALT_SMTP_SERVER); + fromAddress = config.getProperty(CommonKeys.EMAIL_ADMIN); + } + + public void setToAddress(String address) { + toAddress = address; + } + + public String getToAddress() { + return toAddress; + } + + public boolean checkToAddress() { + return toAddress.length() > 0; + } + + public String getSmtpHost() { + return smtpHost; + } + + public String getAltSmtpHost() { + return altSmtpHost; + } + + public String getFromAddress() { + return fromAddress; + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailMsg.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailMsg.java new file mode 100644 index 0000000000..dd834ccfef --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailMsg.java @@ -0,0 +1,19 @@ +package com.coderising.ood.srp; + +public class MailMsg { + protected String subject = null; + protected String message = null; + + public MailMsg(String sub, String msg) { + this.subject = sub; + this.message = msg; + } + + public String getSubject() { + return subject; + } + + public String getMessage() { + return message; + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java index 9f9e749af7..cfb2cffa7c 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -2,17 +2,13 @@ public class MailUtil { - public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, - boolean debug) { + public static void sendEmail(MailAddr mailAddr, MailMsg mailMsg, boolean debug) { //假装发了一封邮件 StringBuilder buffer = new StringBuilder(); - buffer.append("From:").append(fromAddress).append("\n"); - buffer.append("To:").append(toAddress).append("\n"); - buffer.append("Subject:").append(subject).append("\n"); - buffer.append("Content:").append(message).append("\n"); + buffer.append("From:").append(mailAddr.getFromAddress()).append("\n"); + buffer.append("To:").append(mailAddr.getToAddress()).append("\n"); + buffer.append("Subject:").append(mailMsg.getSubject()).append("\n"); + buffer.append("Content:").append(mailMsg.getMessage()).append("\n"); System.out.println(buffer.toString()); - } - - } diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ProductInfo.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ProductInfo.java new file mode 100644 index 0000000000..ad68f0a7eb --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/ProductInfo.java @@ -0,0 +1,49 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; + +public class ProductInfo { + protected String productID = null; + protected String productDesc = null; + + public ProductInfo(String path) { + try { + readFile(path); + } catch (IOException e) { + e.printStackTrace(); + } + } + + protected void readFile(String path) throws IOException + { + File f = new File(path); + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(f)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + this.productID = data[0]; + this.productDesc = data[1]; + + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + public String getProductID() { + return productID; + } + + public String getProductDesc() { + return productDesc; + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java index 781587a846..808caab9f8 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -1,198 +1,88 @@ package com.coderising.ood.srp; -import java.io.BufferedReader; -import java.io.File; -import java.io.FileReader; import java.io.IOException; -import java.io.Serializable; import java.util.HashMap; import java.util.Iterator; import java.util.List; public class PromotionMail { - - protected String sendMailQuery = null; - - - protected String smtpHost = null; - protected String altSmtpHost = null; - protected String fromAddress = null; - protected String toAddress = null; - protected String subject = null; - protected String message = null; - - protected String productID = null; - protected String productDesc = null; - - private static Configuration config; - - - - private static final String NAME_KEY = "NAME"; - private static final String EMAIL_KEY = "EMAIL"; - + protected boolean emailDebug = false; + protected ProductInfo productInfo = null; + protected MailAddr mailAddr = null; + private static Configuration config; public static void main(String[] args) throws Exception { + String path = "D:\\projects\\OOD\\project\\ood-assignment\\config\\product_promotion.txt"; - File f = new File("C:\\coderising\\workspace_ds\\ood-example\\src\\product_promotion.txt"); - boolean emailDebug = false; - - PromotionMail pe = new PromotionMail(f, emailDebug); - + PromotionMail pe = new PromotionMail(path, false); + pe.sendEmails(); } - - public PromotionMail(File file, boolean mailDebug) throws Exception { - - //读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 - readFile(file); - - + public PromotionMail(String path, boolean mailDebug) throws Exception { + this.emailDebug = mailDebug; + productInfo = new ProductInfo(path); config = new Configuration(); - - setSMTPHost(); - setAltSMTPHost(); - - - setFromAddress(); - - - setLoadQuery(); - - sendEMails(mailDebug, loadMailingList()); - - + mailAddr = new MailAddr(config); } - - - - protected void setProductID(String productID) - { - this.productID = productID; - - } - - protected String getproductID() - { - return productID; - } - protected void setLoadQuery() throws Exception { - - sendMailQuery = "Select name from subscriptions " - + "where product_id= '" + productID +"' " - + "and send_mail=1 "; - - + sendMailQuery = "Select name from subscriptions " + "where product_id= '" + this.productInfo.getProductID() + + "' " + "and send_mail=1 "; + System.out.println("loadQuery set"); } - - protected void setSMTPHost() - { - smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); - } + protected MailMsg setMessage(HashMap userInfo) throws IOException { - - protected void setAltSMTPHost() - { - altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + String name = (String) userInfo.get(CommonKeys.NAME_KEY); - } + String subject = "您关注的产品降价了"; + String message = "尊敬的 " + name + ", 您关注的产品 " + this.productInfo.getProductDesc() + " 降价了,欢迎购买!"; - - protected void setFromAddress() - { - fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + return new MailMsg(subject, message); } - protected void setMessage(HashMap userInfo) throws IOException - { - - String name = (String) userInfo.get(NAME_KEY); - - subject = "您关注的产品降价了"; - message = "尊敬的 "+name+", 您关注的产品 " + productDesc + " 降价了,欢迎购买!" ; - - - + protected List loadMailingList() throws Exception { + return DBUtil.query(this.sendMailQuery); } - - protected void readFile(File file) throws IOException // @02C - { - BufferedReader br = null; + public void sendEmails() { try { - br = new BufferedReader(new FileReader(file)); - String temp = br.readLine(); - String[] data = temp.split(" "); - - setProductID(data[0]); - setProductDesc(data[1]); - - System.out.println("产品ID = " + productID + "\n"); - System.out.println("产品描述 = " + productDesc + "\n"); - + setLoadQuery(); + sendEMails(emailDebug, loadMailingList()); } catch (IOException e) { - throw new IOException(e.getMessage()); - } finally { - br.close(); + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (Exception e) { + // TODO Auto-generated catch block + e.printStackTrace(); } } - private void setProductDesc(String desc) { - this.productDesc = desc; - } - - - protected void configureEMail(HashMap userInfo) throws IOException - { - toAddress = (String) userInfo.get(EMAIL_KEY); - if (toAddress.length() > 0) - setMessage(userInfo); - } - - protected List loadMailingList() throws Exception { - return DBUtil.query(this.sendMailQuery); - } - - - protected void sendEMails(boolean debug, List mailingList) throws IOException - { - + protected void sendEMails(boolean debug, List mailingList) throws IOException { System.out.println("开始发送邮件"); - if (mailingList != null) { Iterator iter = mailingList.iterator(); while (iter.hasNext()) { - configureEMail((HashMap) iter.next()); - try - { - if (toAddress.length() > 0) - MailUtil.sendEmail(toAddress, fromAddress, subject, message, smtpHost, debug); - } - catch (Exception e) - { - + HashMap userInfo = (HashMap) iter.next(); + mailAddr.setToAddress((String) userInfo.get(CommonKeys.EMAIL_KEY)); + if (mailAddr.checkToAddress()) { + MailMsg mailmsg = setMessage(userInfo); try { - MailUtil.sendEmail(toAddress, fromAddress, subject, message, altSmtpHost, debug); - - } catch (Exception e2) - { - System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + MailUtil.sendEmail(mailAddr, mailmsg, debug); + } catch (Exception e) { + try { + MailUtil.sendEmail(mailAddr, mailmsg, debug); + } catch (Exception e2) { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } } } } - - - } - - else { + } else { System.out.println("没有邮件发送"); - } } From e052e162418d050ed30edf79acdd758cc4f355e6 Mon Sep 17 00:00:00 2001 From: zhizx Date: Wed, 21 Jun 2017 12:16:23 +0800 Subject: [PATCH 21/73] s --- students/919442958/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/students/919442958/README.md b/students/919442958/README.md index 60472c8281..e4a5485e97 100644 --- a/students/919442958/README.md +++ b/students/919442958/README.md @@ -1 +1 @@ -这是919442958的作业。 \ No newline at end of file +这是919442958的作业。1234 \ No newline at end of file From 14181b6df1f344c80cb6205e2748825a8b9258a8 Mon Sep 17 00:00:00 2001 From: zhizx Date: Wed, 21 Jun 2017 12:52:28 +0800 Subject: [PATCH 22/73] 123 --- students/919442958/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/students/919442958/README.md b/students/919442958/README.md index e4a5485e97..d96760c4ae 100644 --- a/students/919442958/README.md +++ b/students/919442958/README.md @@ -1 +1 @@ -这是919442958的作业。1234 \ No newline at end of file +这是919442958的作业。1234 12 \ No newline at end of file From aef65cd25a8325d6830c810c79f02c2b2ff33175 Mon Sep 17 00:00:00 2001 From: ShiningChenCode Date: Wed, 21 Jun 2017 13:36:58 +0800 Subject: [PATCH 23/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E6=AC=A1=E4=BD=9C?= =?UTF-8?q?=E4=B8=9A=EF=BC=88=E6=89=BE=E5=9B=9E=E7=AC=AC=E4=B8=80=E6=AC=A1?= =?UTF-8?q?=E4=BD=9C=E4=B8=9A=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../coderising/ood/srp/product_promotion.txt | 4 + students/2831099157/ood-assignment/pom.xml | 32 +++++ .../java/com/coderising/ood/ocp/Logger.java | 20 ++++ .../java/com/coderising/ood/ocp/MainTest.java | 20 ++++ .../ood/ocp/formatter/Formatter.java | 9 ++ .../ood/ocp/formatter/FormatterFactory.java | 21 ++++ .../ocp/formatter/OnlyStringFormatter.java | 12 ++ .../formatter/WithCurrentDateFormatter.java | 16 +++ .../ood/ocp/sender/EmailSender.java | 11 ++ .../ood/ocp/sender/PrintSender.java | 11 ++ .../coderising/ood/ocp/sender/SMSSender.java | 11 ++ .../com/coderising/ood/ocp/sender/Sender.java | 9 ++ .../ood/ocp/sender/SenderFactory.java | 30 +++++ .../coderising/ood/ocp/utils/DateUtil.java | 13 ++ .../coderising/ood/ocp/utils/MailUtil.java | 10 ++ .../com/coderising/ood/ocp/utils/SMSUtil.java | 10 ++ .../com/coderising/ood/srp/PromotionMail.java | 21 ++++ .../ood/srp/configure/Configuration.java | 23 ++++ .../ood/srp/configure/ConfigurationKeys.java | 9 ++ .../com/coderising/ood/srp/dao/DBUtil.java | 27 +++++ .../srp/interfaces/GetProductsFunction.java | 13 ++ .../ood/srp/interfaces/SendMailFunction.java | 13 ++ .../com/coderising/ood/srp/model/Mail.java | 112 ++++++++++++++++++ .../com/coderising/ood/srp/model/Product.java | 46 +++++++ .../com/coderising/ood/srp/model/User.java | 25 ++++ .../coderising/ood/srp/product_promotion.txt | 4 + .../ood/srp/service/GetProductsFromFile.java | 47 ++++++++ .../ood/srp/service/GoodsArrivalNotice.java | 13 ++ .../coderising/ood/srp/service/Notice.java | 25 ++++ .../ood/srp/service/PricePromotion.java | 12 ++ .../ood/srp/service/SendGoodsArrivalMail.java | 42 +++++++ .../ood/srp/service/SendPriceMail.java | 42 +++++++ ...10\351\207\215\346\236\204\357\274\211.md" | 23 ++++ .../coderising/ood/srp/product_promotion.txt | 4 + 34 files changed, 740 insertions(+) create mode 100644 students/2831099157/ood-assignment/out/production/main/com/coderising/ood/srp/product_promotion.txt create mode 100644 students/2831099157/ood-assignment/pom.xml create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/MainTest.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/Formatter.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/FormatterFactory.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/OnlyStringFormatter.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/WithCurrentDateFormatter.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/EmailSender.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/PrintSender.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SMSSender.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/Sender.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SenderFactory.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/DateUtil.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/MailUtil.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/SMSUtil.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/Configuration.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/ConfigurationKeys.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/dao/DBUtil.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/GetProductsFunction.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/SendMailFunction.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Mail.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Product.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/User.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GetProductsFromFile.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GoodsArrivalNotice.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/Notice.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/PricePromotion.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendGoodsArrivalMail.java create mode 100644 students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendPriceMail.java create mode 100644 "students/2831099157/ood-assignment/\344\277\203\351\224\200Mail\345\217\221\351\200\201\347\273\203\344\271\240\357\274\210\351\207\215\346\236\204\357\274\211.md" create mode 100644 students/2831099157/out/production/main/com/coderising/ood/srp/product_promotion.txt diff --git a/students/2831099157/ood-assignment/out/production/main/com/coderising/ood/srp/product_promotion.txt b/students/2831099157/ood-assignment/out/production/main/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/2831099157/ood-assignment/out/production/main/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file diff --git a/students/2831099157/ood-assignment/pom.xml b/students/2831099157/ood-assignment/pom.xml new file mode 100644 index 0000000000..cac49a5328 --- /dev/null +++ b/students/2831099157/ood-assignment/pom.xml @@ -0,0 +1,32 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..cd49152e09 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,20 @@ +package com.coderising.ood.ocp; + +import com.coderising.ood.ocp.formatter.Formatter; +import com.coderising.ood.ocp.sender.Sender; + +public class Logger { + private Formatter formatter; + private Sender sender; + + public Logger(Formatter formatter,Sender sender){ + this.formatter = formatter; + this.sender = sender; + } + public void log(String msg){ + sender.send(formatter.format(msg)) ; + } + + +} + diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/MainTest.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/MainTest.java new file mode 100644 index 0000000000..cfa756a14e --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/MainTest.java @@ -0,0 +1,20 @@ +package com.coderising.ood.ocp; + +import com.coderising.ood.ocp.formatter.FormatterFactory; +import com.coderising.ood.ocp.sender.SenderFactory; + +/** + * Created by Iden on 2017/6/21. + */ +public class MainTest { + public static void main(String[] args) { + + Logger logger = new Logger(FormatterFactory.createFormatter(FormatterFactory.ONLY_STRING), + SenderFactory.createSender(SenderFactory.ENAIL)); + logger.log("Messge 1"); + + Logger logger2 = new Logger(FormatterFactory.createFormatter(FormatterFactory.WITH_CURRENT_DATA), + SenderFactory.createSender(SenderFactory.SMS)); + logger2.log("Messge 2"); + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/Formatter.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/Formatter.java new file mode 100644 index 0000000000..aee4b86da5 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/Formatter.java @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp.formatter; + +/** + * Created by Iden on 2017/6/21. + */ +public interface Formatter { + + String format(String msg); +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/FormatterFactory.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/FormatterFactory.java new file mode 100644 index 0000000000..8a1b99fe6a --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/FormatterFactory.java @@ -0,0 +1,21 @@ +package com.coderising.ood.ocp.formatter; + +/** + * Created by Iden on 2017/6/21. + */ +public class FormatterFactory { + + public static final int ONLY_STRING = 1; + public static final int WITH_CURRENT_DATA = 2; + + public static Formatter createFormatter(int type) { + if (type == ONLY_STRING) { + return new OnlyStringFormatter(); + } + if (type == WITH_CURRENT_DATA) { + return new WithCurrentDateFormatter(); + } + return null; + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/OnlyStringFormatter.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/OnlyStringFormatter.java new file mode 100644 index 0000000000..312a2c8d90 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/OnlyStringFormatter.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp.formatter; + +/** + * Created by Iden on 2017/6/21. + */ +public class OnlyStringFormatter implements Formatter{ + + @Override + public String format(String msg) { + return msg; + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/WithCurrentDateFormatter.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/WithCurrentDateFormatter.java new file mode 100644 index 0000000000..bec30c2b15 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/formatter/WithCurrentDateFormatter.java @@ -0,0 +1,16 @@ +package com.coderising.ood.ocp.formatter; + +import com.coderising.ood.ocp.utils.DateUtil; + +/** + * Created by Iden on 2017/6/21. + */ +public class WithCurrentDateFormatter implements Formatter{ + + @Override + public String format(String msg) { + String txtDate = DateUtil.getCurrentDateAsString(); + String logMsg = txtDate + ": " + msg; + return logMsg; + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/EmailSender.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/EmailSender.java new file mode 100644 index 0000000000..921003ba6f --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/EmailSender.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.sender; + +/** + * Created by Iden on 2017/6/21. + */ +public class EmailSender implements Sender { + @Override + public void send(String msg) { + System.out.println("Email发送,内容为:"+msg); + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/PrintSender.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/PrintSender.java new file mode 100644 index 0000000000..af3ce1dc57 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/PrintSender.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.sender; + +/** + * Created by Iden on 2017/6/21. + */ +public class PrintSender implements Sender { + @Override + public void send(String msg) { + System.out.println("Print发送,内容为:"+msg); + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SMSSender.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SMSSender.java new file mode 100644 index 0000000000..6dabed6969 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SMSSender.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.sender; + +/** + * Created by Iden on 2017/6/21. + */ +public class SMSSender implements Sender { + @Override + public void send(String msg) { + System.out.println("SMS发送,内容为:"+ msg); + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/Sender.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/Sender.java new file mode 100644 index 0000000000..7187f23f6a --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/Sender.java @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp.sender; + +/** + * Created by Iden on 2017/6/21. + */ +public interface Sender { + + void send(String msg); +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SenderFactory.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SenderFactory.java new file mode 100644 index 0000000000..ff2346ce58 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/sender/SenderFactory.java @@ -0,0 +1,30 @@ +package com.coderising.ood.ocp.sender; + +import com.coderising.ood.ocp.formatter.Formatter; +import com.coderising.ood.ocp.formatter.OnlyStringFormatter; +import com.coderising.ood.ocp.formatter.WithCurrentDateFormatter; + +/** + * Created by Iden on 2017/6/21. + */ +public class SenderFactory { + + public static final int ENAIL = 1; + public static final int SMS = 2; + public static final int PRINT = 3; + + + public static Sender createSender(int type) { + if (type == ENAIL) { + return new EmailSender(); + } + if (type == SMS) { + return new SMSSender(); + } + if (type == PRINT) { + return new PrintSender(); + } + return null; + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/DateUtil.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/DateUtil.java new file mode 100644 index 0000000000..4b1cf6c78d --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/DateUtil.java @@ -0,0 +1,13 @@ +package com.coderising.ood.ocp.utils; + +import java.text.SimpleDateFormat; +import java.util.Date; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return SimpleDateFormat.getInstance().format(new Date()); + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/MailUtil.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/MailUtil.java new file mode 100644 index 0000000000..7214e763b5 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.utils; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/SMSUtil.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/SMSUtil.java new file mode 100644 index 0000000000..d59b7e6644 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/ocp/utils/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.utils; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..9eb1b21f29 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,21 @@ +package com.coderising.ood.srp; + +import com.coderising.ood.srp.service.GoodsArrivalNotice; +import com.coderising.ood.srp.service.Notice; + +/** + * 可以根据不同运营方案,添加GetProductsFunction,SendMailFunction接口实现类及Notice子类,向订阅者发送通告 + */ +public class PromotionMail { + + public static void main(String[] args) throws Exception { + //降价促销 +// Notice notice = new PricePromotion(); + //到货通知 + Notice notice = new GoodsArrivalNotice(); + notice.sendMail(notice.getProducts()); + + } + + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/Configuration.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/Configuration.java new file mode 100644 index 0000000000..5c0697782a --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/Configuration.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp.configure; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/ConfigurationKeys.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/ConfigurationKeys.java new file mode 100644 index 0000000000..c9cfba4974 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/configure/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp.configure; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/dao/DBUtil.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/dao/DBUtil.java new file mode 100644 index 0000000000..c0e7f6508d --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/dao/DBUtil.java @@ -0,0 +1,27 @@ +package com.coderising.ood.srp.dao; +import com.coderising.ood.srp.model.User; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + User user = new User(); + user.setName("User" + i); + user.seteMail("aa@bb.com"); + userList.add(user); + } + + return userList; + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/GetProductsFunction.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/GetProductsFunction.java new file mode 100644 index 0000000000..f0894ea3c7 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/GetProductsFunction.java @@ -0,0 +1,13 @@ +package com.coderising.ood.srp.interfaces; + +import com.coderising.ood.srp.model.Product; + +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + */ +public interface GetProductsFunction { + + List getProducts(); +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/SendMailFunction.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/SendMailFunction.java new file mode 100644 index 0000000000..cd27a45767 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/interfaces/SendMailFunction.java @@ -0,0 +1,13 @@ +package com.coderising.ood.srp.interfaces; + +import com.coderising.ood.srp.model.Product; + +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + */ +public interface SendMailFunction { + + void sendMail(List products); +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Mail.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Mail.java new file mode 100644 index 0000000000..b94f27b29d --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Mail.java @@ -0,0 +1,112 @@ +package com.coderising.ood.srp.model; + +import com.coderising.ood.srp.configure.Configuration; +import com.coderising.ood.srp.configure.ConfigurationKeys; + +/** + * Created by Iden on 2017/6/14. + */ +public class Mail { + private String fromAddress; + private String toAddress; + private String subject; + private String content; + private String smtpHost = null; + private String altSmtpHost = null; + + public Mail() { + Configuration config = new Configuration(); + fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + } + + public String getFromAddress() { + return fromAddress; + } + + public void setFromAddress(String fromAddress) { + this.fromAddress = fromAddress; + } + + public String getToAddress() { + return toAddress; + } + + public void setToAddress(String toAddress) { + this.toAddress = toAddress; + } + + public String getSubject() { + return subject; + } + + public void setSubject(String subject) { + this.subject = subject; + } + + public String getContent() { + return content; + } + + public void setContent(String content) { + this.content = content; + } + + + public String getSmtpHost() { + return smtpHost; + } + + public void setSmtpHost(String smtpHost) { + this.smtpHost = smtpHost; + } + + public String getAltSmtpHost() { + return altSmtpHost; + } + + public void setAltSmtpHost(String altSmtpHost) { + this.altSmtpHost = altSmtpHost; + } + + + public void send() { + if(null==toAddress){ + System.out.println("发送地址不能为空"); + return; + } + try { + sendMailBySmtpHost(); + } catch (Exception e) { + try { + sendMailBySmtpHost(); + } catch (Exception e2) { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + + } + } + + private void sendMailBySmtpHost() { + System.out.println("通过SMTP服务器开始发送邮件"); + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(content).append("\n"); + System.out.println(buffer.toString()); + } + + private void sendMailByAlSmtpHost() { + System.out.println("通过备用SMTP服务器开始发送邮件"); + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(content).append("\n"); + System.out.println(buffer.toString()); + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Product.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Product.java new file mode 100644 index 0000000000..f9f5b5a145 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/Product.java @@ -0,0 +1,46 @@ +package com.coderising.ood.srp.model; + +import com.coderising.ood.srp.dao.DBUtil; + +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + */ +public class Product { + String id; + String description; + + public Product(String id, String descript) { + this.id = id; + this.description = descript; + } + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } + + public List getSubscribers() { + List userList = null; + String sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + id + "' " + + "and send_mail=1 "; + userList = DBUtil.query(sendMailQuery); + return userList; + + } + + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/User.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/User.java new file mode 100644 index 0000000000..38bec29f59 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/model/User.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp.model; + +/** + * Created by Iden on 2017/6/14. + */ +public class User { + String name; + String eMail; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String geteMail() { + return eMail; + } + + public void seteMail(String eMail) { + this.eMail = eMail; + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GetProductsFromFile.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GetProductsFromFile.java new file mode 100644 index 0000000000..92a1090c5e --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GetProductsFromFile.java @@ -0,0 +1,47 @@ +package com.coderising.ood.srp.service; + +import com.coderising.ood.srp.interfaces.GetProductsFunction; +import com.coderising.ood.srp.model.Product; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + */ +public class GetProductsFromFile implements GetProductsFunction { + public String filePath = "E:\\StudyProjects\\Java\\Workspace\\HomeWork\\coding2017\\liuxin\\ood\\ood-assignment\\" + + "src\\main\\java\\com\\coderising\\ood\\srp\\product_promotion.txt"; + + @Override + public List getProducts() { + BufferedReader br = null; + List products = new ArrayList<>(); + try { + File file = new File(filePath); + br = new BufferedReader(new FileReader(file)); + String temp = null; + while ((temp = br.readLine()) != null) { + String[] data = temp.split(" "); + Product product = new Product(data[0], data[1]); + System.out.println("促销产品ID = " + product.getId()); + System.out.println("促销产品描述 = " + product.getDescription()); + products.add(product); + } + + } catch (IOException e) { + System.out.println("读取文件失败"); + } finally { + try { + br.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + return products; + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GoodsArrivalNotice.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GoodsArrivalNotice.java new file mode 100644 index 0000000000..ee4723ec06 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/GoodsArrivalNotice.java @@ -0,0 +1,13 @@ +package com.coderising.ood.srp.service; + +/** + * Created by Iden on 2017/6/14. + * 到货通知 + */ +public class GoodsArrivalNotice extends Notice { + public GoodsArrivalNotice() { + getProductsFunction = new GetProductsFromFile(); + sendMailFunction = new SendGoodsArrivalMail(); + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/Notice.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/Notice.java new file mode 100644 index 0000000000..6ac8e62402 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/Notice.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp.service; + +import com.coderising.ood.srp.interfaces.GetProductsFunction; +import com.coderising.ood.srp.interfaces.SendMailFunction; +import com.coderising.ood.srp.model.Product; + +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + * 各类通知(降价促销,抢购活动,到货通知等等) + */ +public abstract class Notice { + GetProductsFunction getProductsFunction; + SendMailFunction sendMailFunction; + + public List getProducts() { + return getProductsFunction.getProducts(); + } + + public void sendMail(List products) { + sendMailFunction.sendMail(products); + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/PricePromotion.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/PricePromotion.java new file mode 100644 index 0000000000..ebb59571c0 --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/PricePromotion.java @@ -0,0 +1,12 @@ +package com.coderising.ood.srp.service; + +/** + * Created by Iden on 2017/6/14. + */ +public class PricePromotion extends Notice { + public PricePromotion() { + getProductsFunction = new GetProductsFromFile(); + sendMailFunction = new SendPriceMail(); + } + +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendGoodsArrivalMail.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendGoodsArrivalMail.java new file mode 100644 index 0000000000..79f3a6985f --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendGoodsArrivalMail.java @@ -0,0 +1,42 @@ +package com.coderising.ood.srp.service; + +import com.coderising.ood.srp.interfaces.SendMailFunction; +import com.coderising.ood.srp.model.Mail; +import com.coderising.ood.srp.model.Product; +import com.coderising.ood.srp.model.User; + +import java.util.Iterator; +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + */ +public class SendGoodsArrivalMail implements SendMailFunction { + + + @Override + public void sendMail(List products) { + if (null == products || products.size() == 0) { + System.out.println("没有发现到货的产品"); + return; + } + Iterator iterator = products.iterator(); + while (iterator.hasNext()) { + Product product = iterator.next(); + List userList = product.getSubscribers(); + if (null == userList || userList.size() == 0) { + System.out.println("没有人订阅" + product.getDescription() + " 信息"); + continue; + } + Iterator iter = userList.iterator(); + while (iter.hasNext()) { + User user = (User) iter.next(); + Mail mail = new Mail(); + mail.setSubject("您关注的产品到货了"); + mail.setContent("尊敬的 " + user.getName() + ", 您关注的产品 " + product.getDescription() + " 到货了,欢迎购买"); + mail.setToAddress(user.geteMail()); + mail.send(); + } + } + } +} diff --git a/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendPriceMail.java b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendPriceMail.java new file mode 100644 index 0000000000..bae4803e3f --- /dev/null +++ b/students/2831099157/ood-assignment/src/main/java/com/coderising/ood/srp/service/SendPriceMail.java @@ -0,0 +1,42 @@ +package com.coderising.ood.srp.service; + +import com.coderising.ood.srp.interfaces.SendMailFunction; +import com.coderising.ood.srp.model.Mail; +import com.coderising.ood.srp.model.Product; +import com.coderising.ood.srp.model.User; + +import java.util.Iterator; +import java.util.List; + +/** + * Created by Iden on 2017/6/14. + */ +public class SendPriceMail implements SendMailFunction { + + + @Override + public void sendMail(List products) { + if (null == products || products.size() == 0) { + System.out.println("没有发现需要促销的产品"); + return; + } + Iterator iterator = products.iterator(); + while (iterator.hasNext()) { + Product product = iterator.next(); + List userList = product.getSubscribers(); + if (null == userList || userList.size() == 0) { + System.out.println("没有人订阅 " + product.getDescription() + " 信息"); + continue; + } + Iterator iter = userList.iterator(); + while (iter.hasNext()) { + User user = (User) iter.next(); + Mail mail = new Mail(); + mail.setSubject("您关注的产品降价了"); + mail.setContent("尊敬的 " + user.getName() + ", 您关注的产品 " + product.getDescription() + " 降价了,欢迎购买"); + mail.setToAddress(user.geteMail()); + mail.send(); + } + } + } +} diff --git "a/students/2831099157/ood-assignment/\344\277\203\351\224\200Mail\345\217\221\351\200\201\347\273\203\344\271\240\357\274\210\351\207\215\346\236\204\357\274\211.md" "b/students/2831099157/ood-assignment/\344\277\203\351\224\200Mail\345\217\221\351\200\201\347\273\203\344\271\240\357\274\210\351\207\215\346\236\204\357\274\211.md" new file mode 100644 index 0000000000..33634cb9a9 --- /dev/null +++ "b/students/2831099157/ood-assignment/\344\277\203\351\224\200Mail\345\217\221\351\200\201\347\273\203\344\271\240\357\274\210\351\207\215\346\236\204\357\274\211.md" @@ -0,0 +1,23 @@ +# 第一次OOD练习 # + +## 需求 ## +### 原项目已经实现根据产品列表文件发送促销Mail,需求一直在变化,比如通过数据库获取促销产品或者促销活动改为到货通知,抢购等;为了应变各种变化,需重构代码。 ### +## 需求分析 ## +需求可变因素:
+ +1. 促销产品列表文件可能会变更,或者变更获取方式(如通过数据库获取) +2. 促销活动会根据运营情况变更 +## 重构方案 ## +1. 提取GetProductsFunction,SendMailFunction接口 +2. 添加Notice抽象类,针对接口添加getProducts,sendMai方法 -------各类通知(降价促销,抢购活动,到货通知等等) +3. 添加Mail,Product,User实体类 +4. Mail初始化设置smtpHost,alSmtpHost,fromAddress参数,添加sendMail功能 +5. Product添加getSubscribers功能 +6. 添加GetProductsFunction,SendMailFunction接口实现类 +7. 添加PricePromotion继承Promotion,实现降价促销功能,实例化GetProductsFunction,SendMailFunction接口 +8. 主函数调用sendMail方法 + +## 重构后 ## +重构后项目,可以根据不同运营方案,添加GetProductsFunction,SendMailFunction接口实现类及Notice子类,向订阅者发送通告 + + diff --git a/students/2831099157/out/production/main/com/coderising/ood/srp/product_promotion.txt b/students/2831099157/out/production/main/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/2831099157/out/production/main/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From 19d62a21db181e24d7092c485474d3d3f95746c7 Mon Sep 17 00:00:00 2001 From: ifengdzh Date: Wed, 21 Jun 2017 15:12:22 +0800 Subject: [PATCH 24/73] =?UTF-8?q?srp=20=E5=8E=9F=E5=88=99=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/281918307/ood-ocp/pom.xml | 1 - .../main/java/com/ood/ocp/Application.java | 2 +- .../src/main/resources/log4j.properties | 4 +- students/281918307/ood-srp/pom.xml | 8 ++ .../java/com/ood/srp/file/FileService.java | 6 +- .../ood/srp/file/impl/FileServiceImpl.java | 35 +++++++++ .../java/com/ood/srp/mail/Configuration.java | 34 ++++---- .../com/ood/srp/mail/ConfigurationKeys.java | 6 +- .../java/com/ood/srp/mail/MailService.java | 21 +++++ .../ood/srp/mail/impl/MailServiceImpl.java | 62 +++++++++++++++ .../com/ood/srp/product/ProductDetail.java | 1 + .../ood/srp/product/ProductDetailService.java | 10 ++- .../impl/ProductDetailServiceImpl.java | 43 ++++++++++ .../ood/srp/promotion/PromotionService.java | 21 +---- .../promotion/impl/PromotionServiceImpl.java | 63 +++++++++++++++ .../main/java/com/ood/srp/user/UserInfo.java | 3 +- .../com/ood/srp/user/UserInfoService.java | 16 ++++ .../srp/user/impl/UserInfoServiceImpl.java | 31 ++++++++ .../main/java/com/ood/srp/util/DBUtil.java | 11 ++- .../main/java/com/ood/srp/util/FileUtil.java | 27 ++----- .../main/java/com/ood/srp/util/MailUtil.java | 78 +++---------------- .../src/main/resources/log4j.properties | 4 +- 22 files changed, 343 insertions(+), 144 deletions(-) create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/file/impl/FileServiceImpl.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/mail/impl/MailServiceImpl.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/product/impl/ProductDetailServiceImpl.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/impl/PromotionServiceImpl.java create mode 100644 students/281918307/ood-srp/src/main/java/com/ood/srp/user/impl/UserInfoServiceImpl.java diff --git a/students/281918307/ood-ocp/pom.xml b/students/281918307/ood-ocp/pom.xml index 9daf351b12..284a8b4939 100644 --- a/students/281918307/ood-ocp/pom.xml +++ b/students/281918307/ood-ocp/pom.xml @@ -28,5 +28,4 @@
- \ No newline at end of file diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java index 843af308ec..5fc79ba891 100644 --- a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/Application.java @@ -8,7 +8,7 @@ public class Application { static final Logger logger = Logger.getLogger(Application.class); - public static void main(String [] args) { + public static void main(String[] args) { logger.error("Application running ..."); } } diff --git a/students/281918307/ood-ocp/src/main/resources/log4j.properties b/students/281918307/ood-ocp/src/main/resources/log4j.properties index 508df51466..e70566ce70 100644 --- a/students/281918307/ood-ocp/src/main/resources/log4j.properties +++ b/students/281918307/ood-ocp/src/main/resources/log4j.properties @@ -1,8 +1,6 @@ log4j.rootLogger=debug, stdout - log4j.appender.stdout=org.apache.log4j.ConsoleAppender log4j.appender.stdout.layout=org.apache.log4j.PatternLayout log4j.appender.stdout.layout.ConversionPattern=%-d{yyyy-MM-dd HH:mm:ss} [ %t:%r ] - [ %p ] %l - %m%n - # Third party loggers - log4j.logger.com.ood=debug +log4j.logger.com.ood=debug diff --git a/students/281918307/ood-srp/pom.xml b/students/281918307/ood-srp/pom.xml index 13db2a5ad0..e2c51f2ab2 100644 --- a/students/281918307/ood-srp/pom.xml +++ b/students/281918307/ood-srp/pom.xml @@ -68,6 +68,14 @@ + + org.apache.maven.plugins + maven-compiler-plugin + + 1.8 + 1.8 + + diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java index 301bb6d845..17da5e5add 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/file/FileService.java @@ -1,6 +1,5 @@ package com.ood.srp.file; -import java.io.File; import java.util.List; /** @@ -11,8 +10,9 @@ public interface FileService { /** * 读取文件内容,放到List内 - * @param file + * + * @param filePath * @return */ - List readFile(File file); + List readFile(String filePath) throws Exception; } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/file/impl/FileServiceImpl.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/file/impl/FileServiceImpl.java new file mode 100644 index 0000000000..71385b81ad --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/file/impl/FileServiceImpl.java @@ -0,0 +1,35 @@ +package com.ood.srp.file.impl; + +import com.ood.srp.file.FileService; +import com.ood.srp.util.FileUtil; +import org.springframework.stereotype.Service; + +import java.util.ArrayList; +import java.util.List; + +/** + * 文件处理类 + * Created by yuxia on 2017/6/21. + */ +@Service +public class FileServiceImpl implements FileService { + + + /** + * 获取信息 + * + * @param filePath + * @return + * @throws Exception + */ + public List readFile(String filePath) throws Exception { + List lineList = new ArrayList<>(); + FileUtil fileUtil = new FileUtil(filePath); + while (fileUtil.hasNext()) { + String s = fileUtil.readLine(); + lineList.add(s); + } + fileUtil.close(); + return lineList; + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java index 48ea71dec5..88eb7af347 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/Configuration.java @@ -1,23 +1,27 @@ package com.ood.srp.mail; + import java.util.HashMap; import java.util.Map; public class Configuration { - static Map configurations = new HashMap<>(); - static{ - configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); - configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); - configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); - } - /** - * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 - * @param key - * @return - */ - public String getProperty(String key) { - - return configurations.get(key); - } + static Map configurations = new HashMap<>(); + + static { + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java index 74cc19304a..8199bf780d 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/ConfigurationKeys.java @@ -2,8 +2,8 @@ public class ConfigurationKeys { - public static final String SMTP_SERVER = "smtp.server"; - public static final String ALT_SMTP_SERVER = "alt.smtp.server"; - public static final String EMAIL_ADMIN = "email.admin"; + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java index 55ddcffc56..c85740e19e 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/MailService.java @@ -1,8 +1,29 @@ package com.ood.srp.mail; +import com.ood.srp.user.UserInfo; + +import java.util.List; + /** * Created by ajaxfeng on 2017/6/20. */ public interface MailService { + /** + * 主SMTP服务器地址 + */ + public static final String SMTP_SERVER = "smtp.163.com"; + + /** + * 备用SMTP服务器地址 + */ + public static final String ALT_SMTP_SERVER = "smtp1.163.com"; + + /** + * 以哪个邮箱地址发送给用户 + */ + public static final String EMAIL_ADMIN = "admin@company.com"; + + + public String sendEmail(List userInfoList); } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/impl/MailServiceImpl.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/impl/MailServiceImpl.java new file mode 100644 index 0000000000..e633f94a55 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/mail/impl/MailServiceImpl.java @@ -0,0 +1,62 @@ +package com.ood.srp.mail.impl; + +import com.ood.srp.mail.MailService; +import com.ood.srp.user.UserInfo; +import com.ood.srp.util.MailUtil; +import org.springframework.stereotype.Service; + +import java.util.List; + +/** + * Created by yuxia on 2017/6/21. + */ +@Service +public class MailServiceImpl implements MailService { + + /** + * 发送邮件 + * + * @param userInfoList + * @return + */ + @Override + public String sendEmail(List userInfoList) { + if (userInfoList == null) { + System.out.println("没有邮件发送"); + return "none"; + } + + for (UserInfo info : userInfoList) { + if (!info.getEmail().isEmpty()) { + String emailInfo = generatePromotionEmail(info); + try { + MailUtil.sendPromotionEmail(emailInfo); + } catch (Exception e) { + System.out.println(e.getMessage()); + } + } + } + return "success"; + } + + /** + * 根据用户信息生成促销邮件内容。 + * + * @param userInfo 用户信息。 + * @return 返回生成的邮件。 + */ + private static String generatePromotionEmail(UserInfo userInfo) { + StringBuilder buffer = new StringBuilder(); + + buffer.append("From:").append(EMAIL_ADMIN).append("\n"); + buffer.append("To:").append(userInfo.getEmail()).append("\n"); + buffer.append("Subject:").append("您关注的产品降价了").append("\n"); + buffer.append("Content:").append("尊敬的").append(userInfo.getName()); + buffer.append(", 您关注的产品 ").append(userInfo.getProductDesc()); + buffer.append(" 降价了,欢迎购买!").append("\n"); + + System.out.println(buffer.toString()); + + return buffer.toString(); + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java index edcce88eee..71bfc3e52c 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetail.java @@ -2,6 +2,7 @@ /** * 产品信息数据类。 + * * @since 06.18.2017 */ public class ProductDetail { diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java index 1bc54a563a..0ed1920a18 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/ProductDetailService.java @@ -1,9 +1,17 @@ package com.ood.srp.product; +import java.util.List; + /** * 产品信息 * Created by ajaxfeng on 2017/6/20. */ public interface ProductDetailService { - + /** + * 获取产品详情 + * + * @param lineList + * @return + */ + public List getProductDetailList(List lineList); } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/product/impl/ProductDetailServiceImpl.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/impl/ProductDetailServiceImpl.java new file mode 100644 index 0000000000..9e5f4434a1 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/product/impl/ProductDetailServiceImpl.java @@ -0,0 +1,43 @@ +package com.ood.srp.product.impl; + +import com.ood.srp.product.ProductDetail; +import com.ood.srp.product.ProductDetailService; +import org.springframework.stereotype.Service; + +import java.util.ArrayList; +import java.util.List; + +/** + * 商品信息逻辑 + * Created by yuxia on 2017/6/21. + */ +@Service +public class ProductDetailServiceImpl implements ProductDetailService { + + /** + * 获取商品信息 + * + * @param lineList + * @return + */ + public List getProductDetailList(List lineList) { + List productDetailList = new ArrayList<>(); + lineList.forEach(line -> { + String[] splitInfo = line.split(" "); + if (splitInfo.length >= 2) { + String id = splitInfo[0]; + String description = splitInfo[1]; + ProductDetail productDetail = getProductDetail(id, description); + productDetailList.add(productDetail); + } + }); + return productDetailList; + } + + private ProductDetail getProductDetail(String id, String description) { + ProductDetail productDetail = new ProductDetail(); + productDetail.setId(id); + productDetail.setDescription(description); + return productDetail; + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java index 9ce8a39fe0..1653a981c6 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/PromotionService.java @@ -1,31 +1,16 @@ package com.ood.srp.promotion; -import com.ood.srp.product.ProductDetail; -import com.ood.srp.user.UserInfo; - -import java.util.List; - /** * 促销处理类 * Created by ajaxfeng on 2017/6/20. */ public interface PromotionService { - /** - * 获取产品信息 - * @return - */ - List getPromotionProduct(); - - /** - * 获取用户信息 - * @return - */ - List getPromotionUserInfo(); /** - * 发送促销信息 + * 发布促销信息 + * * @return */ - List sendPromotionInfo(); + String promotion() throws Exception; } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/impl/PromotionServiceImpl.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/impl/PromotionServiceImpl.java new file mode 100644 index 0000000000..c7e104dde5 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/promotion/impl/PromotionServiceImpl.java @@ -0,0 +1,63 @@ +package com.ood.srp.promotion.impl; + +import com.ood.srp.file.FileService; +import com.ood.srp.mail.MailService; +import com.ood.srp.product.ProductDetail; +import com.ood.srp.product.ProductDetailService; +import com.ood.srp.promotion.PromotionService; +import com.ood.srp.user.UserInfo; +import com.ood.srp.user.UserInfoService; +import org.springframework.beans.factory.annotation.Autowired; + +import java.util.ArrayList; +import java.util.List; + +/** + * 发布促销信息 + * Created by yuxia on 2017/6/21. + */ +public class PromotionServiceImpl implements PromotionService { + + private static final String FILE_PATH = "pro.text"; + + @Autowired + FileService fileService; + @Autowired + ProductDetailService productDetailService; + @Autowired + UserInfoService userInfoService; + @Autowired + MailService mailService; + + /** + *

促销


+ * 1. 获取文件内容
+ * 2. 根据文件内容,获取商品信息
+ * 3. 根据商品信息,获得用户信息
+ * 4. 针对用户信息,进行邮件发送
+ * 可扩展行: + * 1. 发送促销信息,可抽象一个接口:具体可以通过邮件、短信等手段发送 + * @return + * @throws Exception + */ + @Override + public String promotion() throws Exception { + List strings = fileService.readFile(FILE_PATH); + List productDetailList = + productDetailService.getProductDetailList(strings); + List idList = productDetailList2IDList(productDetailList); + List userInfoList = userInfoService.listUserInfo(idList); + String s = mailService.sendEmail(userInfoList); + System.out.println(s); + return s; + } + + List productDetailList2IDList(List productDetails) { + List idList = new ArrayList<>(); + for (ProductDetail productDetail : productDetails) { + idList.add(productDetail.getId()); + } + return idList; + } + +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java index 65cc00ea39..14c363fa43 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfo.java @@ -2,6 +2,7 @@ /** * 用户数据类。 + * * @since 06.18.2017 */ public class UserInfo { @@ -9,7 +10,7 @@ public class UserInfo { private String email; private String productDesc; - public UserInfo(String name, String email, String productDesc){ + public UserInfo(String name, String email, String productDesc) { this.name = name; this.email = email; this.productDesc = productDesc; diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java index e828597d4d..da206c4a5a 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/UserInfoService.java @@ -1,9 +1,25 @@ package com.ood.srp.user; +import java.util.List; + /** * 用户逻辑 * Created by ajaxfeng on 2017/6/20. */ public interface UserInfoService { + /** + * 获取用户信息 + * + * @param productID + * @return + */ + public List listUserInfo(String productID); + /** + * 获取用户信息 + * + * @param productID + * @return + */ + public List listUserInfo(List productID); } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/user/impl/UserInfoServiceImpl.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/impl/UserInfoServiceImpl.java new file mode 100644 index 0000000000..5ddd5f6a45 --- /dev/null +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/user/impl/UserInfoServiceImpl.java @@ -0,0 +1,31 @@ +package com.ood.srp.user.impl; + +import com.ood.srp.user.UserInfo; +import com.ood.srp.user.UserInfoService; +import com.ood.srp.util.DBUtil; +import org.springframework.stereotype.Service; + +import java.util.ArrayList; +import java.util.List; + +/** + * Created by yuxia on 2017/6/21. + */ +@Service +public class UserInfoServiceImpl implements UserInfoService { + @Override + public List listUserInfo(String productID) { + List userInfoList = DBUtil.query(productID); + return userInfoList; + } + + @Override + public List listUserInfo(List productIDList) { + List userInfoAll = new ArrayList<>(); + for (String id : productIDList) { + List userInfoList = listUserInfo(id); + userInfoAll.addAll(userInfoList); + } + return userInfoAll; + } +} diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java index 820bbb5dcf..dc9affd22f 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/DBUtil.java @@ -1,7 +1,6 @@ package com.ood.srp.util; -import com.ood.srp.product.ProductDetail; import com.ood.srp.user.UserInfo; import java.util.ArrayList; @@ -22,20 +21,20 @@ public class DBUtil { * 应该从数据库读, 但是简化为直接生成。 * 给一个产品详情,返回一个Array List记载所有订阅该产品的用户信息(名字,邮箱,订阅的产品名称)。 * - * @param productDetail 传产品详情。产品id用来查询数据库。产品名称用于和用户信息绑定 + * @param productID 传产品详情。产品id用来查询数据库。产品名称用于和用户信息绑定 * @return 返回数据库中所有的查询到的结果。 */ - public static List query(ProductDetail productDetail) { - if (productDetail == null || productDetail.getId() == null) + public static List query(String productID) { + if (productID == null) return new ArrayList<>(); String sendMailQuery = "Select name from subscriptions " - + "where product_id= '" + productDetail.getId() + "' " + + "where product_id= '" + productID + "' " + "and send_mail=1 "; //假装用sendMilQuery查了数据库,生成了userList作为查询结果 List userList = new ArrayList<>(); for (int i = 1; i <= 3; i++) { - UserInfo newInfo = new UserInfo("User" + i, "aa@bb.com", productDetail.getDescription()); + UserInfo newInfo = new UserInfo("User" + i, "aa@bb.com", ""); userList.add(newInfo); } return userList; diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java index 060ef0287a..05aa9d9c5b 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/FileUtil.java @@ -1,9 +1,6 @@ package com.ood.srp.util; - -import com.ood.srp.product.ProductDetail; - import java.io.File; import java.io.FileNotFoundException; import java.util.Scanner; @@ -14,6 +11,7 @@ * 此类会打开促销文件,促销文件默认按照: * "id" 空格 "产品名称" * 进行存储,每行一条促销信息。 + * * @since 06.19.2017 */ public class FileUtil { @@ -21,30 +19,19 @@ public class FileUtil { public FileUtil(String filePath) throws FileNotFoundException { - scanner = new Scanner(new File(filePath)); + scanner = new Scanner(new File(filePath)); } - public ProductDetail getNextProduct(){ - String wholeInfo; - ProductDetail nextProduct = new ProductDetail(); - wholeInfo = scanner.nextLine(); - - String[] splitInfo = wholeInfo.split(" "); - if (splitInfo.length < 2) - return nextProduct; - - //促销文件按照 - "id" 空格 "产品名称" 进行记录的 - nextProduct.setId(splitInfo[0]); - nextProduct.setDescription(splitInfo[1]); - - return nextProduct; + public String readLine() { + String wholeInfo = scanner.nextLine(); + return wholeInfo; } - public boolean hasNext(){ + public boolean hasNext() { return scanner.hasNextLine(); } - public void close(){ + public void close() { scanner.close(); } } diff --git a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java index 2f3463e1d8..a6953d5306 100644 --- a/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java +++ b/students/281918307/ood-srp/src/main/java/com/ood/srp/util/MailUtil.java @@ -1,13 +1,10 @@ package com.ood.srp.util; -import com.ood.srp.user.UserInfo; - -import java.util.List; - /** * 邮件发送类。 * 管理邮箱连接,发送等操作。 + * * @since 06.19.2017 */ public class MailUtil { @@ -16,82 +13,25 @@ public class MailUtil { * SMTP连接失败异常。 * 可用getMessage()获得异常内容。 */ - public static class SMTPConnectionFailedException extends Throwable{ - public SMTPConnectionFailedException(String message){ + public static class SMTPConnectionFailedException extends Throwable { + public SMTPConnectionFailedException(String message) { super(message); } } - /** - * 主SMTP服务器地址 - */ - public static final String SMTP_SERVER = "smtp.163.com"; - - /** - * 备用SMTP服务器地址 - */ - public static final String ALT_SMTP_SERVER = "smtp1.163.com"; - - /** - * 以哪个邮箱地址发送给用户 - */ - public static final String EMAIL_ADMIN = "admin@company.com"; - - - /** - * 邮件发送操作。 - * 将降价促销邮件逐个发送给用户信息表中对应的用户。 - * 捕获SMTPConnectionFailedException。提示手动发送。并继续发送下一封邮件。 - * @param usersList 用户信息表。包含用户姓名,邮箱和订阅产品名称。 - */ - public static void sendEmails(List usersList){ - if (usersList == null) { - System.out.println("没有邮件发送"); - return; - } - - for (UserInfo info : usersList){ - if (!info.getEmail().isEmpty()) { - String emailInfo = generatePromotionEmail(info); - try { - sendPromotionEmail(emailInfo); - } catch (SMTPConnectionFailedException e){ - System.out.println("SMTP主副服务器连接失败,请手动发送以下邮件: \n"); - System.out.println(e.getMessage()); - } - } - } - } /** * 假装在发邮件。默认使用主SMTP发送,若发送失败则使用备用SMTP发送。 * 仍然失败,则抛出SMTPConnectFailException异常。 + * * @param emailInfo 要发送的邮件内容 * @throws SMTPConnectionFailedException 若主副SMTP服务器均连接失败,抛出异常。异常中包含完整的发送失败的邮件内容。可通过getMessage()方法获得邮件内容。 */ - private static void sendPromotionEmail(String emailInfo) throws SMTPConnectionFailedException{ - //默认以SMTP_SERVER 发送 - //如果发送失败以ALT_SMTP_SERVER 重新发送 - //如果还失败,throw new SMTPConnectionFailedException(emailInfo). - } - - /** - * 根据用户信息生成促销邮件内容。 - * @param userInfo 用户信息。 - * @return 返回生成的邮件。 - */ - private static String generatePromotionEmail(UserInfo userInfo){ - StringBuilder buffer = new StringBuilder(); - - buffer.append("From:").append(EMAIL_ADMIN).append("\n"); - buffer.append("To:").append(userInfo.getEmail()).append("\n"); - buffer.append("Subject:").append("您关注的产品降价了").append("\n"); - buffer.append("Content:").append("尊敬的").append(userInfo.getName()); - buffer.append(", 您关注的产品 ").append(userInfo.getProductDesc()); - buffer.append(" 降价了,欢迎购买!").append("\n"); + public static void sendPromotionEmail(String emailInfo) throws Exception { + //默认以SMTP_SERVER 发送 + //如果发送失败以ALT_SMTP_SERVER 重新发送 + //如果还失败,throw new SMTPConnectionFailedException(emailInfo). + } - System.out.println(buffer.toString()); - return buffer.toString(); - } } diff --git a/students/281918307/ood-srp/src/main/resources/log4j.properties b/students/281918307/ood-srp/src/main/resources/log4j.properties index 508df51466..e70566ce70 100644 --- a/students/281918307/ood-srp/src/main/resources/log4j.properties +++ b/students/281918307/ood-srp/src/main/resources/log4j.properties @@ -1,8 +1,6 @@ log4j.rootLogger=debug, stdout - log4j.appender.stdout=org.apache.log4j.ConsoleAppender log4j.appender.stdout.layout=org.apache.log4j.PatternLayout log4j.appender.stdout.layout.ConversionPattern=%-d{yyyy-MM-dd HH:mm:ss} [ %t:%r ] - [ %p ] %l - %m%n - # Third party loggers - log4j.logger.com.ood=debug +log4j.logger.com.ood=debug From 9804e978ae0915af4b7ecf7e3c6c537217c50815 Mon Sep 17 00:00:00 2001 From: javmin Date: Wed, 21 Jun 2017 16:18:59 +0800 Subject: [PATCH 25/73] =?UTF-8?q?ood=E4=BD=9C=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/641013587/ood/ood-assignment/pom.xml | 47 ++++++++++++++ .../com/coderising/ood/srp/Configuration.java | 23 +++++++ .../coderising/ood/srp/ConfigurationKeys.java | 9 +++ .../ood/srp/constant/CommonConstant.java | 14 +++++ .../com/coderising/ood/srp/dao/UserDao.java | 26 ++++++++ .../com/coderising/ood/srp/entity/Msg.java | 50 +++++++++++++++ .../coderising/ood/srp/entity/Product.java | 21 +++++++ .../com/coderising/ood/srp/entity/User.java | 20 ++++++ .../ood/srp/main/PromotionMail.java | 33 ++++++++++ .../coderising/ood/srp/product_promotion.txt | 4 ++ .../ood/srp/service/EmailService.java | 61 +++++++++++++++++++ .../ood/srp/service/UserService.java | 17 ++++++ .../com/coderising/ood/srp/util/FileUtil.java | 32 ++++++++++ .../com/coderising/ood/srp/util/MailUtil.java | 20 ++++++ .../ood/srp/util/PropertiesUtil.java | 39 ++++++++++++ .../com/coderising/ood/srp/values.properties | 3 + 16 files changed, 419 insertions(+) create mode 100644 students/641013587/ood/ood-assignment/pom.xml create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/constant/CommonConstant.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/dao/UserDao.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Msg.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Product.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/User.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/UserService.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/PropertiesUtil.java create mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/values.properties diff --git a/students/641013587/ood/ood-assignment/pom.xml b/students/641013587/ood/ood-assignment/pom.xml new file mode 100644 index 0000000000..65607712c0 --- /dev/null +++ b/students/641013587/ood/ood-assignment/pom.xml @@ -0,0 +1,47 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + + + aliyunmaven + http://maven.aliyun.com/nexus/content/groups/public/ + + + + + + + org.apache.maven.plugins + maven-compiler-plugin + 3.2 + + 1.7 + 1.7 + UTF-8 + + + + + diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..f328c1816a --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..8695aed644 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/constant/CommonConstant.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/constant/CommonConstant.java new file mode 100644 index 0000000000..fcba3fc9c2 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/constant/CommonConstant.java @@ -0,0 +1,14 @@ +package com.coderising.ood.srp.constant; + +import com.coderising.ood.srp.entity.Product; +import com.coderising.ood.srp.entity.User; + +public class CommonConstant { + + public static final String SUBJECT = "您关注的产品降价了"; + + public static String getProductMessage(User user,Product product){ + return "尊敬的 "+user.getName()+", 您关注的产品 " + product.getProductDesc() + " 降价了,欢迎购买!"; + } + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/dao/UserDao.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/dao/UserDao.java new file mode 100644 index 0000000000..6b3d11c41b --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/dao/UserDao.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp.dao; +import java.util.ArrayList; +import java.util.List; + +import com.coderising.ood.srp.entity.User; + +public class UserDao { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public List query(String sql){ + + List userList = new ArrayList<>(); + for (int i = 1; i <= 3; i++) { + User userInfo = new User(); + userInfo.setName("User" + i); + userInfo.setEmail("aa@bb.com"); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Msg.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Msg.java new file mode 100644 index 0000000000..8b1bc8b132 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Msg.java @@ -0,0 +1,50 @@ +package com.coderising.ood.srp.entity; + +public class Msg { + + private String smtpHost ; + private String altSmtpHost; + private String fromAddress; + private String toAddress; + private String subject ; + private String message ; + public String getSmtpHost() { + return smtpHost; + } + public void setSmtpHost(String smtpHost) { + this.smtpHost = smtpHost; + } + public String getAltSmtpHost() { + return altSmtpHost; + } + public void setAltSmtpHost(String altSmtpHost) { + this.altSmtpHost = altSmtpHost; + } + public String getFromAddress() { + return fromAddress; + } + public void setFromAddress(String fromAddress) { + this.fromAddress = fromAddress; + } + public String getToAddress() { + return toAddress; + } + public void setToAddress(String toAddress) { + this.toAddress = toAddress; + } + public String getSubject() { + return subject; + } + public void setSubject(String subject) { + this.subject = subject; + } + public String getMessage() { + return message; + } + public void setMessage(String message) { + this.message = message; + } + + + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Product.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Product.java new file mode 100644 index 0000000000..a721930d75 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/Product.java @@ -0,0 +1,21 @@ +package com.coderising.ood.srp.entity; + +public class Product { + private String productID; + private String productDesc; + public String getProductID() { + return productID; + } + public void setProductID(String productID) { + this.productID = productID; + } + public String getProductDesc() { + return productDesc; + } + public void setProductDesc(String productDesc) { + this.productDesc = productDesc; + } + + + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/User.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/User.java new file mode 100644 index 0000000000..78f83b38a1 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/entity/User.java @@ -0,0 +1,20 @@ +package com.coderising.ood.srp.entity; + +public class User { + private String name; + private String email; + public String getName() { + return name; + } + public void setName(String name) { + this.name = name; + } + public String getEmail() { + return email; + } + public void setEmail(String email) { + this.email = email; + } + + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java new file mode 100644 index 0000000000..45191dc71d --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java @@ -0,0 +1,33 @@ +package com.coderising.ood.srp.main; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; + +import com.coderising.ood.srp.Configuration; +import com.coderising.ood.srp.ConfigurationKeys; +import com.coderising.ood.srp.dao.UserDao; +import com.coderising.ood.srp.entity.Product; +import com.coderising.ood.srp.entity.User; +import com.coderising.ood.srp.service.EmailService; +import com.coderising.ood.srp.service.UserService; +import com.coderising.ood.srp.util.FileUtil; +import com.coderising.ood.srp.util.MailUtil; +import com.coderising.ood.srp.util.PropertiesUtil; + +public class PromotionMail { + + public static void main(String[] args) throws Exception { + EmailService emailService = new EmailService(); + UserService userService = new UserService(); + Product product = FileUtil.readRecommendProduct(); + List subscribeUsers = userService.getSubscribeUsers(product); + emailService.sendEMails(false, subscribeUsers, product); + + } + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..0c0124cc61 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java new file mode 100644 index 0000000000..0e46bf5c66 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java @@ -0,0 +1,61 @@ +package com.coderising.ood.srp.service; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; + +import com.coderising.ood.srp.constant.CommonConstant; +import com.coderising.ood.srp.entity.Msg; +import com.coderising.ood.srp.entity.Product; +import com.coderising.ood.srp.entity.User; +import com.coderising.ood.srp.util.MailUtil; +import com.coderising.ood.srp.util.PropertiesUtil; + +public class EmailService { + public static void sendEmail( + boolean debug,Msg msg) { + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(msg.getFromAddress()).append("\n"); + buffer.append("To:").append(msg.getToAddress()).append("\n"); + buffer.append("Subject:").append(msg.getSubject()).append("\n"); + buffer.append("Content:").append(msg.getMessage()).append("\n"); + System.out.println(buffer.toString()); + + } + + + public boolean sendEMails(boolean debug, List mailingList, Product product) throws IOException + { + + System.out.println("开始发送邮件"); + Msg basemsg = PropertiesUtil.BASEMSG; + for (User user : mailingList) { + try + { + basemsg.setToAddress(user.getEmail()); + basemsg.setSubject(CommonConstant.SUBJECT); + basemsg.setMessage(CommonConstant.getProductMessage(user, product)); + if (basemsg.getToAddress().length() > 0) + MailUtil.sendEmail(debug,PropertiesUtil.BASEMSG); + } + catch (Exception e) + { + + try { + MailUtil.sendEmail(debug,PropertiesUtil.BASEMSG); + + } catch (Exception e2) + { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + return false; + } + + } + return true; + + } + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/UserService.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/UserService.java new file mode 100644 index 0000000000..214442bdcd --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/UserService.java @@ -0,0 +1,17 @@ +package com.coderising.ood.srp.service; + +import java.util.List; + +import com.coderising.ood.srp.dao.UserDao; +import com.coderising.ood.srp.entity.Product; +import com.coderising.ood.srp.entity.User; + +public class UserService { + + private UserDao userDao= new UserDao(); + + public List getSubscribeUsers(Product product){ + return userDao.query("Select name from subscriptions where product_id= '" + product.getProductID() +"' and send_mail=1"); + } + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java new file mode 100644 index 0000000000..4f2908a2c6 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/FileUtil.java @@ -0,0 +1,32 @@ +package com.coderising.ood.srp.util; + +import java.io.BufferedReader; +import java.io.FileReader; +import java.io.IOException; + +import com.coderising.ood.srp.entity.Product; + +public class FileUtil { + + public static final String FILE_URL="C:\\Users\\Administrator\\git\\coding2017\\students\\641013587\\ood\\ood-assignment\\src\\main\\java\\com\\coderising\\ood\\srp\\product_promotion.txt"; + + public static Product readRecommendProduct() throws IOException{ + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(FILE_URL)); + String temp = br.readLine(); + String[] data = temp.split(" "); + Product product = new Product(); + product.setProductID(data[0]); + product.setProductDesc(data[1]); + System.out.println("产品ID = " + product.getProductID() + "\n"); + System.out.println("产品描述 = " + product.getProductDesc() + "\n"); + return product; + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java new file mode 100644 index 0000000000..4387e6e73b --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/MailUtil.java @@ -0,0 +1,20 @@ +package com.coderising.ood.srp.util; + +import com.coderising.ood.srp.entity.Msg; + +public class MailUtil { + + public static void sendEmail( + boolean debug,Msg msg) { + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(msg.getFromAddress()).append("\n"); + buffer.append("To:").append(msg.getToAddress()).append("\n"); + buffer.append("Subject:").append(msg.getSubject()).append("\n"); + buffer.append("Content:").append(msg.getMessage()).append("\n"); + System.out.println(buffer.toString()); + + } + + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/PropertiesUtil.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/PropertiesUtil.java new file mode 100644 index 0000000000..7033920b35 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/util/PropertiesUtil.java @@ -0,0 +1,39 @@ +package com.coderising.ood.srp.util; + +import java.io.FileInputStream; +import java.io.IOException; +import java.util.Properties; + +import com.coderising.ood.srp.entity.Msg; + +public class PropertiesUtil { + public static final Properties pro; + public static final Msg BASEMSG = new Msg(); + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + + + static{ + pro = new Properties(); + FileInputStream in = null ; + try { + in= new FileInputStream("C:\\Users\\Administrator\\git\\coding2017\\students\\641013587\\ood\\ood-assignment\\src\\main\\java\\com\\coderising\\ood\\srp\\values.properties"); + pro.load(in); + BASEMSG.setAltSmtpHost(pro.getProperty(ALT_SMTP_SERVER)); + BASEMSG.setSmtpHost(SMTP_SERVER); + BASEMSG.setFromAddress(EMAIL_ADMIN); + } catch (IOException e) { + e.printStackTrace(); + }finally { + try { + in.close(); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + + +} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/values.properties b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/values.properties new file mode 100644 index 0000000000..1f67810743 --- /dev/null +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/values.properties @@ -0,0 +1,3 @@ +smtp.server = smtp.163.com +alt.smtp.server = smtp1.163.com +email.admin = admin@company.com \ No newline at end of file From 4e2a19f13d5f7a2abcdb48771764aa715a94c4a0 Mon Sep 17 00:00:00 2001 From: javmin Date: Wed, 21 Jun 2017 16:27:21 +0800 Subject: [PATCH 26/73] =?UTF-8?q?ood=E4=BD=9C=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/coderising/ood/srp/Configuration.java | 23 ------------------- .../coderising/ood/srp/ConfigurationKeys.java | 9 -------- .../ood/srp/main/PromotionMail.java | 2 -- 3 files changed, 34 deletions(-) delete mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java delete mode 100644 students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java deleted file mode 100644 index f328c1816a..0000000000 --- a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java +++ /dev/null @@ -1,23 +0,0 @@ -package com.coderising.ood.srp; -import java.util.HashMap; -import java.util.Map; - -public class Configuration { - - static Map configurations = new HashMap<>(); - static{ - configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); - configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); - configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); - } - /** - * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 - * @param key - * @return - */ - public String getProperty(String key) { - - return configurations.get(key); - } - -} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java deleted file mode 100644 index 8695aed644..0000000000 --- a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java +++ /dev/null @@ -1,9 +0,0 @@ -package com.coderising.ood.srp; - -public class ConfigurationKeys { - - public static final String SMTP_SERVER = "smtp.server"; - public static final String ALT_SMTP_SERVER = "alt.smtp.server"; - public static final String EMAIL_ADMIN = "email.admin"; - -} diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java index 45191dc71d..217a42ceb1 100644 --- a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/main/PromotionMail.java @@ -8,8 +8,6 @@ import java.util.Iterator; import java.util.List; -import com.coderising.ood.srp.Configuration; -import com.coderising.ood.srp.ConfigurationKeys; import com.coderising.ood.srp.dao.UserDao; import com.coderising.ood.srp.entity.Product; import com.coderising.ood.srp.entity.User; From 6a4b51197ca4559f648db44d723a365d60692152 Mon Sep 17 00:00:00 2001 From: yangzhm Date: Wed, 21 Jun 2017 16:27:44 +0800 Subject: [PATCH 27/73] pull base source of OCP --- .../java/com/coderising/ood/ocp/DateUtil.java | 10 +++++ .../java/com/coderising/ood/ocp/Logger.java | 38 +++++++++++++++++++ .../java/com/coderising/ood/ocp/MailUtil.java | 10 +++++ .../java/com/coderising/ood/ocp/SMSUtil.java | 10 +++++ .../coderising/ood/ocp/good/Formatter.java | 7 ++++ .../ood/ocp/good/FormatterFactory.java | 13 +++++++ .../ood/ocp/good/HtmlFormatter.java | 11 ++++++ .../com/coderising/ood/ocp/good/Logger.java | 18 +++++++++ .../coderising/ood/ocp/good/RawFormatter.java | 11 ++++++ .../com/coderising/ood/ocp/good/Sender.java | 7 ++++ 10 files changed, 135 insertions(+) create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Formatter.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/FormatterFactory.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/HtmlFormatter.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Logger.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/RawFormatter.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Sender.java diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..b6cf28c096 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..0357c4d912 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,38 @@ +package com.coderising.ood.ocp; + +public class Logger { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + int type = 0; + int method = 0; + + public Logger(int logType, int logMethod){ + this.type = logType; + this.method = logMethod; + } + public void log(String msg){ + + String logMsg = msg; + + if(this.type == RAW_LOG){ + logMsg = msg; + } else if(this.type == RAW_LOG_WITH_DATE){ + String txtDate = DateUtil.getCurrentDateAsString(); + logMsg = txtDate + ": " + msg; + } + + if(this.method == EMAIL_LOG){ + MailUtil.send(logMsg); + } else if(this.method == SMS_LOG){ + SMSUtil.send(logMsg); + } else if(this.method == PRINT_LOG){ + System.out.println(logMsg); + } + } +} + diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..ec54b839c5 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..13cf802418 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Formatter.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Formatter.java new file mode 100644 index 0000000000..b6e2ccbc16 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Formatter.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp.good; + +public interface Formatter { + + String format(String msg); + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/FormatterFactory.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/FormatterFactory.java new file mode 100644 index 0000000000..3c2009a674 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/FormatterFactory.java @@ -0,0 +1,13 @@ +package com.coderising.ood.ocp.good; + +public class FormatterFactory { + public static Formatter createFormatter(int type){ + if(type == 1){ + return new RawFormatter(); + } + if (type == 2){ + return new HtmlFormatter(); + } + return null; + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/HtmlFormatter.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/HtmlFormatter.java new file mode 100644 index 0000000000..3d375f5acc --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/HtmlFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.good; + +public class HtmlFormatter implements Formatter { + + @Override + public String format(String msg) { + + return null; + } + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Logger.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Logger.java new file mode 100644 index 0000000000..f206472d0d --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Logger.java @@ -0,0 +1,18 @@ +package com.coderising.ood.ocp.good; + +public class Logger { + + private Formatter formatter; + private Sender sender; + + public Logger(Formatter formatter,Sender sender){ + this.formatter = formatter; + this.sender = sender; + } + public void log(String msg){ + sender.send(formatter.format(msg)) ; + } + + +} + diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/RawFormatter.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/RawFormatter.java new file mode 100644 index 0000000000..7f1cb4ae30 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/RawFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.good; + +public class RawFormatter implements Formatter { + + @Override + public String format(String msg) { + + return null; + } + +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Sender.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Sender.java new file mode 100644 index 0000000000..aaa46c1fb7 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/good/Sender.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp.good; + +public interface Sender { + + void send(String msg); + +} From 5af33a4bb6af88de966bdc62d5884bda09e9be68 Mon Sep 17 00:00:00 2001 From: yangzhm Date: Wed, 21 Jun 2017 16:29:48 +0800 Subject: [PATCH 28/73] modify project according to OCP rule --- .../com/coderising/ood/ocp/ComSender.java | 7 +++++++ .../java/com/coderising/ood/ocp/LogType.java | 9 +++++++++ .../java/com/coderising/ood/ocp/Logger.java | 19 +++---------------- .../java/com/coderising/ood/ocp/MailUtil.java | 4 ++-- .../java/com/coderising/ood/ocp/SMSUtil.java | 4 ++-- .../java/com/coderising/ood/ocp/Sender.java | 5 +++++ .../com/coderising/ood/ocp/SenderFactory.java | 15 +++++++++++++++ 7 files changed, 43 insertions(+), 20 deletions(-) create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/ComSender.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/LogType.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Sender.java create mode 100644 students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SenderFactory.java diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/ComSender.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/ComSender.java new file mode 100644 index 0000000000..19f2c796b0 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/ComSender.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp; + +public class ComSender implements Sender { + public void send(String msg) { + System.out.println(msg); + } +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/LogType.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/LogType.java new file mode 100644 index 0000000000..d33d7d0240 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/LogType.java @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp; + +public class LogType { + public static final int RAW_LOG = 1; + public static final int RAW_LOG_WITH_DATE = 2; + public static final int EMAIL_LOG = 1; + public static final int SMS_LOG = 2; + public static final int PRINT_LOG = 3; +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java index 0357c4d912..45525df9ba 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -1,13 +1,6 @@ package com.coderising.ood.ocp; public class Logger { - - public final int RAW_LOG = 1; - public final int RAW_LOG_WITH_DATE = 2; - public final int EMAIL_LOG = 1; - public final int SMS_LOG = 2; - public final int PRINT_LOG = 3; - int type = 0; int method = 0; @@ -19,20 +12,14 @@ public void log(String msg){ String logMsg = msg; - if(this.type == RAW_LOG){ + if(this.type == LogType.RAW_LOG){ logMsg = msg; - } else if(this.type == RAW_LOG_WITH_DATE){ + } else if(this.type == LogType.RAW_LOG_WITH_DATE){ String txtDate = DateUtil.getCurrentDateAsString(); logMsg = txtDate + ": " + msg; } - if(this.method == EMAIL_LOG){ - MailUtil.send(logMsg); - } else if(this.method == SMS_LOG){ - SMSUtil.send(logMsg); - } else if(this.method == PRINT_LOG){ - System.out.println(logMsg); - } + SenderFactory.createSender(type).send(logMsg); } } diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java index ec54b839c5..dff0eb9748 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -1,8 +1,8 @@ package com.coderising.ood.ocp; -public class MailUtil { +public class MailUtil implements Sender{ - public static void send(String logMsg) { + public void send(String logMsg) { // TODO Auto-generated method stub } diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java index 13cf802418..be47b2c084 100644 --- a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -1,8 +1,8 @@ package com.coderising.ood.ocp; -public class SMSUtil { +public class SMSUtil implements Sender { - public static void send(String logMsg) { + public void send(String logMsg) { // TODO Auto-generated method stub } diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Sender.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Sender.java new file mode 100644 index 0000000000..4bb54aa1e8 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/Sender.java @@ -0,0 +1,5 @@ +package com.coderising.ood.ocp; + +public interface Sender { + public void send(String msg); +} diff --git a/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SenderFactory.java b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SenderFactory.java new file mode 100644 index 0000000000..6915ff2992 --- /dev/null +++ b/students/495232796/OOD/ood-assignment/src/main/java/com/coderising/ood/ocp/SenderFactory.java @@ -0,0 +1,15 @@ +package com.coderising.ood.ocp; + +public class SenderFactory { + public static Sender createSender(int type) { + if(type == LogType.EMAIL_LOG){ + return new MailUtil(); + } else if(type == LogType.SMS_LOG){ + return new SMSUtil(); + } else if(type == LogType.PRINT_LOG){ + return new ComSender(); + } + + return new ComSender(); + } +} From d5e10f962ed71bdbc4f9abc77a7d0f2a45736efb Mon Sep 17 00:00:00 2001 From: javmin Date: Wed, 21 Jun 2017 16:42:36 +0800 Subject: [PATCH 29/73] bug --- .../coderising/ood/srp/service/EmailService.java | 16 ++-------------- 1 file changed, 2 insertions(+), 14 deletions(-) diff --git a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java index 0e46bf5c66..0bd0841517 100644 --- a/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java +++ b/students/641013587/ood/ood-assignment/src/main/java/com/coderising/ood/srp/service/EmailService.java @@ -13,18 +13,6 @@ import com.coderising.ood.srp.util.PropertiesUtil; public class EmailService { - public static void sendEmail( - boolean debug,Msg msg) { - //假装发了一封邮件 - StringBuilder buffer = new StringBuilder(); - buffer.append("From:").append(msg.getFromAddress()).append("\n"); - buffer.append("To:").append(msg.getToAddress()).append("\n"); - buffer.append("Subject:").append(msg.getSubject()).append("\n"); - buffer.append("Content:").append(msg.getMessage()).append("\n"); - System.out.println(buffer.toString()); - - } - public boolean sendEMails(boolean debug, List mailingList, Product product) throws IOException { @@ -38,13 +26,13 @@ public boolean sendEMails(boolean debug, List mailingList, Product product basemsg.setSubject(CommonConstant.SUBJECT); basemsg.setMessage(CommonConstant.getProductMessage(user, product)); if (basemsg.getToAddress().length() > 0) - MailUtil.sendEmail(debug,PropertiesUtil.BASEMSG); + MailUtil.sendEmail(debug,basemsg); } catch (Exception e) { try { - MailUtil.sendEmail(debug,PropertiesUtil.BASEMSG); + MailUtil.sendEmail(debug,basemsg); } catch (Exception e2) { From 988a409828c6b1b5e749929861758524e361dc58 Mon Sep 17 00:00:00 2001 From: GordenChow <513274874@qq.com> Date: Wed, 21 Jun 2017 16:44:03 +0800 Subject: [PATCH 30/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E5=AD=A3=E7=AC=AC?= =?UTF-8?q?=E4=BA=8C=E6=AC=A1=E4=BD=9C=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 第二季第二次作业 --- .../java/com/coderising/ood/ocp/DateUtil.java | 10 +++++ .../java/com/coderising/ood/ocp/Logger.java | 39 +++++++++++++++++++ .../java/com/coderising/ood/ocp/MailUtil.java | 10 +++++ .../java/com/coderising/ood/ocp/SMSUtil.java | 10 +++++ .../com/coderising/ood/ocp/mine/Fomatter.java | 8 ++++ .../com/coderising/ood/ocp/mine/Logger.java | 19 +++++++++ .../ood/ocp/mine/MailProcessor.java | 10 +++++ .../ood/ocp/mine/PrintProcessor.java | 10 +++++ .../coderising/ood/ocp/mine/Processor.java | 8 ++++ .../ood/ocp/mine/RawLogFormatter.java | 11 ++++++ .../ood/ocp/mine/RawWithDateLogFormatter.java | 13 +++++++ .../coderising/ood/ocp/mine/SMSProcessor.java | 10 +++++ 12 files changed, 158 insertions(+) create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Fomatter.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Logger.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/MailProcessor.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/PrintProcessor.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Processor.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawLogFormatter.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawWithDateLogFormatter.java create mode 100644 students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/SMSProcessor.java diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..0d0d01098f --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..e404d9e702 --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,39 @@ +package com.coderising.ood.ocp; + +public class Logger { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + int type = 0; + int method = 0; + + public Logger(int logType, int logMethod){ + this.type = logType; + this.method = logMethod; + } + public void log(String msg){ + + String logMsg = msg; + + if(this.type == RAW_LOG){ + logMsg = msg; + } else if(this.type == RAW_LOG_WITH_DATE){ + String txtDate = DateUtil.getCurrentDateAsString(); + logMsg = txtDate + ": " + msg; + } + + if(this.method == EMAIL_LOG){ + MailUtil.send(logMsg); + } else if(this.method == SMS_LOG){ + SMSUtil.send(logMsg); + } else if(this.method == PRINT_LOG){ + System.out.println(logMsg); + } + } +} + diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..59d77649a2 --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..fab4cd01b7 --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Fomatter.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Fomatter.java new file mode 100644 index 0000000000..6d107d54e9 --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Fomatter.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public interface Fomatter { + public String format(String message); +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Logger.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Logger.java new file mode 100644 index 0000000000..e25da9ca4b --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Logger.java @@ -0,0 +1,19 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public class Logger { + + private Fomatter fomatter; + private Processor processor; + + public Logger(Fomatter fomatter, Processor processor) { + this.fomatter = fomatter; + this.processor = processor; + } + + public void log(String message){ + processor.process(fomatter.format(message)); + } +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/MailProcessor.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/MailProcessor.java new file mode 100644 index 0000000000..c3ce50d5ec --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/MailProcessor.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public class MailProcessor implements Processor { + public void process(String message) { + System.out.println("Mail sending message :"+message); + } +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/PrintProcessor.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/PrintProcessor.java new file mode 100644 index 0000000000..13b983064d --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/PrintProcessor.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public class PrintProcessor implements Processor { + public void process(String message) { + System.out.println("Printing message :"+message); + } +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Processor.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Processor.java new file mode 100644 index 0000000000..4cca74572f --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/Processor.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public interface Processor { + public void process(String message); +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawLogFormatter.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawLogFormatter.java new file mode 100644 index 0000000000..550361b511 --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawLogFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public class RawLogFormatter implements Fomatter { + + public String format(String message) { + return message; + } +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawWithDateLogFormatter.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawWithDateLogFormatter.java new file mode 100644 index 0000000000..80da623d5d --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/RawWithDateLogFormatter.java @@ -0,0 +1,13 @@ +package com.coderising.ood.ocp.mine; + +import java.util.Date; + +/** + * Created by guodongchow on 2017/6/21. + */ +public class RawWithDateLogFormatter implements Fomatter { + public String format(String message) { + String txtDate = new Date().toString(); + return txtDate + ":" + message; + } +} diff --git a/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/SMSProcessor.java b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/SMSProcessor.java new file mode 100644 index 0000000000..946c14dea0 --- /dev/null +++ b/students/513274874/ood/ood-assignment/src/main/java/com/coderising/ood/ocp/mine/SMSProcessor.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.mine; + +/** + * Created by guodongchow on 2017/6/21. + */ +public class SMSProcessor implements Processor { + public void process(String message) { + System.out.println("SMS sending message :" + message); + } +} From 3e1703a7763bea71581892b0deaa044f4a247163 Mon Sep 17 00:00:00 2001 From: skomefen <1072760797@qq.com> Date: Wed, 21 Jun 2017 19:16:58 +0800 Subject: [PATCH 31/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E5=AD=A3=E7=AC=AC?= =?UTF-8?q?=E4=B8=80=E6=AC=A1=E5=A4=A7=E4=BD=9C=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/com/coderising/ood/ocp/DateUtil.java | 10 +++ .../src/com/coderising/ood/ocp/Logger.java | 38 +++++++++ .../src/com/coderising/ood/ocp/MailUtil.java | 10 +++ .../src/com/coderising/ood/ocp/SMSUtil.java | 10 +++ .../coderising/ood/ocp/good/Formatter.java | 7 ++ .../ood/ocp/good/FormatterFactory.java | 13 ++++ .../ood/ocp/good/HtmlFormatter.java | 11 +++ .../com/coderising/ood/ocp/good/Logger.java | 18 +++++ .../coderising/ood/ocp/good/RawFormatter.java | 11 +++ .../com/coderising/ood/ocp/good/Sender.java | 7 ++ .../com/coderising/ood/srp/Configuration.java | 58 ++++++++++++++ .../coderising/ood/srp/ConfigurationKeys.java | 9 +++ .../coderising/ood/srp/ConfigureEmail.java | 58 ++++++++++++++ .../src/com/coderising/ood/srp/DBUtil.java | 27 +++++++ .../src/com/coderising/ood/srp/EmailBean.java | 50 ++++++++++++ .../src/com/coderising/ood/srp/MailUtil.java | 24 ++++++ .../com/coderising/ood/srp/MailingDao.java | 23 ++++++ .../src/com/coderising/ood/srp/Product.java | 62 +++++++++++++++ .../com/coderising/ood/srp/PromotionMail.java | 77 +++++++++++++++++++ .../coderising/ood/srp/product_promotion.txt | 4 + 20 files changed, 527 insertions(+) create mode 100644 students/1072760797/src/com/coderising/ood/ocp/DateUtil.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/Logger.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/MailUtil.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/SMSUtil.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/good/Formatter.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/good/FormatterFactory.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/good/HtmlFormatter.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/good/Logger.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/good/RawFormatter.java create mode 100644 students/1072760797/src/com/coderising/ood/ocp/good/Sender.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/Configuration.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/ConfigureEmail.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/DBUtil.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/EmailBean.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/MailUtil.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/MailingDao.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/Product.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/1072760797/src/com/coderising/ood/srp/product_promotion.txt diff --git a/students/1072760797/src/com/coderising/ood/ocp/DateUtil.java b/students/1072760797/src/com/coderising/ood/ocp/DateUtil.java new file mode 100644 index 0000000000..b6cf28c096 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/Logger.java b/students/1072760797/src/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..0357c4d912 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,38 @@ +package com.coderising.ood.ocp; + +public class Logger { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + int type = 0; + int method = 0; + + public Logger(int logType, int logMethod){ + this.type = logType; + this.method = logMethod; + } + public void log(String msg){ + + String logMsg = msg; + + if(this.type == RAW_LOG){ + logMsg = msg; + } else if(this.type == RAW_LOG_WITH_DATE){ + String txtDate = DateUtil.getCurrentDateAsString(); + logMsg = txtDate + ": " + msg; + } + + if(this.method == EMAIL_LOG){ + MailUtil.send(logMsg); + } else if(this.method == SMS_LOG){ + SMSUtil.send(logMsg); + } else if(this.method == PRINT_LOG){ + System.out.println(logMsg); + } + } +} + diff --git a/students/1072760797/src/com/coderising/ood/ocp/MailUtil.java b/students/1072760797/src/com/coderising/ood/ocp/MailUtil.java new file mode 100644 index 0000000000..ec54b839c5 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/SMSUtil.java b/students/1072760797/src/com/coderising/ood/ocp/SMSUtil.java new file mode 100644 index 0000000000..13cf802418 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/good/Formatter.java b/students/1072760797/src/com/coderising/ood/ocp/good/Formatter.java new file mode 100644 index 0000000000..b6e2ccbc16 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/good/Formatter.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp.good; + +public interface Formatter { + + String format(String msg); + +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/good/FormatterFactory.java b/students/1072760797/src/com/coderising/ood/ocp/good/FormatterFactory.java new file mode 100644 index 0000000000..3c2009a674 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/good/FormatterFactory.java @@ -0,0 +1,13 @@ +package com.coderising.ood.ocp.good; + +public class FormatterFactory { + public static Formatter createFormatter(int type){ + if(type == 1){ + return new RawFormatter(); + } + if (type == 2){ + return new HtmlFormatter(); + } + return null; + } +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/good/HtmlFormatter.java b/students/1072760797/src/com/coderising/ood/ocp/good/HtmlFormatter.java new file mode 100644 index 0000000000..3d375f5acc --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/good/HtmlFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.good; + +public class HtmlFormatter implements Formatter { + + @Override + public String format(String msg) { + + return null; + } + +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/good/Logger.java b/students/1072760797/src/com/coderising/ood/ocp/good/Logger.java new file mode 100644 index 0000000000..f206472d0d --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/good/Logger.java @@ -0,0 +1,18 @@ +package com.coderising.ood.ocp.good; + +public class Logger { + + private Formatter formatter; + private Sender sender; + + public Logger(Formatter formatter,Sender sender){ + this.formatter = formatter; + this.sender = sender; + } + public void log(String msg){ + sender.send(formatter.format(msg)) ; + } + + +} + diff --git a/students/1072760797/src/com/coderising/ood/ocp/good/RawFormatter.java b/students/1072760797/src/com/coderising/ood/ocp/good/RawFormatter.java new file mode 100644 index 0000000000..7f1cb4ae30 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/good/RawFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.good; + +public class RawFormatter implements Formatter { + + @Override + public String format(String msg) { + + return null; + } + +} diff --git a/students/1072760797/src/com/coderising/ood/ocp/good/Sender.java b/students/1072760797/src/com/coderising/ood/ocp/good/Sender.java new file mode 100644 index 0000000000..aaa46c1fb7 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/good/Sender.java @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp.good; + +public interface Sender { + + void send(String msg); + +} diff --git a/students/1072760797/src/com/coderising/ood/srp/Configuration.java b/students/1072760797/src/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..c458c8774a --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,58 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + private static Map configurations = new HashMap<>(); + private static String smtpHost; + private static String altSmtpHost; + private static String fromAddress; + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public Configuration(){ + setSMTPHost(); + setAltSMTPHost(); + setFromAddress(); + } + public String getProperty(String key) { + + return configurations.get(key); + } + + protected void setSMTPHost() + { + smtpHost = this.getProperty(ConfigurationKeys.SMTP_SERVER); + } + + protected void setAltSMTPHost() + { + altSmtpHost = this.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + + } + + protected void setFromAddress() + { + fromAddress = this.getProperty(ConfigurationKeys.EMAIL_ADMIN); + } + + public static String getSmtpHost() { + return smtpHost; + } + public static String getAltSmtpHost() { + return altSmtpHost; + } + public static String getFromAddress() { + return fromAddress; + } + + +} diff --git a/students/1072760797/src/com/coderising/ood/srp/ConfigurationKeys.java b/students/1072760797/src/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..8695aed644 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/1072760797/src/com/coderising/ood/srp/ConfigureEmail.java b/students/1072760797/src/com/coderising/ood/srp/ConfigureEmail.java new file mode 100644 index 0000000000..87af1e42db --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/ConfigureEmail.java @@ -0,0 +1,58 @@ +package com.coderising.ood.srp; + +import java.io.IOException; +import java.util.HashMap; + +public class ConfigureEmail { + + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + private Configuration config = null; + private EmailBean email = new EmailBean(); + private Product product; + + private String message; + private String subject; + private String toAddress; + + public ConfigureEmail(Configuration config, Product product, + HashMap userInfo) { + + this.config = config; + this.product = product; + + setMessage(userInfo); + setToAddress(userInfo); + + setBean(); + + } + + private void setBean() { + + email.setFromAddress(config.getFromAddress()); + email.setMessage(message); + email.setSmtpHost(config.getSmtpHost()); + email.setSubject(subject); + email.setToAddress(toAddress); + } + + public EmailBean getEmail() { + return email; + } + + public void setMessage(HashMap userInfo) { + + String name = (String) userInfo.get(NAME_KEY); + + subject = "您关注的产品降价了"; + message = "尊敬的 " + name + ", 您关注的产品 " + product.getProductDesc() + + " 降价了,欢迎购买!"; + } + + protected void setToAddress(HashMap userInfo) { + toAddress = (String) userInfo.get(EMAIL_KEY); + } + +} diff --git a/students/1072760797/src/com/coderising/ood/srp/DBUtil.java b/students/1072760797/src/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..7597905da1 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,27 @@ +package com.coderising.ood.srp; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * + * @param sql + * @return + */ + public static List query(String sql) { + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com"); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/1072760797/src/com/coderising/ood/srp/EmailBean.java b/students/1072760797/src/com/coderising/ood/srp/EmailBean.java new file mode 100644 index 0000000000..d5923b9f28 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/EmailBean.java @@ -0,0 +1,50 @@ +package com.coderising.ood.srp; + +public class EmailBean { + private String toAddress; + private String fromAddress; + private String subject; + private String message; + private String smtpHost; + + public String getToAddress() { + return toAddress; + } + + public void setToAddress(String toAddress) { + this.toAddress = toAddress; + } + + public String getFromAddress() { + return fromAddress; + } + + public void setFromAddress(String fromAddress) { + this.fromAddress = fromAddress; + } + + public String getSubject() { + return subject; + } + + public void setSubject(String subject) { + this.subject = subject; + } + + public String getMessage() { + return message; + } + + public void setMessage(String message) { + this.message = message; + } + + public String getSmtpHost() { + return smtpHost; + } + + public void setSmtpHost(String smtpHost) { + this.smtpHost = smtpHost; + } + +} diff --git a/students/1072760797/src/com/coderising/ood/srp/MailUtil.java b/students/1072760797/src/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..508a11f3d8 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,24 @@ +package com.coderising.ood.srp; + +public class MailUtil { + + public static void sendEmail(String toAddress, String fromAddress, + String subject, String message, String smtpHost, boolean debug) { + // 假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + + } + + public static void sendEmail(EmailBean email, boolean debug) { + // TODO Auto-generated method stub + sendEmail(email.getToAddress(), email.getFromAddress(), + email.getSubject(), email.getMessage(), email.getSmtpHost(), + debug); + } + +} diff --git a/students/1072760797/src/com/coderising/ood/srp/MailingDao.java b/students/1072760797/src/com/coderising/ood/srp/MailingDao.java new file mode 100644 index 0000000000..cb5924f604 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/MailingDao.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp; + +import java.util.List; + +public class MailingDao { + + private String sendMailQuery; + public List getQuery(String productID) throws Exception { + + sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + + System.out.println("loadQuery set"); + + return loadMailingList(); + } + + private List loadMailingList() throws Exception { + return DBUtil.query(this.sendMailQuery); + } +} diff --git a/students/1072760797/src/com/coderising/ood/srp/Product.java b/students/1072760797/src/com/coderising/ood/srp/Product.java new file mode 100644 index 0000000000..7b5abd3c88 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/Product.java @@ -0,0 +1,62 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; + +public class Product { + + private File file = null; + private String productID; + private String productDesc; + public Product(){} + public Product(File file) throws IOException{ + this.file = file; + //读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 + readFile(file); + } + protected void readFile(File file) throws IOException // @02C + { + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + setProductID(data[0]); + setProductDesc(data[1]); + + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + public void setFile(File file) throws IOException { + this.file = file; + readFile(file); + } + public String getProductID() { + if(productID.isEmpty()){ + throw new RuntimeException("no productID"); + } + return productID; + } + public void setProductID(String productID) { + this.productID = productID; + } + public String getProductDesc() { + if(productDesc.isEmpty()){ + throw new RuntimeException("no productDesc"); + } + return productDesc; + } + public void setProductDesc(String productDesc) { + this.productDesc = productDesc; + } +} diff --git a/students/1072760797/src/com/coderising/ood/srp/PromotionMail.java b/students/1072760797/src/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..b2713840e0 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,77 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.io.Serializable; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; + +public class PromotionMail { + + List mailingList = null; + private static Configuration config; + + private Product product = null; + + public static void main(String[] args) throws Exception { + File f = new File("src/com/coderising/ood/srp/product_promotion.txt"); + boolean emailDebug = false; + + PromotionMail pe = new PromotionMail(f, emailDebug); + + } + + public PromotionMail(File file, boolean mailDebug) throws Exception { + + init(file, mailDebug); + + } + + private void init(File file, boolean mailDebug) throws Exception { + product = new Product(file); + config = new Configuration(); + MailingDao dao = new MailingDao(); + mailingList = dao.getQuery(product.getProductID()); + + sendEMails(mailDebug, mailingList); + + } + + protected void sendEMails(boolean debug, List mailingList) + throws IOException { + + System.out.println("开始发送邮件"); + + if (mailingList != null) { + Iterator iter = mailingList.iterator(); + while (iter.hasNext()) { + ConfigureEmail ce = new ConfigureEmail(config, product, + (HashMap) iter.next()); + EmailBean email = ce.getEmail(); + try { + if (email.getToAddress().length() > 0) + MailUtil.sendEmail(email, debug); + } catch (Exception e) { + + try { + MailUtil.sendEmail(email, debug); + + } catch (Exception e2) { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + + e2.getMessage()); + } + } + } + + } + + else { + System.out.println("没有邮件发送"); + + } + + } +} diff --git a/students/1072760797/src/com/coderising/ood/srp/product_promotion.txt b/students/1072760797/src/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From af065578cd2fb97b12d79d5a53a09a0e7889bbdf Mon Sep 17 00:00:00 2001 From: skomefen <1072760797@qq.com> Date: Wed, 21 Jun 2017 20:13:23 +0800 Subject: [PATCH 32/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E5=AD=A3=E7=AC=AC?= =?UTF-8?q?=E4=BA=8C=E6=AC=A1=E5=B0=8F=E4=BD=9C=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/com/coderising/ood/ocp/Logger.java | 39 +++++-------------- .../com/coderising/ood/ocp/RAW_Logger.java | 18 +++++++++ 2 files changed, 27 insertions(+), 30 deletions(-) create mode 100644 students/1072760797/src/com/coderising/ood/ocp/RAW_Logger.java diff --git a/students/1072760797/src/com/coderising/ood/ocp/Logger.java b/students/1072760797/src/com/coderising/ood/ocp/Logger.java index 0357c4d912..b89d355fef 100644 --- a/students/1072760797/src/com/coderising/ood/ocp/Logger.java +++ b/students/1072760797/src/com/coderising/ood/ocp/Logger.java @@ -1,38 +1,17 @@ package com.coderising.ood.ocp; -public class Logger { +public abstract class Logger { - public final int RAW_LOG = 1; - public final int RAW_LOG_WITH_DATE = 2; - public final int EMAIL_LOG = 1; - public final int SMS_LOG = 2; - public final int PRINT_LOG = 3; - - int type = 0; - int method = 0; - - public Logger(int logType, int logMethod){ - this.type = logType; - this.method = logMethod; - } + public void log(String msg){ + + setMsg(msg); - String logMsg = msg; - - if(this.type == RAW_LOG){ - logMsg = msg; - } else if(this.type == RAW_LOG_WITH_DATE){ - String txtDate = DateUtil.getCurrentDateAsString(); - logMsg = txtDate + ": " + msg; - } - - if(this.method == EMAIL_LOG){ - MailUtil.send(logMsg); - } else if(this.method == SMS_LOG){ - SMSUtil.send(logMsg); - } else if(this.method == PRINT_LOG){ - System.out.println(logMsg); - } + sendMsg(msg); } + + public abstract void setMsg(String msg); + public abstract void sendMsg(String logMsg); + } diff --git a/students/1072760797/src/com/coderising/ood/ocp/RAW_Logger.java b/students/1072760797/src/com/coderising/ood/ocp/RAW_Logger.java new file mode 100644 index 0000000000..c3e684e735 --- /dev/null +++ b/students/1072760797/src/com/coderising/ood/ocp/RAW_Logger.java @@ -0,0 +1,18 @@ +package com.coderising.ood.ocp; + +public class RAW_Logger extends Logger { + + @Override + public void setMsg(String msg) { + // TODO Auto-generated method stub + String logMsg = msg; + logMsg = msg; + } + + @Override + public void sendMsg(String logMsg) { + // TODO Auto-generated method stub + MailUtil.send(logMsg); + } + +} From 4e650533c4cd08f1dc4e4d8b7d10cdc8482174ba Mon Sep 17 00:00:00 2001 From: YouHmilyForProgramming <706097141@qq.com> Date: Wed, 21 Jun 2017 20:38:51 +0800 Subject: [PATCH 33/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E6=AC=A1=E4=BD=9C?= =?UTF-8?q?=E4=B8=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../ocp/DateUtil.java" | 10 ++++++++++ .../ocp/EmailLogger.java" | 9 +++++++++ .../ocp/LogOutput.java" | 8 ++++++++ .../ocp/Logger.java" | 7 +++++++ .../ocp/MailUtil.java" | 10 ++++++++++ .../ocp/PrintLogger.java" | 9 +++++++++ .../ocp/RawLogOutput.java" | 9 +++++++++ .../ocp/RawLogWithDateOutput.java" | 12 ++++++++++++ .../ocp/SMSUtil.java" | 10 ++++++++++ .../ocp/SmsLogger.java" | 11 +++++++++++ 10 files changed, 95 insertions(+) create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/DateUtil.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/EmailLogger.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/LogOutput.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/Logger.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/MailUtil.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/PrintLogger.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogOutput.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogWithDateOutput.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SMSUtil.java" create mode 100644 "students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SmsLogger.java" diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/DateUtil.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/DateUtil.java" new file mode 100644 index 0000000000..b6cf28c096 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/DateUtil.java" @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/EmailLogger.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/EmailLogger.java" new file mode 100644 index 0000000000..7a51f98c23 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/EmailLogger.java" @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp; + +public class EmailLogger extends Logger{ + + public void log(String msg){ + MailUtil.send(msg); + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/LogOutput.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/LogOutput.java" new file mode 100644 index 0000000000..caf9986293 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/LogOutput.java" @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp; + +public abstract class LogOutput { + + + public abstract void logOutput(String msg,Logger logger); + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/Logger.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/Logger.java" new file mode 100644 index 0000000000..8913377e5a --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/Logger.java" @@ -0,0 +1,7 @@ +package com.coderising.ood.ocp; + +public abstract class Logger { + + public abstract void log(String msg); +} + diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/MailUtil.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/MailUtil.java" new file mode 100644 index 0000000000..ec54b839c5 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/MailUtil.java" @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/PrintLogger.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/PrintLogger.java" new file mode 100644 index 0000000000..6960fb9af3 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/PrintLogger.java" @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp; + +public class PrintLogger extends Logger{ + +public void log(String msg){ + System.out.println(msg); + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogOutput.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogOutput.java" new file mode 100644 index 0000000000..9603d16687 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogOutput.java" @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp; + +public class RawLogOutput extends LogOutput{ + + public void logOutput(String msg,Logger logger) { + logger.log(msg); + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogWithDateOutput.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogWithDateOutput.java" new file mode 100644 index 0000000000..5f414d992d --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/RawLogWithDateOutput.java" @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +public class RawLogWithDateOutput extends LogOutput{ + + @Override + public void logOutput(String msg,Logger logger) { + String txtDate = DateUtil.getCurrentDateAsString(); + String logMsg = txtDate + ": " + msg; + logger.log(logMsg); + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SMSUtil.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SMSUtil.java" new file mode 100644 index 0000000000..13cf802418 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SMSUtil.java" @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git "a/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SmsLogger.java" "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SmsLogger.java" new file mode 100644 index 0000000000..8a22e52e78 --- /dev/null +++ "b/students/706097141/\347\254\254\344\272\214\346\254\241\344\275\234\344\270\232/ocp/SmsLogger.java" @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class SmsLogger extends Logger{ + + + public void log(String msg){ + + SMSUtil.send(msg); + } + +} From 2235a2e8e886a715119a5b480521ea90d03fe67f Mon Sep 17 00:00:00 2001 From: thomas_young Date: Thu, 22 Jun 2017 08:11:38 +0800 Subject: [PATCH 34/73] =?UTF-8?q?=E7=AC=AC=E4=B8=80=E6=AC=A1=E4=BD=9C?= =?UTF-8?q?=E4=B8=9Av2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/coderising/ood/srp/EmailParam.java | 43 +++- .../com/coderising/ood/srp/MailService.java | 116 +++++++++++ .../java/com/coderising/ood/srp/MailUtil.java | 4 +- .../com/coderising/ood/srp/ProductInfo.java | 65 ++++++ .../com/coderising/ood/srp/PromotionMail.java | 186 +----------------- .../java/com/coderising/ood/srp/UserDao.java | 26 +++ 6 files changed, 254 insertions(+), 186 deletions(-) create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/MailService.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java b/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java index 934ff2139b..3a9fd4f2f0 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java @@ -1,8 +1,49 @@ package com.coderising.ood.srp; + /** * Created by thomas_young on 20/6/2017. */ public class EmailParam { - protected String smtpHost = null; + private String smtpHost = null; + private String altSmtpHost = null; + private static Configuration config = new Configuration(); + private String fromAddress = null; + + protected void setFromAddress() + { + fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + } + + private void loadEmailConfig() { + setFromAddress(); + setSMTPHost(); + setAltSMTPHost(); + } + + public EmailParam() { + loadEmailConfig(); + } + + public String getSmtpHost() { + return smtpHost; + } + + private void setSMTPHost() + { + smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + } + + public String getAltSmtpHost() { + return altSmtpHost; + } + + public String getFromAddress() { + return fromAddress; + } + + private void setAltSMTPHost() + { + altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + } } diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/MailService.java b/students/812350401/src/main/java/com/coderising/ood/srp/MailService.java new file mode 100644 index 0000000000..7b01d47575 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/MailService.java @@ -0,0 +1,116 @@ +package com.coderising.ood.srp; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.LinkedList; +import java.util.List; + +/** + * Created by thomas_young on 20/6/2017. + */ +public class MailService { + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + private static String fromAddress; + private static EmailParam emailParam; + + static { + emailParam = new EmailParam(); + fromAddress = emailParam.getFromAddress(); + } + + public void sendMails(boolean debug) throws Exception { + ProductInfo productInfo = new ProductInfo(); + UserDao userDao = new UserDao(); + List userInfos = userDao.loadMailingList(productInfo.getProductID()); + List mailInfos = convertToMails(userInfos, productInfo); + System.out.println("开始发送邮件"); + for (MailInfo mail: mailInfos) { + sendOneMail(mail, debug); + } + + } + + private void sendOneMail(MailInfo mail, boolean debug) { + try { + MailUtil.sendEmail( + mail.getToAddress(), + fromAddress, + mail.getSubject(), + mail.getMessage(), + emailParam.getSmtpHost(), debug); + } catch (Exception e) { + + try { + MailUtil.sendEmail(mail.getToAddress(), + fromAddress, + mail.getSubject(), + mail.getMessage(), + emailParam.getAltSmtpHost(), + debug); + } catch (Exception e2) + { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + } + } + + public static class MailInfo { + + public String getFromAddress() { + return fromAddress; + } + + public String getToAddress() { + return toAddress; + } + + public String getSubject() { + return subject; + } + + public String getMessage() { + return message; + } + + private String fromAddress = null; + private String toAddress = null; + private String subject = null; + private String message = null; + + + public MailInfo(String fromAddress, String toAddress, String subject, String message) { + this.fromAddress = fromAddress; + this.toAddress = toAddress; + this.subject = subject; + this.message = message; + } + } + + private List convertToMails(List userInfos, ProductInfo productInfo) throws IOException { + List mailInfos = new LinkedList<>(); + if (userInfos != null) { + Iterator iter = userInfos.iterator(); + while (iter.hasNext()) { + MailInfo mailInfo = configureEMail((HashMap) iter.next(), productInfo); + if (mailInfo != null) { + mailInfos.add(mailInfo); + } + } + } + return mailInfos; + } + + private MailInfo configureEMail(HashMap userInfo, ProductInfo productInfo) throws IOException + { + String toAddress = (String) userInfo.get(EMAIL_KEY); + if (toAddress.length() > 0) { + String name = (String) userInfo.get(NAME_KEY); + String subject = "您关注的产品降价了"; + String message = "尊敬的 "+name+", 您关注的产品 " + productInfo.getProductDesc() + " 降价了,欢迎购买!" ; + return new MailInfo(fromAddress, toAddress, subject, message); + } + return null; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java index 9f9e749af7..3e81821544 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -1,5 +1,8 @@ package com.coderising.ood.srp; + +import java.util.concurrent.atomic.AtomicInteger; + public class MailUtil { public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, @@ -11,7 +14,6 @@ public static void sendEmail(String toAddress, String fromAddress, String subjec buffer.append("Subject:").append(subject).append("\n"); buffer.append("Content:").append(message).append("\n"); System.out.println(buffer.toString()); - } diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java b/students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java new file mode 100644 index 0000000000..6d74acb3bf --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java @@ -0,0 +1,65 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; + +/** + * Created by thomas_young on 20/6/2017. + */ +public class ProductInfo { + private String productID = null; + private String productDesc = null; + + private static File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + + public ProductInfo() { + try { + readFileSetProperty(); + } catch (IOException e) { + e.printStackTrace(); + } + } + + /** + * 读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 + * @throws IOException + */ + private void readFileSetProperty() throws IOException + { + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(f)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + setProductID(data[0]); + setProductDesc(data[1]); + + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + public String getProductID() { + return productID; + } + + public void setProductID(String productID) { + this.productID = productID; + } + + public String getProductDesc() { + return productDesc; + } + + public void setProductDesc(String productDesc) { + this.productDesc = productDesc; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java index b359f3aa6f..bd635ea702 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -10,190 +10,8 @@ import java.util.List; public class PromotionMail { - - - protected String sendMailQuery = null; - - - protected String smtpHost = null; - protected String altSmtpHost = null; - protected String fromAddress = null; - protected String toAddress = null; - protected String subject = null; - protected String message = null; - - protected String productID = null; - protected String productDesc = null; - - private static Configuration config; - - - - private static final String NAME_KEY = "NAME"; - private static final String EMAIL_KEY = "EMAIL"; - - public static void main(String[] args) throws Exception { - - File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt"); - boolean emailDebug = false; - - PromotionMail pe = new PromotionMail(f, emailDebug); - - } - - - public PromotionMail(File file, boolean mailDebug) throws Exception { - - //读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 - readFile(file); - - - config = new Configuration(); - - setSMTPHost(); - setAltSMTPHost(); - - - setFromAddress(); - - - setLoadQuery(); - - sendEMails(mailDebug, loadMailingList()); - - - } - - - - - protected void setProductID(String productID) - { - this.productID = productID; - - } - - protected String getproductID() - { - return productID; - } - - protected void setLoadQuery() throws Exception { - - sendMailQuery = "Select name from subscriptions " - + "where product_id= '" + productID +"' " - + "and send_mail=1 "; - - - System.out.println("loadQuery set"); - } - - - protected void setSMTPHost() - { - smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); - } - - - protected void setAltSMTPHost() - { - altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); - - } - - - protected void setFromAddress() - { - fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); - } - - protected void setMessage(HashMap userInfo) throws IOException - { - - String name = (String) userInfo.get(NAME_KEY); - - subject = "您关注的产品降价了"; - message = "尊敬的 "+name+", 您关注的产品 " + productDesc + " 降价了,欢迎购买!" ; - - - - } - - - protected void readFile(File file) throws IOException // @02C - { - BufferedReader br = null; - try { - br = new BufferedReader(new FileReader(file)); - String temp = br.readLine(); - String[] data = temp.split(" "); - - setProductID(data[0]); - setProductDesc(data[1]); - - System.out.println("产品ID = " + productID + "\n"); - System.out.println("产品描述 = " + productDesc + "\n"); - - } catch (IOException e) { - throw new IOException(e.getMessage()); - } finally { - br.close(); - } - } - - private void setProductDesc(String desc) { - this.productDesc = desc; - } - - - protected void configureEMail(HashMap userInfo) throws IOException - { - toAddress = (String) userInfo.get(EMAIL_KEY); - if (toAddress.length() > 0) - setMessage(userInfo); - } - - protected List loadMailingList() throws Exception { - return DBUtil.query(this.sendMailQuery); - } - - - protected void sendEMails(boolean debug, List mailingList) throws IOException - { - - System.out.println("开始发送邮件"); - - - if (mailingList != null) { - Iterator iter = mailingList.iterator(); - while (iter.hasNext()) { - configureEMail((HashMap) iter.next()); - try - { - if (toAddress.length() > 0) - MailUtil.sendEmail(toAddress, fromAddress, subject, message, smtpHost, debug); - } - catch (Exception e) - { - - try { - MailUtil.sendEmail(toAddress, fromAddress, subject, message, altSmtpHost, debug); - - } catch (Exception e2) - { - System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); - } - } - } - - - } - - else { - System.out.println("没有邮件发送"); - - } - + MailService mailService = new MailService(); + mailService.sendMails(true); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java b/students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java new file mode 100644 index 0000000000..49a0ce4040 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp; + +import java.util.List; + +/** + * Created by thomas_young on 21/6/2017. + */ +public class UserDao { + private String sendMailQuery = null; + + private void setLoadQuery(String productID) throws Exception { + + sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + + System.out.println("loadQuery set"); + } + + public List loadMailingList(String productID) throws Exception { + setLoadQuery(productID); + return DBUtil.query(this.sendMailQuery); + } + +} From a84bcec61bae01daa8e33d85c8405733ef478cb4 Mon Sep 17 00:00:00 2001 From: thomas_young Date: Thu, 22 Jun 2017 08:12:52 +0800 Subject: [PATCH 35/73] =?UTF-8?q?Revert=20"=E7=AC=AC=E4=B8=80=E6=AC=A1?= =?UTF-8?q?=E4=BD=9C=E4=B8=9A=20init2"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 3f84999c2816fe5592a7f8964092f89d7903f38f. --- liuxin/ood/ood-assignment/pom.xml | 13 ------------- .../java/com/coderising/ood/srp/PromotionMail.java | 2 +- 2 files changed, 1 insertion(+), 14 deletions(-) diff --git a/liuxin/ood/ood-assignment/pom.xml b/liuxin/ood/ood-assignment/pom.xml index 9a28365d2a..cac49a5328 100644 --- a/liuxin/ood/ood-assignment/pom.xml +++ b/liuxin/ood/ood-assignment/pom.xml @@ -10,19 +10,6 @@ ood-assignment http://maven.apache.org - - - - org.apache.maven.plugins - maven-compiler-plugin - - 1.8 - 1.8 - - - - - UTF-8 diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java index 9d07330831..781587a846 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -35,7 +35,7 @@ public class PromotionMail { public static void main(String[] args) throws Exception { - File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + File f = new File("C:\\coderising\\workspace_ds\\ood-example\\src\\product_promotion.txt"); boolean emailDebug = false; PromotionMail pe = new PromotionMail(f, emailDebug); From fbd64c7a8f27cedbdbdba7a0b4be5b3eb5c29bf7 Mon Sep 17 00:00:00 2001 From: Harry Date: Thu, 22 Jun 2017 23:24:31 +0800 Subject: [PATCH 36/73] add ocp refactor MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 20170622 完成ocp重构 --- .../src/com/coderising/ood/ocp/Formatter.java | 5 +++++ .../coderising/ood/ocp/FormatterFactory.java | 14 +++++++++++++ .../com/coderising/ood/ocp/HtmlFormatter.java | 11 ++++++++++ .../com/coderising/ood/ocp/LogTestDrive.java | 20 +++++++++++++++++++ .../src/com/coderising/ood/ocp/Logger.java | 15 ++++++++++++++ .../com/coderising/ood/ocp/MailSenderImp.java | 12 +++++++++++ .../coderising/ood/ocp/PrintSenderImp.java | 11 ++++++++++ .../com/coderising/ood/ocp/RawFormatter.java | 10 ++++++++++ .../com/coderising/ood/ocp/SMSSenderImp.java | 11 ++++++++++ .../src/com/coderising/ood/ocp/Sender.java | 5 +++++ .../com/coderising/ood/ocp/SenderFactory.java | 17 ++++++++++++++++ 11 files changed, 131 insertions(+) create mode 100644 students/727171008/src/com/coderising/ood/ocp/Formatter.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/FormatterFactory.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/HtmlFormatter.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/LogTestDrive.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/Logger.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/MailSenderImp.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/PrintSenderImp.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/RawFormatter.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/SMSSenderImp.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/Sender.java create mode 100644 students/727171008/src/com/coderising/ood/ocp/SenderFactory.java diff --git a/students/727171008/src/com/coderising/ood/ocp/Formatter.java b/students/727171008/src/com/coderising/ood/ocp/Formatter.java new file mode 100644 index 0000000000..07391dacab --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/Formatter.java @@ -0,0 +1,5 @@ +package com.coderising.ood.ocp; + +public interface Formatter { + String formate(String msg); +} diff --git a/students/727171008/src/com/coderising/ood/ocp/FormatterFactory.java b/students/727171008/src/com/coderising/ood/ocp/FormatterFactory.java new file mode 100644 index 0000000000..4d6cc9603e --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/FormatterFactory.java @@ -0,0 +1,14 @@ +package com.coderising.ood.ocp; + +public class FormatterFactory { + public Formatter createFormatter(int type) { + Formatter formatter = null; + if (type == 1) { + formatter = new RawFormatter(); + } + if (type == 2) { + formatter = new HtmlFormatter(); + } + return formatter; + } +} diff --git a/students/727171008/src/com/coderising/ood/ocp/HtmlFormatter.java b/students/727171008/src/com/coderising/ood/ocp/HtmlFormatter.java new file mode 100644 index 0000000000..6d3d76f58e --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/HtmlFormatter.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class HtmlFormatter implements Formatter { + + @Override + public String formate(String msg) { + + return null; + } + +} diff --git a/students/727171008/src/com/coderising/ood/ocp/LogTestDrive.java b/students/727171008/src/com/coderising/ood/ocp/LogTestDrive.java new file mode 100644 index 0000000000..d96987e6d4 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/LogTestDrive.java @@ -0,0 +1,20 @@ +package com.coderising.ood.ocp; + +public class LogTestDrive { + + public static void main(String[] args) { + FormatterFactory ff = new FormatterFactory(); + SenderFactory sf = new SenderFactory(); + + Formatter formatter = ff.createFormatter(1); + Sender sender = sf.createSender(1); + + Logger logger = new Logger(formatter, sender); + String msg = "此处应该从文本读取?或者html读取?"; + logger.log(msg); + + System.out.println("end"); + + } + +} diff --git a/students/727171008/src/com/coderising/ood/ocp/Logger.java b/students/727171008/src/com/coderising/ood/ocp/Logger.java new file mode 100644 index 0000000000..a02cf8658c --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/Logger.java @@ -0,0 +1,15 @@ +package com.coderising.ood.ocp; + +public class Logger { + private Formatter formatter; + private Sender sender; + + public Logger(Formatter formatter, Sender sender) { + this.formatter = formatter; + this.sender = sender; + } + + public void log(String msg) { + sender.send(formatter.formate(msg)); + } +} diff --git a/students/727171008/src/com/coderising/ood/ocp/MailSenderImp.java b/students/727171008/src/com/coderising/ood/ocp/MailSenderImp.java new file mode 100644 index 0000000000..ab79fe070b --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/MailSenderImp.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp; + +public class MailSenderImp implements Sender { + + @Override + public String send(String msg) { + + return "Raw data "; + + } + +} diff --git a/students/727171008/src/com/coderising/ood/ocp/PrintSenderImp.java b/students/727171008/src/com/coderising/ood/ocp/PrintSenderImp.java new file mode 100644 index 0000000000..22a4c8db2b --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/PrintSenderImp.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class PrintSenderImp implements Sender { + + @Override + public String send(String msg) { + + return "print "; + } + +} diff --git a/students/727171008/src/com/coderising/ood/ocp/RawFormatter.java b/students/727171008/src/com/coderising/ood/ocp/RawFormatter.java new file mode 100644 index 0000000000..762917e981 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/RawFormatter.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class RawFormatter implements Formatter { + + @Override + public String formate(String msg) { + return null; + } + +} diff --git a/students/727171008/src/com/coderising/ood/ocp/SMSSenderImp.java b/students/727171008/src/com/coderising/ood/ocp/SMSSenderImp.java new file mode 100644 index 0000000000..6aaa16f23e --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/SMSSenderImp.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp; + +public class SMSSenderImp implements Sender { + + @Override + public String send(String msg) { + + return "SMS data "; + } + +} diff --git a/students/727171008/src/com/coderising/ood/ocp/Sender.java b/students/727171008/src/com/coderising/ood/ocp/Sender.java new file mode 100644 index 0000000000..4c54985454 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/Sender.java @@ -0,0 +1,5 @@ +package com.coderising.ood.ocp; + +public interface Sender { + String send(String msg); +} diff --git a/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java b/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java new file mode 100644 index 0000000000..7708250e10 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java @@ -0,0 +1,17 @@ +package com.coderising.ood.ocp; + +public class SenderFactory { + public Sender createSender(int type) { + Sender sender = null; + if (type == 1) { + sender = new MailSenderImp(); + } + if (type == 2) { + sender = new SMSSenderImp(); + } + if (type == 3) { + sender = new PrintSenderImp(); + } + return sender; + } +} From 3f6b591142ccc7a71ecc5b08fdc65f3e72ee334b Mon Sep 17 00:00:00 2001 From: Harry Date: Fri, 23 Jun 2017 10:04:15 +0800 Subject: [PATCH 37/73] update SenderFactory --- .../727171008/src/com/coderising/ood/ocp/SenderFactory.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java b/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java index 7708250e10..96663989cf 100644 --- a/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java +++ b/students/727171008/src/com/coderising/ood/ocp/SenderFactory.java @@ -3,7 +3,7 @@ public class SenderFactory { public Sender createSender(int type) { Sender sender = null; - if (type == 1) { + if(type == 1) { sender = new MailSenderImp(); } if (type == 2) { From 3e26f6dca3e333b8197935914f9de805aba1f9c1 Mon Sep 17 00:00:00 2001 From: yyglider Date: Fri, 23 Jun 2017 10:50:23 +0800 Subject: [PATCH 38/73] update update --- .../src/main/java/work02/ocp/DateUtil.java | 10 +++++++ .../src/main/java/work02/ocp/Formatter.java | 7 +++++ .../src/main/java/work02/ocp/Logger.java | 29 +++++++++++++++++++ .../src/main/java/work02/ocp/MailSender.java | 7 +++++ .../src/main/java/work02/ocp/MailUtil.java | 10 +++++++ .../main/java/work02/ocp/PrinterSender.java | 8 +++++ .../java/work02/ocp/RawDateFormatter.java | 9 ++++++ .../main/java/work02/ocp/RawFormatter.java | 8 +++++ .../src/main/java/work02/ocp/SMSSender.java | 8 +++++ .../src/main/java/work02/ocp/SMSUtil.java | 10 +++++++ .../src/main/java/work02/ocp/Sender.java | 8 +++++ 11 files changed, 114 insertions(+) create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/DateUtil.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/Formatter.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/Logger.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/MailSender.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/MailUtil.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/PrinterSender.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/RawDateFormatter.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/RawFormatter.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/SMSSender.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/SMSUtil.java create mode 100644 students/769232552/season_two/src/main/java/work02/ocp/Sender.java diff --git a/students/769232552/season_two/src/main/java/work02/ocp/DateUtil.java b/students/769232552/season_two/src/main/java/work02/ocp/DateUtil.java new file mode 100644 index 0000000000..ab721d91aa --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package work02.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/Formatter.java b/students/769232552/season_two/src/main/java/work02/ocp/Formatter.java new file mode 100644 index 0000000000..ce705806b5 --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/Formatter.java @@ -0,0 +1,7 @@ +package work02.ocp; + +public interface Formatter { + + String formatMsg(String msg); + +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/Logger.java b/students/769232552/season_two/src/main/java/work02/ocp/Logger.java new file mode 100644 index 0000000000..0f0ecd7ae0 --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/Logger.java @@ -0,0 +1,29 @@ +package work02.ocp; + +public class Logger { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + int type = 0; + int method = 0; + + public Logger(int logType, int logMethod){ + this.type = logType; + this.method = logMethod; + } + + Sender sender; + Formatter formatter; + + public void log(String msg){ + + String logMsg = formatter.formatMsg(msg); + sender.send(logMsg); + + } +} + diff --git a/students/769232552/season_two/src/main/java/work02/ocp/MailSender.java b/students/769232552/season_two/src/main/java/work02/ocp/MailSender.java new file mode 100644 index 0000000000..1d13f449eb --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/MailSender.java @@ -0,0 +1,7 @@ +package work02.ocp; + +public class MailSender implements Sender { + public void send(String msg) { + MailUtil.send(msg); + } +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/MailUtil.java b/students/769232552/season_two/src/main/java/work02/ocp/MailUtil.java new file mode 100644 index 0000000000..62e26c25be --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package work02.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/PrinterSender.java b/students/769232552/season_two/src/main/java/work02/ocp/PrinterSender.java new file mode 100644 index 0000000000..7511b9652f --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/PrinterSender.java @@ -0,0 +1,8 @@ +package work02.ocp; + + +public class PrinterSender implements Sender { + public void send(String msg) { + System.out.println(msg); + } +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/RawDateFormatter.java b/students/769232552/season_two/src/main/java/work02/ocp/RawDateFormatter.java new file mode 100644 index 0000000000..16db075e51 --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/RawDateFormatter.java @@ -0,0 +1,9 @@ +package work02.ocp; + +public class RawDateFormatter implements Formatter { + + public String formatMsg(String msg) { + String txtDate = DateUtil.getCurrentDateAsString(); + return txtDate + ": " + msg; + } +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/RawFormatter.java b/students/769232552/season_two/src/main/java/work02/ocp/RawFormatter.java new file mode 100644 index 0000000000..9ff801b9de --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/RawFormatter.java @@ -0,0 +1,8 @@ +package work02.ocp; + +public class RawFormatter implements Formatter { + + public String formatMsg(String msg) { + return msg; + } +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/SMSSender.java b/students/769232552/season_two/src/main/java/work02/ocp/SMSSender.java new file mode 100644 index 0000000000..9fa42a752f --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/SMSSender.java @@ -0,0 +1,8 @@ +package work02.ocp; + + +public class SMSSender implements Sender{ + public void send(String msg) { + SMSUtil.send(msg); + } +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/SMSUtil.java b/students/769232552/season_two/src/main/java/work02/ocp/SMSUtil.java new file mode 100644 index 0000000000..435e07300a --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package work02.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/769232552/season_two/src/main/java/work02/ocp/Sender.java b/students/769232552/season_two/src/main/java/work02/ocp/Sender.java new file mode 100644 index 0000000000..746ffdffb5 --- /dev/null +++ b/students/769232552/season_two/src/main/java/work02/ocp/Sender.java @@ -0,0 +1,8 @@ +package work02.ocp; + + +public interface Sender { + + void send(String msg); + +} \ No newline at end of file From 697cd574c848bac3afe3dfa006e1fbe430e48f2b Mon Sep 17 00:00:00 2001 From: Harry Date: Fri, 23 Jun 2017 11:05:25 +0800 Subject: [PATCH 39/73] add srp MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 20170623 重构srp:促销邮件发送。 --- .../com/coderising/ood/srp/Configuration.java | 26 ++++++++++++++ .../coderising/ood/srp/ConfigurationKeys.java | 9 +++++ .../src/com/coderising/ood/srp/Mail.java | 34 ++++++++++++++++++ .../com/coderising/ood/srp/MailSender.java | 35 +++++++++++++++++++ .../src/com/coderising/ood/srp/Product.java | 10 ++++++ .../coderising/ood/srp/ProductService.java | 16 +++++++++ .../com/coderising/ood/srp/PromotionJob.java | 24 +++++++++++++ .../src/com/coderising/ood/srp/User.java | 26 ++++++++++++++ .../com/coderising/ood/srp/UserService.java | 11 ++++++ .../coderising/ood/srp/product_promotion.txt | 4 +++ 10 files changed, 195 insertions(+) create mode 100644 students/727171008/src/com/coderising/ood/srp/Configuration.java create mode 100644 students/727171008/src/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/727171008/src/com/coderising/ood/srp/Mail.java create mode 100644 students/727171008/src/com/coderising/ood/srp/MailSender.java create mode 100644 students/727171008/src/com/coderising/ood/srp/Product.java create mode 100644 students/727171008/src/com/coderising/ood/srp/ProductService.java create mode 100644 students/727171008/src/com/coderising/ood/srp/PromotionJob.java create mode 100644 students/727171008/src/com/coderising/ood/srp/User.java create mode 100644 students/727171008/src/com/coderising/ood/srp/UserService.java create mode 100644 students/727171008/src/com/coderising/ood/srp/product_promotion.txt diff --git a/students/727171008/src/com/coderising/ood/srp/Configuration.java b/students/727171008/src/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..5a52efee25 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp; + +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static { + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/727171008/src/com/coderising/ood/srp/ConfigurationKeys.java b/students/727171008/src/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..945db9004a --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp.good1; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/727171008/src/com/coderising/ood/srp/Mail.java b/students/727171008/src/com/coderising/ood/srp/Mail.java new file mode 100644 index 0000000000..8ecea4a35e --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/Mail.java @@ -0,0 +1,34 @@ +package com.coderising.ood.srp; + +import java.util.List; + +public class Mail { + private User user; + + public Mail(User user) { + this.user = user; + } + + public String getAddress() { + return user.getEMailAddress(); + } + + public String getSubjcet() { + return "您关注的商品降价了!"; + } + + public String getBody() { + return "尊敬的用户: " + user.getName() + ", 您关注的商品: " + this.buildProductDescList(); + } + + private String buildProductDescList() { + List products = user.getSubscribedProducts(); + + return null; + } + + public String getSubject() { + + return null; + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/MailSender.java b/students/727171008/src/com/coderising/ood/srp/MailSender.java new file mode 100644 index 0000000000..48c29ac877 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/MailSender.java @@ -0,0 +1,35 @@ +package com.coderising.ood.srp; + +public class MailSender { + + private String fromAddress; + private String smtpHost; + private String altSmtpHost; + + public MailSender(Configuration config) { + this.fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + this.smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + this.altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + } + + public void sendMail(Mail mail) { + try { + sendEmail(mail, this.smtpHost); + } catch (Exception e) { + try { + sendEmail(mail, this.altSmtpHost); + } catch (Exception ex) { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + ex.getMessage()); + } + + } + } + + private void sendEmail(Mail mail, String smtpHost) { + + String toAddress = mail.getAddress(); + String subject = mail.getSubject(); + String msg = mail.getBody(); + // 发送邮件 + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/Product.java b/students/727171008/src/com/coderising/ood/srp/Product.java new file mode 100644 index 0000000000..d04cdb97f4 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/Product.java @@ -0,0 +1,10 @@ +package com.coderising.ood.srp; + +public class Product { + private String id; + private String desc; + + public String getDesc() { + return desc; + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/ProductService.java b/students/727171008/src/com/coderising/ood/srp/ProductService.java new file mode 100644 index 0000000000..5eea405243 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/ProductService.java @@ -0,0 +1,16 @@ +package com.coderising.ood.srp; + +import java.io.File; + +public class ProductService { + public Product getPromotionProduct() { + File f = new File("F:\\coding2017\\com\\codering\\ood\\src\\product_promotion.txt"); + Product product = readFile(f); + return product; + } + + private Product readFile(File file) { + + return null; + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/PromotionJob.java b/students/727171008/src/com/coderising/ood/srp/PromotionJob.java new file mode 100644 index 0000000000..616335aa05 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/PromotionJob.java @@ -0,0 +1,24 @@ +package com.coderising.ood.srp; + +import java.util.List; + +public class PromotionJob { + + private ProductService productService = null; // 获取production service + private UserService userService = null;// 获取UserService + + public void run() { + + Configuration cfg = new Configuration(); + + Product p = productService.getPromotionProduct(); + + List users = userService.getUsers(p); //一次只读取了一件商品 + + MailSender mailSender = new MailSender(cfg); + + for (User user : users) { + mailSender.sendMail(new Mail(user)); + } + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/User.java b/students/727171008/src/com/coderising/ood/srp/User.java new file mode 100644 index 0000000000..a79bc5c97a --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/User.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp; + +import java.util.List; + +public class User { + + private String name; + private String emailAddress; + + private List subscribedProducts; + + public String getName() { + + return name; + } + + public String getEMailAddress() { + + return emailAddress; + } + + public List getSubscribedProducts() { + + return this.subscribedProducts; + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/UserService.java b/students/727171008/src/com/coderising/ood/srp/UserService.java new file mode 100644 index 0000000000..9bc682a229 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/UserService.java @@ -0,0 +1,11 @@ +package com.coderising.ood.srp; + +import java.util.List; + +public class UserService { + + public List getUsers(Product product) { + // 调用DAO相关的类从数据库中读取订阅产品的用户列表 + return null; + } +} diff --git a/students/727171008/src/com/coderising/ood/srp/product_promotion.txt b/students/727171008/src/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/727171008/src/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file From 38a98482b32e4f2abcabdb9f1cb57d3edb3bf451 Mon Sep 17 00:00:00 2001 From: thomas_young Date: Sat, 24 Jun 2017 16:26:43 +0800 Subject: [PATCH 40/73] =?UTF-8?q?=E5=8F=91=E9=82=AE=E4=BB=B6=EF=BC=8C?= =?UTF-8?q?=E9=87=8D=E6=9E=842?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/com/coderising/ood/srp/MailUtil.java | 2 - .../ood/srp/goodSrp/Configuration.java | 26 +++++++++++++ .../ood/srp/goodSrp/ConfigurationKeys.java | 9 +++++ .../coderising/ood/srp/goodSrp/DBUtil.java | 25 ++++++++++++ .../com/coderising/ood/srp/goodSrp/Mail.java | 29 ++++++++++++++ .../ood/srp/goodSrp/MailSender.java | 35 +++++++++++++++++ .../coderising/ood/srp/goodSrp/MailUtil.java | 17 ++++++++ .../coderising/ood/srp/goodSrp/Product.java | 34 ++++++++++++++++ .../ood/srp/goodSrp/ProductService.java | 38 ++++++++++++++++++ .../ood/srp/goodSrp/PromotionJob.java | 29 ++++++++++++++ .../com/coderising/ood/srp/goodSrp/User.java | 39 +++++++++++++++++++ .../ood/srp/goodSrp/UserService.java | 26 +++++++++++++ .../goodSrp/template/MailBodyTemplate.java | 5 +++ .../template/TextMailBodyTemplate.java | 25 ++++++++++++ 14 files changed, 337 insertions(+), 2 deletions(-) create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java index 3e81821544..aa931433a9 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -1,8 +1,6 @@ package com.coderising.ood.srp; -import java.util.concurrent.atomic.AtomicInteger; - public class MailUtil { public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java new file mode 100644 index 0000000000..a9a4d3f207 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp.goodSrp; + +import com.coderising.ood.srp.ConfigurationKeys; + +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(com.coderising.ood.srp.ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(com.coderising.ood.srp.ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java new file mode 100644 index 0000000000..c39f1fcff9 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp.goodSrp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java new file mode 100644 index 0000000000..53631cfa7f --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp.goodSrp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com" + i); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java new file mode 100644 index 0000000000..cbac40d547 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java @@ -0,0 +1,29 @@ +package com.coderising.ood.srp.goodSrp; + +import java.util.List; +import java.util.stream.Collectors; + +public class Mail { + + private User user; + + public Mail(User u){ + this.user = u; + } + public String getAddress(){ + return user.getEMailAddress(); + } + public String getSubject(){ + return "您关注的产品降价了"; + } + public String getBody(){ + + return "尊敬的 "+user.getName()+", 您关注的产品 " + this.buildProductDescList() + " 降价了,欢迎购买!" ; + } + private String buildProductDescList() { + List products = user.getSubscribedProducts(); + //.... 实现略... + return products.stream().map(Object::toString) + .collect(Collectors.joining(", ")); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java new file mode 100644 index 0000000000..8ef8769291 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java @@ -0,0 +1,35 @@ +package com.coderising.ood.srp.goodSrp; + +/** + * Created by thomas_young on 24/6/2017. + */ +public class MailSender { + private String fromAddress ; + private String smtpHost; + private String altSmtpHost; + + public MailSender(Configuration config){ + this.fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + this.smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + this.altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + } + + public void sendMail(Mail mail){ + try{ + sendEmail(mail, this.smtpHost); + }catch(Exception e){ + try{ + sendEmail(mail, this.altSmtpHost); + }catch (Exception ex){ + System.out.println("通过备用 SMTP服务器发送邮件失败: " + ex.getMessage()); + } + + } + } + + private void sendEmail(Mail mail, String smtpHost){ + //发送邮件 + System.out.println("开始发送邮件"); + MailUtil.sendEmail(mail, smtpHost, fromAddress); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java new file mode 100644 index 0000000000..a1fb0ceb73 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java @@ -0,0 +1,17 @@ +package com.coderising.ood.srp.goodSrp; + + +import com.coderising.ood.srp.goodSrp.template.MailBodyTemplate; +import com.coderising.ood.srp.goodSrp.template.TextMailBodyTemplate; + +public class MailUtil { + + public static void sendEmail(Mail mail, String smtpHost, String fromAddress) { + //假装发了一封邮件 + System.out.println("使用smtpHost为"+smtpHost); + MailBodyTemplate template = new TextMailBodyTemplate(mail, fromAddress); + System.out.println(template.render()); + } + + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java new file mode 100644 index 0000000000..dba13425c1 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java @@ -0,0 +1,34 @@ +package com.coderising.ood.srp.goodSrp; + + + +public class Product { + + private String id; + private String desc; + public String getDescription(){ + return desc; + } + + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getDesc() { + return desc; + } + + public void setDesc(String desc) { + this.desc = desc; + } + + @Override + public String toString() { + return desc; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java new file mode 100644 index 0000000000..a787d00eb3 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java @@ -0,0 +1,38 @@ +package com.coderising.ood.srp.goodSrp; + + +import java.io.*; +import java.util.LinkedList; +import java.util.List; + +public class ProductService { + private static File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + public List getPromotionProducts() { + //从文本文件中读取文件列表 + String line; + List products = new LinkedList<>(); + try (BufferedReader br = new BufferedReader(new FileReader(f))) { + while ((line = br.readLine()) != null) { + Product p =parseGenProduct(line); + products.add(p); + } + } catch (IOException e) { + e.printStackTrace(); + } + return products; + } + + private Product parseGenProduct(String line) { + String[] data = line.split(" "); + String productID = data[0]; + String productDesc = data[1]; + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + Product p = new Product(); + p.setDesc(productDesc); + p.setId(productID); + return p; + } + + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java new file mode 100644 index 0000000000..59db8cdada --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java @@ -0,0 +1,29 @@ +package com.coderising.ood.srp.goodSrp; + +import java.util.List; + +public class PromotionJob { + + private ProductService productService = new ProductService() ; //获取production service + private UserService userService = new UserService() ;// 获取UserService + + public void run(){ + + Configuration cfg = new Configuration(); + + List ps = productService.getPromotionProducts(); + + List users = userService.getUsers(ps); + + + MailSender mailSender = new MailSender(cfg); + + for(User user : users){ + mailSender.sendMail(new Mail(user)); + } + } + + public static void main(String[] args) { + new PromotionJob().run(); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java new file mode 100644 index 0000000000..295345ae38 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java @@ -0,0 +1,39 @@ +package com.coderising.ood.srp.goodSrp; + +import java.util.List; + +/** + * Created by thomas_young on 24/6/2017. + */ +public class User { + private String name; + private String emailAddress; + + private List subscribedProducts; + + public String getName(){ + return name; + } + public String getEMailAddress() { + return emailAddress; + } + public List getSubscribedProducts(){ + return this.subscribedProducts; + } + + public void setName(String name) { + this.name = name; + } + + public String getEmailAddress() { + return emailAddress; + } + + public void setEmailAddress(String emailAddress) { + this.emailAddress = emailAddress; + } + + public void setSubscribedProducts(List subscribedProducts) { + this.subscribedProducts = subscribedProducts; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java new file mode 100644 index 0000000000..635f9fe140 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java @@ -0,0 +1,26 @@ +package com.coderising.ood.srp.goodSrp; + +import java.util.LinkedList; +import java.util.List; +import java.util.Map; + +/** + * Created by thomas_young on 24/6/2017. + */ +public class UserService { + + public List getUsers(List ps) { + List users = new LinkedList<>(); + String sql = "Select name from subscriptions where send_mail=1"; + System.out.println("loadQuery set"); + List userInfoList = DBUtil.query(sql); + for (Object userInfo: userInfoList) { + User user = new User(); + user.setName(((Map)userInfo).get("NAME")); + user.setEmailAddress(((Map)userInfo).get("EMAIL")); + user.setSubscribedProducts(ps); + users.add(user); + } + return users; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java new file mode 100644 index 0000000000..1852b6155a --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java @@ -0,0 +1,5 @@ +package com.coderising.ood.srp.goodSrp.template; + +public interface MailBodyTemplate { + public String render(); +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java new file mode 100644 index 0000000000..b7906c6bf2 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp.goodSrp.template; + +import com.coderising.ood.srp.goodSrp.Mail; + + +public class TextMailBodyTemplate implements MailBodyTemplate { + private Mail mail; + String fromAdress; + public TextMailBodyTemplate(Mail mail, String fromAdress){ + this.mail = mail; + this.fromAdress = fromAdress; + } + + @Override + public String render() { + //使用某种模板技术实现Render + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAdress).append("\n"); + buffer.append("To:").append(mail.getAddress()).append("\n"); + buffer.append("Subject:").append(mail.getSubject()).append("\n"); + buffer.append("Content:").append(mail.getBody()).append("\n"); + return buffer.toString(); + } + +} From 636f71c2fb35ae819e80546a6c2588709f369fb0 Mon Sep 17 00:00:00 2001 From: thomas_young Date: Sat, 24 Jun 2017 19:12:31 +0800 Subject: [PATCH 41/73] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E5=91=A8=E4=BD=9C?= =?UTF-8?q?=E4=B8=9A=EF=BC=9A=E6=89=93=E5=8D=B0=E4=B8=8D=E5=90=8C=E7=9A=84?= =?UTF-8?q?=E6=97=A5=E5=BF=97?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/com/coderising/ood/ocp/MailUtil.java | 2 +- .../java/com/coderising/ood/ocp/SMSUtil.java | 2 +- .../com/coderising/ood/ocp/myocp/DateMsg.java | 14 +++++ .../coderising/ood/ocp/myocp/DateUtil.java | 17 ++++++ .../coderising/ood/ocp/myocp/EmailMethod.java | 12 +++++ .../coderising/ood/ocp/myocp/LogDrive.java | 18 +++++++ .../coderising/ood/ocp/myocp/LogFactory.java | 52 +++++++++++++++++++ .../com/coderising/ood/ocp/myocp/Logger.java | 16 ++++++ .../coderising/ood/ocp/myocp/MailUtil.java | 10 ++++ .../com/coderising/ood/ocp/myocp/Method.java | 8 +++ .../com/coderising/ood/ocp/myocp/Msg.java | 9 ++++ .../coderising/ood/ocp/myocp/PrintMethod.java | 11 ++++ .../com/coderising/ood/ocp/myocp/RawMsg.java | 12 +++++ .../com/coderising/ood/ocp/myocp/SMSUtil.java | 10 ++++ .../coderising/ood/ocp/myocp/SmsMethod.java | 12 +++++ 15 files changed, 203 insertions(+), 2 deletions(-) create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java index 59d77649a2..88cd252cf4 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java @@ -4,7 +4,7 @@ public class MailUtil { public static void send(String logMsg) { // TODO Auto-generated method stub - + System.out.println("email "+logMsg); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java index fab4cd01b7..8e955ab085 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java @@ -4,7 +4,7 @@ public class SMSUtil { public static void send(String logMsg) { // TODO Auto-generated method stub - + System.out.println("sms "+logMsg); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java new file mode 100644 index 0000000000..7484827d5f --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java @@ -0,0 +1,14 @@ +package com.coderising.ood.ocp.myocp; + + +/** + * Created by thomas_young on 24/6/2017. + */ +public class DateMsg implements Msg { + + @Override + public String msg(String msg) { + String txtDate = DateUtil.getCurrentDateAsString(); + return txtDate + ": " + msg; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java new file mode 100644 index 0000000000..d207c1d3c0 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java @@ -0,0 +1,17 @@ +package com.coderising.ood.ocp.myocp; + +import java.text.SimpleDateFormat; +import java.util.Date; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return new SimpleDateFormat("dd-MM-yyyy").format(new Date()); + } + + public static void main(String[] args) { + System.out.println(DateUtil.getCurrentDateAsString()); + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java new file mode 100644 index 0000000000..fd73f99924 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp.myocp; + + +/** + * Created by thomas_young on 24/6/2017. + */ +public class EmailMethod implements Method { + @Override + public void action(String msg) { + MailUtil.send(msg); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java new file mode 100644 index 0000000000..f0f8f3cf1e --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java @@ -0,0 +1,18 @@ +package com.coderising.ood.ocp.myocp; + +/** + * Created by thomas_young on 24/6/2017. + */ +public class LogDrive { + + public static void main(String[] args) { + LogFactory logFactory = new LogFactory(); + Logger logger; + for (int i = 1; i<=2; i++) { + for (int j = 1; j<=3; j++ ) { + logger = logFactory.createLogger(i, j); + logger.log("haha"); + } + } + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java new file mode 100644 index 0000000000..f9fa56ef35 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java @@ -0,0 +1,52 @@ +package com.coderising.ood.ocp.myocp; + + +/** + * Created by thomas_young on 24/6/2017. + */ +public class LogFactory { + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + public Logger createLogger(int logType, int logMethod) { + Msg msg = genMsg(logType); + Method method = genMethod(logMethod); + return new Logger(msg, method); + } + + private Method genMethod(int logMethod) { + Method method; + switch (logMethod) { + case EMAIL_LOG: + method = new EmailMethod(); + break; + case SMS_LOG: + method = new SmsMethod(); + break; + case PRINT_LOG: + method = new PrintMethod(); + break; + default: + throw new IllegalArgumentException("Invalid logMethod " + logMethod); + } + return method; + } + + private Msg genMsg(int logType) { + Msg msg; + switch (logType) { + case RAW_LOG: + msg = new RawMsg(); + break; + case RAW_LOG_WITH_DATE: + msg = new DateMsg(); + break; + default: + throw new IllegalArgumentException("Invalid logType " + logType); + } + return msg; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java new file mode 100644 index 0000000000..9889d0a9b0 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java @@ -0,0 +1,16 @@ +package com.coderising.ood.ocp.myocp; + +public class Logger { + + Method method; + Msg msg; + + public Logger(Msg aMsg, Method aMethod){ + msg= aMsg; + method = aMethod; + } + public void log(String message){ + method.action(msg.msg(message)); + } +} + diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java new file mode 100644 index 0000000000..6bd1a1f27a --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.myocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + System.out.println("email "+logMsg); + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java new file mode 100644 index 0000000000..49ff988579 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java @@ -0,0 +1,8 @@ +package com.coderising.ood.ocp.myocp; + +/** + * Created by thomas_young on 24/6/2017. + */ +public interface Method { + public void action(String msg); +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java new file mode 100644 index 0000000000..f479dbecff --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java @@ -0,0 +1,9 @@ +package com.coderising.ood.ocp.myocp; + +/** + * Created by thomas_young on 24/6/2017. + */ +public interface Msg { + public String msg(String msg); + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java new file mode 100644 index 0000000000..a88a229bb3 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java @@ -0,0 +1,11 @@ +package com.coderising.ood.ocp.myocp; + +/** + * Created by thomas_young on 24/6/2017. + */ +public class PrintMethod implements Method { + @Override + public void action(String msg) { + System.out.println(msg); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java new file mode 100644 index 0000000000..363746b9e9 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp.myocp; + +/** + * Created by thomas_young on 24/6/2017. + */ +public class RawMsg implements Msg { + + @Override + public String msg(String msg) { + return msg; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java new file mode 100644 index 0000000000..214f583c4c --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp.myocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + System.out.println("sms "+logMsg); + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java new file mode 100644 index 0000000000..63cce66a2e --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java @@ -0,0 +1,12 @@ +package com.coderising.ood.ocp.myocp; + + +/** + * Created by thomas_young on 24/6/2017. + */ +public class SmsMethod implements Method { + @Override + public void action(String msg) { + SMSUtil.send(msg); + } +} From 18a6b2d316d60391338ab49c6ddfafd5640dfeed Mon Sep 17 00:00:00 2001 From: thomas_young Date: Sat, 24 Jun 2017 19:39:11 +0800 Subject: [PATCH 42/73] =?UTF-8?q?=E6=89=93=E6=97=A5=E5=BF=97=EF=BC=9A?= =?UTF-8?q?=E9=87=8D=E6=9E=84=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../{DateMsg.java => DateFormatter.java} | 4 +- .../{EmailMethod.java => EmailSender.java} | 4 +- .../ocp/myocp/{Method.java => Formatter.java} | 4 +- .../ood/ocp/myocp/FormatterFactory.java | 21 ++++++++ .../coderising/ood/ocp/myocp/LogFactory.java | 50 +++---------------- .../com/coderising/ood/ocp/myocp/Logger.java | 12 ++--- .../coderising/ood/ocp/myocp/MailUtil.java | 2 +- .../{PrintMethod.java => PrintSender.java} | 4 +- .../myocp/{RawMsg.java => RawFormatter.java} | 4 +- .../com/coderising/ood/ocp/myocp/SMSUtil.java | 2 +- .../ood/ocp/myocp/{Msg.java => Sender.java} | 5 +- .../ood/ocp/myocp/SenderFactory.java | 25 ++++++++++ .../myocp/{SmsMethod.java => SmsSender.java} | 4 +- 13 files changed, 75 insertions(+), 66 deletions(-) rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{DateMsg.java => DateFormatter.java} (70%) rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{EmailMethod.java => EmailSender.java} (62%) rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{Method.java => Formatter.java} (59%) create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{PrintMethod.java => PrintSender.java} (63%) rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{RawMsg.java => RawFormatter.java} (59%) rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{Msg.java => Sender.java} (60%) create mode 100644 students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java rename students/812350401/src/main/java/com/coderising/ood/ocp/myocp/{SmsMethod.java => SmsSender.java} (63%) diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateFormatter.java similarity index 70% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateFormatter.java index 7484827d5f..b9c3f7b026 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateMsg.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateFormatter.java @@ -4,10 +4,10 @@ /** * Created by thomas_young on 24/6/2017. */ -public class DateMsg implements Msg { +public class DateFormatter implements Formatter { @Override - public String msg(String msg) { + public String format(String msg) { String txtDate = DateUtil.getCurrentDateAsString(); return txtDate + ": " + msg; } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailSender.java similarity index 62% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailSender.java index fd73f99924..bc91dc2d58 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailMethod.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailSender.java @@ -4,9 +4,9 @@ /** * Created by thomas_young on 24/6/2017. */ -public class EmailMethod implements Method { +public class EmailSender implements Sender { @Override - public void action(String msg) { + public void send(String msg) { MailUtil.send(msg); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Formatter.java similarity index 59% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Formatter.java index 49ff988579..c831fcb369 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Method.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Formatter.java @@ -3,6 +3,6 @@ /** * Created by thomas_young on 24/6/2017. */ -public interface Method { - public void action(String msg); +public interface Formatter { + String format(String msg); } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java new file mode 100644 index 0000000000..6c08688f5f --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java @@ -0,0 +1,21 @@ +package com.coderising.ood.ocp.myocp; + +public class FormatterFactory { + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + + public Formatter createFormatter(int logType) { + Formatter formatter; + switch (logType) { + case RAW_LOG: + formatter = new RawFormatter(); + break; + case RAW_LOG_WITH_DATE: + formatter = new DateFormatter(); + break; + default: + throw new IllegalArgumentException("Invalid logType " + logType); + } + return formatter; + } +} \ No newline at end of file diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java index f9fa56ef35..9d2bde495e 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java @@ -1,52 +1,16 @@ package com.coderising.ood.ocp.myocp; - +// 有几个问题: Msg和Method起名不好,建议起Formatter和Sender +// 其次,可以建FormatterFactory和SenderFactory来分别建工厂 /** * Created by thomas_young on 24/6/2017. */ public class LogFactory { - public final int RAW_LOG = 1; - public final int RAW_LOG_WITH_DATE = 2; - public final int EMAIL_LOG = 1; - public final int SMS_LOG = 2; - public final int PRINT_LOG = 3; - public Logger createLogger(int logType, int logMethod) { - Msg msg = genMsg(logType); - Method method = genMethod(logMethod); - return new Logger(msg, method); - } - - private Method genMethod(int logMethod) { - Method method; - switch (logMethod) { - case EMAIL_LOG: - method = new EmailMethod(); - break; - case SMS_LOG: - method = new SmsMethod(); - break; - case PRINT_LOG: - method = new PrintMethod(); - break; - default: - throw new IllegalArgumentException("Invalid logMethod " + logMethod); - } - return method; - } - - private Msg genMsg(int logType) { - Msg msg; - switch (logType) { - case RAW_LOG: - msg = new RawMsg(); - break; - case RAW_LOG_WITH_DATE: - msg = new DateMsg(); - break; - default: - throw new IllegalArgumentException("Invalid logType " + logType); - } - return msg; + SenderFactory senderFactory = new SenderFactory(); + FormatterFactory formatterFactory = new FormatterFactory(); + Formatter formatter = formatterFactory.createFormatter(logType); + Sender sender = senderFactory.createSender(logMethod); + return new Logger(formatter, sender); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java index 9889d0a9b0..94cbab377c 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java @@ -2,15 +2,15 @@ public class Logger { - Method method; - Msg msg; + Sender sender; + Formatter formatter; - public Logger(Msg aMsg, Method aMethod){ - msg= aMsg; - method = aMethod; + public Logger(Formatter aFormatter, Sender aSender){ + formatter = aFormatter; + sender = aSender; } public void log(String message){ - method.action(msg.msg(message)); + sender.send(formatter.format(message)); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java index 6bd1a1f27a..b6ce02902c 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java @@ -3,7 +3,7 @@ public class MailUtil { public static void send(String logMsg) { - // TODO Auto-generated method stub + // TODO Auto-generated sender stub System.out.println("email "+logMsg); } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintSender.java similarity index 63% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintSender.java index a88a229bb3..67a545f6fd 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintMethod.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintSender.java @@ -3,9 +3,9 @@ /** * Created by thomas_young on 24/6/2017. */ -public class PrintMethod implements Method { +public class PrintSender implements Sender { @Override - public void action(String msg) { + public void send(String msg) { System.out.println(msg); } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawFormatter.java similarity index 59% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawFormatter.java index 363746b9e9..f2218bf59d 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawMsg.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawFormatter.java @@ -3,10 +3,10 @@ /** * Created by thomas_young on 24/6/2017. */ -public class RawMsg implements Msg { +public class RawFormatter implements Formatter { @Override - public String msg(String msg) { + public String format(String msg) { return msg; } } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java index 214f583c4c..c127e204b8 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java @@ -3,7 +3,7 @@ public class SMSUtil { public static void send(String logMsg) { - // TODO Auto-generated method stub + // TODO Auto-generated sender stub System.out.println("sms "+logMsg); } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Sender.java similarity index 60% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Sender.java index f479dbecff..939409612a 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Msg.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Sender.java @@ -3,7 +3,6 @@ /** * Created by thomas_young on 24/6/2017. */ -public interface Msg { - public String msg(String msg); - +public interface Sender { + void send(String msg); } diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java new file mode 100644 index 0000000000..e068685b35 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java @@ -0,0 +1,25 @@ +package com.coderising.ood.ocp.myocp; + +public class SenderFactory { + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + public Sender createSender(int logMethod) { + Sender sender; + switch (logMethod) { + case EMAIL_LOG: + sender = new EmailSender(); + break; + case SMS_LOG: + sender = new SmsSender(); + break; + case PRINT_LOG: + sender = new PrintSender(); + break; + default: + throw new IllegalArgumentException("Invalid logMethod " + logMethod); + } + return sender; + } +} \ No newline at end of file diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsSender.java similarity index 63% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java rename to students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsSender.java index 63cce66a2e..47f6b1a412 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsMethod.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsSender.java @@ -4,9 +4,9 @@ /** * Created by thomas_young on 24/6/2017. */ -public class SmsMethod implements Method { +public class SmsSender implements Sender { @Override - public void action(String msg) { + public void send(String msg) { SMSUtil.send(msg); } } From b04dcdf683a976203b51186df329d6c44d7d76ae Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Sat, 24 Jun 2017 19:57:38 +0800 Subject: [PATCH 43/73] =?UTF-8?q?=E5=88=A0=E9=99=A4=E6=97=A0=E7=94=A8?= =?UTF-8?q?=E6=B3=A8=E9=87=8A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java | 2 -- 1 file changed, 2 deletions(-) diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java index 9d2bde495e..63b2d1b8e4 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java +++ b/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java @@ -1,6 +1,4 @@ package com.coderising.ood.ocp.myocp; -// 有几个问题: Msg和Method起名不好,建议起Formatter和Sender -// 其次,可以建FormatterFactory和SenderFactory来分别建工厂 /** * Created by thomas_young on 24/6/2017. From 7082e05e4413a640250b1b7b0ced527d9227fcd8 Mon Sep 17 00:00:00 2001 From: fengdz Date: Sun, 25 Jun 2017 00:15:37 +0800 Subject: [PATCH 44/73] =?UTF-8?q?=E5=88=9B=E5=BB=BA=E8=B4=A3=E4=BB=BB?= =?UTF-8?q?=E5=8C=85=EF=BC=8C=E6=8E=A5=E5=8F=A3=E3=80=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- liuxin/ood/ood-assignment/pom.xml | 14 +++- students/281918307/ood-ocp/pom.xml | 64 +++++++++++++++++-- .../main/java/com/ood/ocp/util/DateUtil.java | 10 +++ .../main/java/com/ood/ocp/util/MailUtil.java | 10 +++ .../main/java/com/ood/ocp/util/SMSUtil.java | 10 +++ 5 files changed, 101 insertions(+), 7 deletions(-) create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/DateUtil.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/MailUtil.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/SMSUtil.java diff --git a/liuxin/ood/ood-assignment/pom.xml b/liuxin/ood/ood-assignment/pom.xml index d1ed73a0bf..84315c8139 100644 --- a/liuxin/ood/ood-assignment/pom.xml +++ b/liuxin/ood/ood-assignment/pom.xml @@ -5,7 +5,19 @@ com.coderising ood-assignment 0.0.1-SNAPSHOT - jar + + + + org.apache.maven.plugins + maven-compiler-plugin + + 1.7 + 1.7 + + + + + jar ood-assignment http://maven.apache.org diff --git a/students/281918307/ood-ocp/pom.xml b/students/281918307/ood-ocp/pom.xml index 284a8b4939..60ad55a370 100644 --- a/students/281918307/ood-ocp/pom.xml +++ b/students/281918307/ood-ocp/pom.xml @@ -14,18 +14,70 @@ ood-ocp jar - + + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-starter-test + + - junit - junit - test + org.springframework.boot + spring-boot-starter-freemarker + + + + org.springframework.boot + spring-boot-starter-data-redis + + + + + org.springframework.boot + spring-boot-devtools + provided + true - log4j - log4j + org.apache.tomcat.embed + tomcat-embed-core + + + + org.springframework.boot + spring-boot-maven-plugin + + com.dajia.customization.Application + -Dfile.encoding=${project.build.sourceEncoding} + + true + + + + + repackage + + + + + + org.apache.maven.plugins + maven-compiler-plugin + + 1.8 + 1.8 + + + + + \ No newline at end of file diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/DateUtil.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/DateUtil.java new file mode 100644 index 0000000000..927250a6c5 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/DateUtil.java @@ -0,0 +1,10 @@ +package com.ood.ocp.util; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/MailUtil.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/MailUtil.java new file mode 100644 index 0000000000..d2be222460 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/MailUtil.java @@ -0,0 +1,10 @@ +package com.ood.ocp.util; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/SMSUtil.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/SMSUtil.java new file mode 100644 index 0000000000..30851cbb40 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/util/SMSUtil.java @@ -0,0 +1,10 @@ +package com.ood.ocp.util; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} From 178a3627620b9e416cc8805ba83be29f8463b4ef Mon Sep 17 00:00:00 2001 From: fengdz Date: Sun, 25 Jun 2017 00:31:49 +0800 Subject: [PATCH 45/73] ocp commit --- .../com/ood/ocp/logs/config/LoggerConfig.java | 25 +++++++ .../ood/ocp/logs/config/LoggerConfigImpl.java | 71 +++++++++++++++++++ .../ood/ocp/logs/content/ContentService.java | 9 +++ .../logs/content/DateContentServiceImpl.java | 17 +++++ .../content/DefaultContentServiceImpl.java | 14 ++++ .../ood/ocp/logs/logger/LoggerService.java | 10 +++ .../ocp/logs/logger/LoggerServiceImpl.java | 35 +++++++++ .../ocp/logs/sender/ConsoleLoggerSender.java | 15 ++++ .../com/ood/ocp/logs/sender/LoggerSender.java | 11 +++ .../ood/ocp/logs/sender/MailLoggerSender.java | 17 +++++ .../ood/ocp/logs/sender/SMSLoggerSender.java | 17 +++++ 11 files changed, 241 insertions(+) create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/ContentService.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DateContentServiceImpl.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DefaultContentServiceImpl.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerService.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/ConsoleLoggerSender.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSender.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/MailLoggerSender.java create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/SMSLoggerSender.java diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java new file mode 100644 index 0000000000..66f82210ba --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java @@ -0,0 +1,25 @@ +package com.ood.ocp.logs.config; + +import com.ood.ocp.logs.content.ContentService; +import com.ood.ocp.logs.sender.LoggerSender; + +/** + * Created by ajaxfeng on 2017/6/24. + */ +public interface LoggerConfig { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + public ContentService getContentService(); + + public LoggerSender getLoggerSender(); + + public void setContentType(int contentType); + + public void setSendType(int sendType); + +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java new file mode 100644 index 0000000000..f5b26cba56 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java @@ -0,0 +1,71 @@ +package com.ood.ocp.logs.config; + +import com.ood.ocp.logs.content.ContentService; +import com.ood.ocp.logs.sender.LoggerSender; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +/** + * Created by ajaxfeng on 2017/6/24. + */ +@Service +public class LoggerConfigImpl implements LoggerConfig { + + private int contentType; + + private int sendType; + @Autowired + private LoggerSender mailLoggerSender; + @Autowired + private LoggerSender smsLoggerSender; + @Autowired + private LoggerSender consoleLoggerSender; + @Autowired + private ContentService contentService; + @Autowired + private ContentService dateContentService; + + + @Override + public ContentService getContentService() { + if (RAW_LOG == contentType) { + return contentService; + } + if (RAW_LOG_WITH_DATE == contentType) { + return dateContentService; + } + + return contentService; + } + + @Override + public LoggerSender getLoggerSender() { + if (EMAIL_LOG == sendType) { + return mailLoggerSender; + } + if (SMS_LOG == sendType) { + return smsLoggerSender; + } + if (PRINT_LOG == sendType) { + return consoleLoggerSender; + } + return mailLoggerSender; + } + + + public int getContentType() { + return contentType; + } + + public void setContentType(int contentType) { + this.contentType = contentType; + } + + public int getSendType() { + return sendType; + } + + public void setSendType(int sendType) { + this.sendType = sendType; + } +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/ContentService.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/ContentService.java new file mode 100644 index 0000000000..b10fedb33a --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/ContentService.java @@ -0,0 +1,9 @@ +package com.ood.ocp.logs.content; + +/** + * Created by ajaxfeng on 2017/6/24. + */ +public interface ContentService { + + public String getConteng(String logMsg); +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DateContentServiceImpl.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DateContentServiceImpl.java new file mode 100644 index 0000000000..a088d537a0 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DateContentServiceImpl.java @@ -0,0 +1,17 @@ +package com.ood.ocp.logs.content; + +import com.ood.ocp.util.DateUtil; +import org.springframework.stereotype.Service; + +/** + * 日期+log + * Created by ajaxfeng on 2017/6/24. + */ +@Service("dateContentService") +public class DateContentServiceImpl implements ContentService { + + @Override + public String getConteng(String logMsg) { + return DateUtil.getCurrentDateAsString() + ":" + logMsg; + } +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DefaultContentServiceImpl.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DefaultContentServiceImpl.java new file mode 100644 index 0000000000..2fee453d79 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/content/DefaultContentServiceImpl.java @@ -0,0 +1,14 @@ +package com.ood.ocp.logs.content; + +import org.springframework.stereotype.Service; + +/** + * Created by ajaxfeng on 2017/6/24. + */ +@Service("contentService") +public class DefaultContentServiceImpl implements ContentService { + @Override + public String getConteng(String logMsg) { + return logMsg; + } +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerService.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerService.java new file mode 100644 index 0000000000..07cda40042 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerService.java @@ -0,0 +1,10 @@ +package com.ood.ocp.logs.logger; + +/** + * 发送日志 + * Created by ajaxfeng on 2017/6/24. + */ +public interface LoggerService { + + public String logger(String logMsg); +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java new file mode 100644 index 0000000000..fa9c4e7d44 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java @@ -0,0 +1,35 @@ +package com.ood.ocp.logs.logger; + +import com.ood.ocp.logs.config.LoggerConfig; +import com.ood.ocp.logs.content.ContentService; +import com.ood.ocp.logs.sender.LoggerSender; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +/** + * Created by ajaxfeng on 2017/6/24. + */ +@Service +public class LoggerServiceImpl implements LoggerService { + + @Autowired + LoggerConfig loggerConfig; + + + @Override + public String logger(String logMsg) { + + loggerConfig.setContentType(1); + loggerConfig.setSendType(1); + + + ContentService contentService = loggerConfig.getContentService(); + String conteng = contentService.getConteng(logMsg); + + + LoggerSender loggerSender = loggerConfig.getLoggerSender(); + loggerSender.sendLog(conteng); + + return "success"; + } +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/ConsoleLoggerSender.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/ConsoleLoggerSender.java new file mode 100644 index 0000000000..ec20cb1229 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/ConsoleLoggerSender.java @@ -0,0 +1,15 @@ +package com.ood.ocp.logs.sender; + +import org.springframework.stereotype.Service; + +/** + * Created by ajaxfeng on 2017/6/25. + */ +@Service("consoleLoggerSender") +public class ConsoleLoggerSender implements LoggerSender { + @Override + public String sendLog(String logMsg) { + System.out.println(logMsg); + return null; + } +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSender.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSender.java new file mode 100644 index 0000000000..1aee4b6ae1 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSender.java @@ -0,0 +1,11 @@ +package com.ood.ocp.logs.sender; + +/** + * 日志发送 + * Created by ajaxfeng on 2017/6/24. + */ +public interface LoggerSender { + + public String sendLog(String logMsg); + +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/MailLoggerSender.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/MailLoggerSender.java new file mode 100644 index 0000000000..513f352ff1 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/MailLoggerSender.java @@ -0,0 +1,17 @@ +package com.ood.ocp.logs.sender; + +import com.ood.ocp.util.MailUtil; +import org.springframework.stereotype.Service; + +/** + * 邮件实现类 + * Created by ajaxfeng on 2017/6/24. + */ +@Service("mailLoggerSender") +public class MailLoggerSender implements LoggerSender { + @Override + public String sendLog(String logMsg) { + MailUtil.send(logMsg); + return "success"; + } +} diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/SMSLoggerSender.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/SMSLoggerSender.java new file mode 100644 index 0000000000..3d6f8f3ea9 --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/SMSLoggerSender.java @@ -0,0 +1,17 @@ +package com.ood.ocp.logs.sender; + +import com.ood.ocp.util.SMSUtil; +import org.springframework.stereotype.Service; + +/** + * 短信 + * Created by ajaxfeng on 2017/6/24. + */ +@Service("smsLoggerSender") +public class SMSLoggerSender implements LoggerSender { + @Override + public String sendLog(String logMsg) { + SMSUtil.send(logMsg); + return null; + } +} From d5f27cf7fea73c9e1f00e8653a9ae7410ef2e0ed Mon Sep 17 00:00:00 2001 From: Yangming Xie Date: Sat, 24 Jun 2017 12:47:11 -0400 Subject: [PATCH 46/73] change the courseWork, add homework 2 and prepare to change --- .../2_assignment/course/bad/Course.java | 24 ++++++++++++ .../course/bad/CourseOffering.java | 24 ++++++++++++ .../course/bad/CourseService.java | 12 ++++++ .../2_assignment/course/bad/Student.java | 20 ++++++++++ .../2_assignment/course/good/Course.java | 18 +++++++++ .../course/good/CourseOffering.java | 34 +++++++++++++++++ .../course/good/CourseService.java | 14 +++++++ .../2_assignment/course/good/Student.java | 21 ++++++++++ .../702282822/2_assignment/ocp/DateUtil.java | 10 +++++ .../702282822/2_assignment/ocp/Logger.java | 38 +++++++++++++++++++ .../702282822/2_assignment/ocp/MailUtil.java | 10 +++++ .../702282822/2_assignment/ocp/SMSUtil.java | 10 +++++ 12 files changed, 235 insertions(+) create mode 100644 students/702282822/2_assignment/course/bad/Course.java create mode 100644 students/702282822/2_assignment/course/bad/CourseOffering.java create mode 100644 students/702282822/2_assignment/course/bad/CourseService.java create mode 100644 students/702282822/2_assignment/course/bad/Student.java create mode 100644 students/702282822/2_assignment/course/good/Course.java create mode 100644 students/702282822/2_assignment/course/good/CourseOffering.java create mode 100644 students/702282822/2_assignment/course/good/CourseService.java create mode 100644 students/702282822/2_assignment/course/good/Student.java create mode 100644 students/702282822/2_assignment/ocp/DateUtil.java create mode 100644 students/702282822/2_assignment/ocp/Logger.java create mode 100644 students/702282822/2_assignment/ocp/MailUtil.java create mode 100644 students/702282822/2_assignment/ocp/SMSUtil.java diff --git a/students/702282822/2_assignment/course/bad/Course.java b/students/702282822/2_assignment/course/bad/Course.java new file mode 100644 index 0000000000..436d092f58 --- /dev/null +++ b/students/702282822/2_assignment/course/bad/Course.java @@ -0,0 +1,24 @@ +package com.coderising.ood.course.bad; + +import java.util.List; + +public class Course { + private String id; + private String desc; + private int duration ; + + List prerequisites; + + public List getPrerequisites() { + return prerequisites; + } + + + public boolean equals(Object o){ + if(o == null || !(o instanceof Course)){ + return false; + } + Course c = (Course)o; + return (c != null) && c.id.equals(id); + } +} diff --git a/students/702282822/2_assignment/course/bad/CourseOffering.java b/students/702282822/2_assignment/course/bad/CourseOffering.java new file mode 100644 index 0000000000..e24bcd2062 --- /dev/null +++ b/students/702282822/2_assignment/course/bad/CourseOffering.java @@ -0,0 +1,24 @@ +package com.coderising.ood.course.bad; + +import java.util.ArrayList; +import java.util.List; + + +public class CourseOffering { + private Course course; + private String location; + private String teacher; + private int maxStudents; + + List students = new ArrayList(); + + public void addStudent(Student st) + { + if(st.canAttend(course) && maxStudents > students.size()) + { + students.add(st); + } + } + + +} diff --git a/students/702282822/2_assignment/course/bad/CourseService.java b/students/702282822/2_assignment/course/bad/CourseService.java new file mode 100644 index 0000000000..3d06149ca2 --- /dev/null +++ b/students/702282822/2_assignment/course/bad/CourseService.java @@ -0,0 +1,12 @@ +package com.coderising.ood.course.bad; + + + +public class CourseService { + + public void chooseCourse(Student student, CourseOffering sc){ + //如果学生上过该科目的先修科目,并且该课程还未满, 则学生可以加入该课程 + sc.addStudent(student); + } + +} diff --git a/students/702282822/2_assignment/course/bad/Student.java b/students/702282822/2_assignment/course/bad/Student.java new file mode 100644 index 0000000000..6629b60bfb --- /dev/null +++ b/students/702282822/2_assignment/course/bad/Student.java @@ -0,0 +1,20 @@ +package com.coderising.ood.course.bad; + +import java.util.ArrayList; +import java.util.List; + +public class Student { + private String id; + private String name; + private List coursesAlreadyTaken = new ArrayList(); + + public List getCoursesAlreadyTaken() { + return coursesAlreadyTaken; + } + public boolean canAttend(Course course){ + return getCoursesAlreadyTaken().containsAll( + course.getPrerequisites()); + } + + +} diff --git a/students/702282822/2_assignment/course/good/Course.java b/students/702282822/2_assignment/course/good/Course.java new file mode 100644 index 0000000000..aefc9692bb --- /dev/null +++ b/students/702282822/2_assignment/course/good/Course.java @@ -0,0 +1,18 @@ +package com.coderising.ood.course.good; + +import java.util.List; + +public class Course { + private String id; + private String desc; + private int duration ; + + List prerequisites; + + public List getPrerequisites() { + return prerequisites; + } + +} + + diff --git a/students/702282822/2_assignment/course/good/CourseOffering.java b/students/702282822/2_assignment/course/good/CourseOffering.java new file mode 100644 index 0000000000..8660ec8109 --- /dev/null +++ b/students/702282822/2_assignment/course/good/CourseOffering.java @@ -0,0 +1,34 @@ +package com.coderising.ood.course.good; + +import java.util.ArrayList; +import java.util.List; + +public class CourseOffering { + private Course course; + private String location; + private String teacher; + private int maxStudents; + + List students = new ArrayList(); + + public List getStudents() { + return students; + } + public int getMaxStudents() { + return maxStudents; + } + public Course getCourse() { + return course; + } + + + // 第二步: 把主要逻辑移动到CourseOffering 中 + public void addStudent(Student student){ + + if(student.canAttend(course) + && this.maxStudents > students.size()){ + students.add(student); + } + } + // 第三步: 重构CourseService +} diff --git a/students/702282822/2_assignment/course/good/CourseService.java b/students/702282822/2_assignment/course/good/CourseService.java new file mode 100644 index 0000000000..22ba4a5450 --- /dev/null +++ b/students/702282822/2_assignment/course/good/CourseService.java @@ -0,0 +1,14 @@ +package com.coderising.ood.course.good; + + + +public class CourseService { + + public void chooseCourse(Student student, CourseOffering sc){ + //第一步:重构: canAttend , 但是还有问题 + if(student.canAttend(sc.getCourse()) + && sc.getMaxStudents() > sc.getStudents().size()){ + sc.getStudents().add(student); + } + } +} diff --git a/students/702282822/2_assignment/course/good/Student.java b/students/702282822/2_assignment/course/good/Student.java new file mode 100644 index 0000000000..2c7e128b2a --- /dev/null +++ b/students/702282822/2_assignment/course/good/Student.java @@ -0,0 +1,21 @@ +package com.coderising.ood.course.good; + +import java.util.ArrayList; +import java.util.List; + +public class Student { + private String id; + private String name; + private List coursesAlreadyTaken = new ArrayList(); + + public List getCoursesAlreadyTaken() { + return coursesAlreadyTaken; + } + + public boolean canAttend(Course course){ + return this.coursesAlreadyTaken.containsAll( + course.getPrerequisites()); + } +} + + diff --git a/students/702282822/2_assignment/ocp/DateUtil.java b/students/702282822/2_assignment/ocp/DateUtil.java new file mode 100644 index 0000000000..b6cf28c096 --- /dev/null +++ b/students/702282822/2_assignment/ocp/DateUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class DateUtil { + + public static String getCurrentDateAsString() { + + return null; + } + +} diff --git a/students/702282822/2_assignment/ocp/Logger.java b/students/702282822/2_assignment/ocp/Logger.java new file mode 100644 index 0000000000..0357c4d912 --- /dev/null +++ b/students/702282822/2_assignment/ocp/Logger.java @@ -0,0 +1,38 @@ +package com.coderising.ood.ocp; + +public class Logger { + + public final int RAW_LOG = 1; + public final int RAW_LOG_WITH_DATE = 2; + public final int EMAIL_LOG = 1; + public final int SMS_LOG = 2; + public final int PRINT_LOG = 3; + + int type = 0; + int method = 0; + + public Logger(int logType, int logMethod){ + this.type = logType; + this.method = logMethod; + } + public void log(String msg){ + + String logMsg = msg; + + if(this.type == RAW_LOG){ + logMsg = msg; + } else if(this.type == RAW_LOG_WITH_DATE){ + String txtDate = DateUtil.getCurrentDateAsString(); + logMsg = txtDate + ": " + msg; + } + + if(this.method == EMAIL_LOG){ + MailUtil.send(logMsg); + } else if(this.method == SMS_LOG){ + SMSUtil.send(logMsg); + } else if(this.method == PRINT_LOG){ + System.out.println(logMsg); + } + } +} + diff --git a/students/702282822/2_assignment/ocp/MailUtil.java b/students/702282822/2_assignment/ocp/MailUtil.java new file mode 100644 index 0000000000..ec54b839c5 --- /dev/null +++ b/students/702282822/2_assignment/ocp/MailUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class MailUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/702282822/2_assignment/ocp/SMSUtil.java b/students/702282822/2_assignment/ocp/SMSUtil.java new file mode 100644 index 0000000000..13cf802418 --- /dev/null +++ b/students/702282822/2_assignment/ocp/SMSUtil.java @@ -0,0 +1,10 @@ +package com.coderising.ood.ocp; + +public class SMSUtil { + + public static void send(String logMsg) { + // TODO Auto-generated method stub + + } + +} From ad51dedc75c0ca5aaf032a5ef0dcd6337f067a72 Mon Sep 17 00:00:00 2001 From: Yangming Xie Date: Sun, 25 Jun 2017 01:18:40 -0400 Subject: [PATCH 47/73] refactor second homework, refert to the good one --- .../702282822/2_assignment/ocp/Deliver.java | 5 +++ .../2_assignment/ocp/DeliveryFactory.java | 20 ++++++++++ .../2_assignment/ocp/Email_Deliver.java | 9 +++++ .../702282822/2_assignment/ocp/Formatter.java | 4 ++ .../2_assignment/ocp/FormatterFactory.java | 14 +++++++ .../702282822/2_assignment/ocp/Logger.java | 40 +++++-------------- .../2_assignment/ocp/Print_Deliver.java | 8 ++++ .../702282822/2_assignment/ocp/Raw_log.java | 8 ++++ .../2_assignment/ocp/Raw_log_withDate.java | 12 ++++++ .../2_assignment/ocp/SMS_Deliver.java | 10 +++++ 10 files changed, 100 insertions(+), 30 deletions(-) create mode 100644 students/702282822/2_assignment/ocp/Deliver.java create mode 100644 students/702282822/2_assignment/ocp/DeliveryFactory.java create mode 100644 students/702282822/2_assignment/ocp/Email_Deliver.java create mode 100644 students/702282822/2_assignment/ocp/Formatter.java create mode 100644 students/702282822/2_assignment/ocp/FormatterFactory.java create mode 100644 students/702282822/2_assignment/ocp/Print_Deliver.java create mode 100644 students/702282822/2_assignment/ocp/Raw_log.java create mode 100644 students/702282822/2_assignment/ocp/Raw_log_withDate.java create mode 100644 students/702282822/2_assignment/ocp/SMS_Deliver.java diff --git a/students/702282822/2_assignment/ocp/Deliver.java b/students/702282822/2_assignment/ocp/Deliver.java new file mode 100644 index 0000000000..377fcf3a64 --- /dev/null +++ b/students/702282822/2_assignment/ocp/Deliver.java @@ -0,0 +1,5 @@ + +public interface Dilever +{ + public void process(string str); +} diff --git a/students/702282822/2_assignment/ocp/DeliveryFactory.java b/students/702282822/2_assignment/ocp/DeliveryFactory.java new file mode 100644 index 0000000000..daf562759e --- /dev/null +++ b/students/702282822/2_assignment/ocp/DeliveryFactory.java @@ -0,0 +1,20 @@ + +public interface DeliveryFactory +{ + public static Deliver createDelivery(int type) + { + if(type == 1) + { + return new Email_Deliver(); + } + else if(type == 2) + { + return new SMS_Deliver(); + } + else if(type == 3) + { + return new Print_Deliver(); + } + } + +} diff --git a/students/702282822/2_assignment/ocp/Email_Deliver.java b/students/702282822/2_assignment/ocp/Email_Deliver.java new file mode 100644 index 0000000000..c4eee88ded --- /dev/null +++ b/students/702282822/2_assignment/ocp/Email_Deliver.java @@ -0,0 +1,9 @@ + +public class Email_Deliver implements dileverMsg +{ + public void process(string str) + { + MailUtil.send(logMsg); + } + +} diff --git a/students/702282822/2_assignment/ocp/Formatter.java b/students/702282822/2_assignment/ocp/Formatter.java new file mode 100644 index 0000000000..35cf0bf4e3 --- /dev/null +++ b/students/702282822/2_assignment/ocp/Formatter.java @@ -0,0 +1,4 @@ +public interface Formatter +{ + public string format(string msg); +} diff --git a/students/702282822/2_assignment/ocp/FormatterFactory.java b/students/702282822/2_assignment/ocp/FormatterFactory.java new file mode 100644 index 0000000000..1f9ef348fd --- /dev/null +++ b/students/702282822/2_assignment/ocp/FormatterFactory.java @@ -0,0 +1,14 @@ + +public class FormatterFactory { + public static Formatter createFormate(int type) + { + if(type == 1) + { + return new Raw_log(); + } + else if(type == 2) + { + return new Raw_log_withDate(); + } + } +} diff --git a/students/702282822/2_assignment/ocp/Logger.java b/students/702282822/2_assignment/ocp/Logger.java index 0357c4d912..839c8d74cd 100644 --- a/students/702282822/2_assignment/ocp/Logger.java +++ b/students/702282822/2_assignment/ocp/Logger.java @@ -2,37 +2,17 @@ public class Logger { - public final int RAW_LOG = 1; - public final int RAW_LOG_WITH_DATE = 2; - public final int EMAIL_LOG = 1; - public final int SMS_LOG = 2; - public final int PRINT_LOG = 3; - - int type = 0; - int method = 0; - - public Logger(int logType, int logMethod){ - this.type = logType; - this.method = logMethod; + private Formatter formatter; + private Dilever deliver; + public Logger(Formatter formatter, Dilever deliver) + { + this.formatter = formatter; + this.deliver = deliver; } - public void log(String msg){ - - String logMsg = msg; - - if(this.type == RAW_LOG){ - logMsg = msg; - } else if(this.type == RAW_LOG_WITH_DATE){ - String txtDate = DateUtil.getCurrentDateAsString(); - logMsg = txtDate + ": " + msg; - } - - if(this.method == EMAIL_LOG){ - MailUtil.send(logMsg); - } else if(this.method == SMS_LOG){ - SMSUtil.send(logMsg); - } else if(this.method == PRINT_LOG){ - System.out.println(logMsg); - } + public void log(String msg) + { + String message = formatter.formate(msg); + deliver.process(message); } } diff --git a/students/702282822/2_assignment/ocp/Print_Deliver.java b/students/702282822/2_assignment/ocp/Print_Deliver.java new file mode 100644 index 0000000000..10c31ba398 --- /dev/null +++ b/students/702282822/2_assignment/ocp/Print_Deliver.java @@ -0,0 +1,8 @@ + +public class Print_Deliver +{ + public void process(string str) + { + System.out.print(str); + } +} diff --git a/students/702282822/2_assignment/ocp/Raw_log.java b/students/702282822/2_assignment/ocp/Raw_log.java new file mode 100644 index 0000000000..5f6af6cf2c --- /dev/null +++ b/students/702282822/2_assignment/ocp/Raw_log.java @@ -0,0 +1,8 @@ + +public class Raw_log implements Formatter +{ + public string format(string msg) + { + return msg; + } +} diff --git a/students/702282822/2_assignment/ocp/Raw_log_withDate.java b/students/702282822/2_assignment/ocp/Raw_log_withDate.java new file mode 100644 index 0000000000..3458923e3f --- /dev/null +++ b/students/702282822/2_assignment/ocp/Raw_log_withDate.java @@ -0,0 +1,12 @@ + +public class Raw_log_withDate implements Raw_log +{ + public string format(string msg) + { + string msg = super.format(msg); + String txtDate = DateUtil.getCurrentDateAsString(); + return txtDate + ": " + msg; + } + + +} diff --git a/students/702282822/2_assignment/ocp/SMS_Deliver.java b/students/702282822/2_assignment/ocp/SMS_Deliver.java new file mode 100644 index 0000000000..047cf55b28 --- /dev/null +++ b/students/702282822/2_assignment/ocp/SMS_Deliver.java @@ -0,0 +1,10 @@ + +public class SMS_Deliver implements dileverMsg +{ + public void process(string str) + { + SMSUtil.send(str); + } + + +} From 1f5e3e33061985d291055499f07f88bb9e09f0b7 Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Mon, 26 Jun 2017 00:27:25 +0800 Subject: [PATCH 48/73] =?UTF-8?q?=E5=8F=91=E9=82=AE=E4=BB=B6=E7=9A=84?= =?UTF-8?q?=E6=A8=A1=E6=9D=BF=E4=BC=98=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/coderising/ood/srp/goodSrp/Mail.java | 9 +++++--- .../coderising/ood/srp/goodSrp/MailUtil.java | 15 +++++++------ .../ood/srp/goodSrp/ProductService.java | 2 +- .../ood/srp/goodSrp/UserService.java | 2 +- .../goodSrp/template/MailBodyTemplate.java | 2 +- .../template/TextMailBodyTemplate.java | 21 +++++++------------ 6 files changed, 24 insertions(+), 27 deletions(-) diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java index cbac40d547..858c154713 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java @@ -1,12 +1,15 @@ package com.coderising.ood.srp.goodSrp; +import com.coderising.ood.srp.goodSrp.template.MailBodyTemplate; +import com.coderising.ood.srp.goodSrp.template.TextMailBodyTemplate; + import java.util.List; import java.util.stream.Collectors; public class Mail { private User user; - + MailBodyTemplate mailBodyTemplate; public Mail(User u){ this.user = u; } @@ -17,8 +20,8 @@ public String getSubject(){ return "您关注的产品降价了"; } public String getBody(){ - - return "尊敬的 "+user.getName()+", 您关注的产品 " + this.buildProductDescList() + " 降价了,欢迎购买!" ; + mailBodyTemplate = new TextMailBodyTemplate(user.getName(), buildProductDescList(), getAddress()); + return mailBodyTemplate.render(); } private String buildProductDescList() { List products = user.getSubscribedProducts(); diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java index a1fb0ceb73..132ca6be87 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java @@ -1,17 +1,16 @@ package com.coderising.ood.srp.goodSrp; - -import com.coderising.ood.srp.goodSrp.template.MailBodyTemplate; -import com.coderising.ood.srp.goodSrp.template.TextMailBodyTemplate; - public class MailUtil { public static void sendEmail(Mail mail, String smtpHost, String fromAddress) { //假装发了一封邮件 System.out.println("使用smtpHost为"+smtpHost); - MailBodyTemplate template = new TextMailBodyTemplate(mail, fromAddress); - System.out.println(template.render()); - } + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(mail.getAddress()).append("\n"); + buffer.append("Subject:").append(mail.getSubject()).append("\n"); + buffer.append("Content:").append(mail.getBody()).append("\n"); - + System.out.println(buffer.toString()); + } } diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java index a787d00eb3..12ad38262e 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java @@ -26,7 +26,7 @@ private Product parseGenProduct(String line) { String[] data = line.split(" "); String productID = data[0]; String productDesc = data[1]; - System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品ID = " + productID); System.out.println("产品描述 = " + productDesc + "\n"); Product p = new Product(); p.setDesc(productDesc); diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java index 635f9fe140..a2bd152896 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java @@ -12,7 +12,7 @@ public class UserService { public List getUsers(List ps) { List users = new LinkedList<>(); String sql = "Select name from subscriptions where send_mail=1"; - System.out.println("loadQuery set"); + System.out.println("loadQuery set\n"); List userInfoList = DBUtil.query(sql); for (Object userInfo: userInfoList) { User user = new User(); diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java index 1852b6155a..95eeff723f 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java @@ -1,5 +1,5 @@ package com.coderising.ood.srp.goodSrp.template; public interface MailBodyTemplate { - public String render(); + String render(); } diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java index b7906c6bf2..4dd174a3ce 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java +++ b/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java @@ -1,25 +1,20 @@ package com.coderising.ood.srp.goodSrp.template; -import com.coderising.ood.srp.goodSrp.Mail; - public class TextMailBodyTemplate implements MailBodyTemplate { - private Mail mail; - String fromAdress; - public TextMailBodyTemplate(Mail mail, String fromAdress){ - this.mail = mail; - this.fromAdress = fromAdress; + String productDescription; + String name; + String toAdress; + public TextMailBodyTemplate(String name, String productDescription, String toAdress){ + this.productDescription = productDescription; + this.name = name; + this.toAdress = toAdress; } @Override public String render() { //使用某种模板技术实现Render - StringBuilder buffer = new StringBuilder(); - buffer.append("From:").append(fromAdress).append("\n"); - buffer.append("To:").append(mail.getAddress()).append("\n"); - buffer.append("Subject:").append(mail.getSubject()).append("\n"); - buffer.append("Content:").append(mail.getBody()).append("\n"); - return buffer.toString(); + return "尊敬的 "+ name +", 您关注的产品 " + productDescription + " 降价了,欢迎购买!" ; } } From 23bcc0e21b61ef5831a69ed5ec44d865a1d09c8d Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Mon, 26 Jun 2017 00:49:09 +0800 Subject: [PATCH 49/73] =?UTF-8?q?=E5=88=9B=E5=BB=BA=E5=A4=9A=E7=BA=BF?= =?UTF-8?q?=E7=A8=8B=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../myknowledgepoint/cas/CASSequence.java | 18 +++++++++ .../myknowledgepoint/cas/NoBlockingStack.java | 34 +++++++++++++++++ .../myknowledgepoint/cas/Sequence.java | 11 ++++++ .../myknowledgepoint/threadlocal/Context.java | 21 ++++++++++ .../threadlocal/TransactionManager.java | 22 +++++++++++ .../threadpool/BlockingQueue.java | 36 ++++++++++++++++++ .../myknowledgepoint/threadpool/Task.java | 5 +++ .../threadpool/ThreadPool.java | 38 +++++++++++++++++++ .../threadpool/WorkerThread.java | 32 ++++++++++++++++ 9 files changed, 217 insertions(+) create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/CASSequence.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/NoBlockingStack.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/Sequence.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/Context.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/TransactionManager.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/BlockingQueue.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/WorkerThread.java diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/CASSequence.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/CASSequence.java new file mode 100644 index 0000000000..144aa264ff --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/CASSequence.java @@ -0,0 +1,18 @@ +package com.coderising.myknowledgepoint.cas; + +import java.util.concurrent.atomic.AtomicInteger; + +public class CASSequence{ + + private AtomicInteger count = new AtomicInteger(0); + + public int next(){ + while(true){ + int current = count.get(); + int next = current +1; + if(count.compareAndSet(current, next)){ + return next; + } + } + } +} \ No newline at end of file diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/NoBlockingStack.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/NoBlockingStack.java new file mode 100644 index 0000000000..c03c096c78 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/NoBlockingStack.java @@ -0,0 +1,34 @@ +package com.coderising.myknowledgepoint.cas; + +import java.util.concurrent.atomic.AtomicReference; + +public class NoBlockingStack { + static class Node { + final E item; + Node next; + public Node(E item) { this.item = item; } + } + + AtomicReference> head = new AtomicReference>(); + + public void push(E item) { + Node newHead = new Node(item); + Node oldHead; + do { + oldHead = head.get(); + newHead.next = oldHead; + } while (!head.compareAndSet(oldHead, newHead)); + } + public E pop() { + Node oldHead; + Node newHead; + do { + oldHead = head.get(); + if (oldHead == null) + return null; + newHead = oldHead.next; + } while (!head.compareAndSet(oldHead,newHead)); + return oldHead.item; + } + +} diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/Sequence.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/Sequence.java new file mode 100644 index 0000000000..25909d0dd9 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/cas/Sequence.java @@ -0,0 +1,11 @@ +package com.coderising.myknowledgepoint.cas; + +public class Sequence{ + + private int value; + + public int next(){ + return value ++; + } + +} diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/Context.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/Context.java new file mode 100644 index 0000000000..a9b18ddaf4 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/Context.java @@ -0,0 +1,21 @@ +package com.coderising.myknowledgepoint.threadlocal; + +import java.util.HashMap; +import java.util.Map; + +public class Context { + + private static final ThreadLocal txThreadLocal + = new ThreadLocal(); + + public static void setTransactionID(String txID) { + txThreadLocal.set(txID); + + } + + public static String getTransactionId() { + return txThreadLocal.get(); + } + +} + diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/TransactionManager.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/TransactionManager.java new file mode 100644 index 0000000000..2cf9170578 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadlocal/TransactionManager.java @@ -0,0 +1,22 @@ +package com.coderising.myknowledgepoint.threadlocal; + +public class TransactionManager { + private static final ThreadLocal context = new ThreadLocal(); + + public static void startTransaction() { + // logic to start a transaction + // ... + String txID = null; + context.set(txID); + } + + public static String getTransactionId() { + return context.get(); + } + + public static void endTransaction() { + // logic to end a transaction + // … + context.remove(); + } +} diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/BlockingQueue.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/BlockingQueue.java new file mode 100644 index 0000000000..d6e9ec5104 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/BlockingQueue.java @@ -0,0 +1,36 @@ +package com.coderising.myknowledgepoint.threadpool; + +import java.util.LinkedList; +import java.util.List; + +public class BlockingQueue { + + private List queue = new LinkedList(); + private int limit = 10; + + public BlockingQueue(int limit) { + this.limit = limit; + } + + public synchronized void enqueue(Object item) throws InterruptedException { + while (this.queue.size() == this.limit) { + wait(); + } + if (this.queue.size() == 0) { + notifyAll(); + } + this.queue.add(item); + } + + public synchronized Object dequeue() throws InterruptedException { + while (this.queue.size() == 0) { + wait(); + } + if (this.queue.size() == this.limit) { + notifyAll(); + } + + return this.queue.remove(0); + } + +} diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java new file mode 100644 index 0000000000..be844e09f3 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java @@ -0,0 +1,5 @@ +package com.coderising.myknowledgepoint.threadpool; + +public interface Task { + public void execute(); +} diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java new file mode 100644 index 0000000000..267c3fb9f5 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java @@ -0,0 +1,38 @@ +package com.coderising.myknowledgepoint.threadpool; + +import java.util.ArrayList; +import java.util.List; + + +public class ThreadPool { + + private BlockingQueue taskQueue = null; + private List threads = new ArrayList(); + private boolean isStopped = false; + + public ThreadPool(int numOfThreads, int maxNumOfTasks){ + taskQueue = new BlockingQueue(maxNumOfTasks); + + for(int i=0; i Date: Mon, 26 Jun 2017 15:50:53 +0800 Subject: [PATCH 50/73] add homework for UML --- students/495232796/OOD/UML/DiceGame-class.jpg | Bin 0 -> 60971 bytes .../495232796/OOD/UML/DiceGame-sequence.jpg | Bin 0 -> 71663 bytes students/495232796/OOD/UML/ShoppingSite.jpg | Bin 0 -> 74258 bytes 3 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 students/495232796/OOD/UML/DiceGame-class.jpg create mode 100644 students/495232796/OOD/UML/DiceGame-sequence.jpg create mode 100644 students/495232796/OOD/UML/ShoppingSite.jpg diff --git a/students/495232796/OOD/UML/DiceGame-class.jpg b/students/495232796/OOD/UML/DiceGame-class.jpg new file mode 100644 index 0000000000000000000000000000000000000000..869d72dd5e3c11b168d4b32d3540e9cd953ffc29 GIT binary patch literal 60971 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

8rGu>D-$ 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 literal 0 HcmV?d00001 diff --git a/students/495232796/OOD/UML/ShoppingSite.jpg b/students/495232796/OOD/UML/ShoppingSite.jpg new file mode 100644 index 0000000000000000000000000000000000000000..5e05336f627ef4fb76a38ebd31d59556bff1983e GIT binary patch literal 74258 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 Pw~xu{UXIqfw$}C&ox Date: Mon, 26 Jun 2017 19:52:48 +0800 Subject: [PATCH 51/73] =?UTF-8?q?ocp=20commit,=20=E6=94=AF=E6=8C=81?= =?UTF-8?q?=E8=A7=82=E5=AF=9F=E8=80=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/ood/ocp/logs/config/LoggerConfig.java | 18 ++++++--- .../ood/ocp/logs/config/LoggerConfigImpl.java | 37 +++++++++++------- .../ocp/logs/logger/LoggerServiceImpl.java | 22 +++++++---- .../ocp/logs/sender/LoggerSenderWacher.java | 39 +++++++++++++++++++ 4 files changed, 88 insertions(+), 28 deletions(-) create mode 100644 students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSenderWacher.java diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java index 66f82210ba..fac6f09e8c 100644 --- a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfig.java @@ -1,7 +1,8 @@ package com.ood.ocp.logs.config; import com.ood.ocp.logs.content.ContentService; -import com.ood.ocp.logs.sender.LoggerSender; + +import java.util.List; /** * Created by ajaxfeng on 2017/6/24. @@ -14,12 +15,17 @@ public interface LoggerConfig { public final int SMS_LOG = 2; public final int PRINT_LOG = 3; + /** + * + * @return + */ public ContentService getContentService(); - public LoggerSender getLoggerSender(); - - public void setContentType(int contentType); - - public void setSendType(int sendType); + /** + * 设置类型 + * + * @param sendTypeList + */ + public void setSendTypeList(List sendTypeList); } diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java index f5b26cba56..f8ef1661cd 100644 --- a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/config/LoggerConfigImpl.java @@ -2,18 +2,23 @@ import com.ood.ocp.logs.content.ContentService; import com.ood.ocp.logs.sender.LoggerSender; +import com.ood.ocp.logs.sender.LoggerSenderWacher; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; +import java.util.List; + /** * Created by ajaxfeng on 2017/6/24. */ @Service public class LoggerConfigImpl implements LoggerConfig { + @Autowired + private LoggerSenderWacher loggerSenderWacher; private int contentType; - private int sendType; + private List sendTypeList; @Autowired private LoggerSender mailLoggerSender; @Autowired @@ -38,21 +43,18 @@ public ContentService getContentService() { return contentService; } - @Override - public LoggerSender getLoggerSender() { - if (EMAIL_LOG == sendType) { - return mailLoggerSender; + private void initLoggerWacher(){ + if(sendTypeList.contains(EMAIL_LOG)){ + loggerSenderWacher.addLoggerSender(mailLoggerSender); } - if (SMS_LOG == sendType) { - return smsLoggerSender; + if(sendTypeList.contains(SMS_LOG)){ + loggerSenderWacher.addLoggerSender(smsLoggerSender); } - if (PRINT_LOG == sendType) { - return consoleLoggerSender; + if(sendTypeList.contains(PRINT_LOG)){ + loggerSenderWacher.addLoggerSender(consoleLoggerSender); } - return mailLoggerSender; } - public int getContentType() { return contentType; } @@ -61,11 +63,16 @@ public void setContentType(int contentType) { this.contentType = contentType; } - public int getSendType() { - return sendType; + public List getSendTypeList() { + return sendTypeList; } - public void setSendType(int sendType) { - this.sendType = sendType; + /** + * 设置类型 + * @param sendTypeList + */ + public void setSendTypeList(List sendTypeList) { + this.sendTypeList = sendTypeList; + initLoggerWacher(); } } diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java index fa9c4e7d44..b1d370e4c6 100644 --- a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/logger/LoggerServiceImpl.java @@ -3,9 +3,13 @@ import com.ood.ocp.logs.config.LoggerConfig; import com.ood.ocp.logs.content.ContentService; import com.ood.ocp.logs.sender.LoggerSender; +import com.ood.ocp.logs.sender.LoggerSenderWacher; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; +import java.util.ArrayList; +import java.util.List; + /** * Created by ajaxfeng on 2017/6/24. */ @@ -14,22 +18,26 @@ public class LoggerServiceImpl implements LoggerService { @Autowired LoggerConfig loggerConfig; + @Autowired + LoggerSenderWacher loggerSenderWacher; @Override public String logger(String logMsg) { - loggerConfig.setContentType(1); - loggerConfig.setSendType(1); + List typeList=new ArrayList(); + typeList.add(1); + typeList.add(2); + typeList.add(3); + loggerConfig.setSendTypeList(typeList); + //构造内容 ContentService contentService = loggerConfig.getContentService(); - String conteng = contentService.getConteng(logMsg); - - - LoggerSender loggerSender = loggerConfig.getLoggerSender(); - loggerSender.sendLog(conteng); + String content = contentService.getConteng(logMsg); + //推送消息 + loggerSenderWacher.watch(content); return "success"; } } diff --git a/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSenderWacher.java b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSenderWacher.java new file mode 100644 index 0000000000..72f5c8013a --- /dev/null +++ b/students/281918307/ood-ocp/src/main/java/com/ood/ocp/logs/sender/LoggerSenderWacher.java @@ -0,0 +1,39 @@ +package com.ood.ocp.logs.sender; + +import org.springframework.stereotype.Service; + +import java.util.List; + +/** + * 日志观察者 + * Created by ajaxfeng on 2017/6/26. + */ +@Service +public class LoggerSenderWacher { + private List loggerSenders; + + public List getLoggerSenders() { + return loggerSenders; + } + + public void addLoggerSender(LoggerSender loggerSender){ + if(!loggerSenders.contains(loggerSender)){ + loggerSenders.add(loggerSender); + } + } + + public void setLoggerSenders(List loggerSenders) { + this.loggerSenders = loggerSenders; + } + + /** + * 调用观察者发送消息 + * @param content + */ + public void watch(String content){ + for(LoggerSender loggerSender:loggerSenders){ + loggerSender.sendLog(content); + } + } + +} From f6588e44bcd46f8ca695616483b5b50a1316fd11 Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Mon, 26 Jun 2017 22:55:05 +0800 Subject: [PATCH 52/73] =?UTF-8?q?=E7=BA=BF=E7=A8=8B=E6=B1=A0=E4=BD=BF?= =?UTF-8?q?=E7=94=A81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../threadpool/DriveThreadPool.java | 25 +++++++++++++++++++ .../myknowledgepoint/threadpool/Task.java | 2 +- .../threadpool/ThreadPool.java | 14 +++++++++-- .../threadpool/WorkerThread.java | 3 ++- 4 files changed, 40 insertions(+), 4 deletions(-) create mode 100644 students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/DriveThreadPool.java diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/DriveThreadPool.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/DriveThreadPool.java new file mode 100644 index 0000000000..015317af41 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/DriveThreadPool.java @@ -0,0 +1,25 @@ +package com.coderising.myknowledgepoint.threadpool; + +/** + * Created by thomas_young on 26/6/2017. + */ +public class DriveThreadPool { + + public static void main(String[] args) throws Exception { + Task task = ()-> { + try { + Thread.sleep(1000); + } catch (InterruptedException e) { + System.out.println("I'm killed!"); + } + System.out.println("haha"); + }; + + ThreadPool pool = new ThreadPool(5, 2); + for (int i=1; i<10; i++) { + pool.execute(task); + } + pool.stop(); + + } +} diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java index be844e09f3..418d672f78 100644 --- a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/Task.java @@ -1,5 +1,5 @@ package com.coderising.myknowledgepoint.threadpool; public interface Task { - public void execute(); + void execute(); } diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java index 267c3fb9f5..96472822e2 100644 --- a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/ThreadPool.java @@ -7,9 +7,14 @@ public class ThreadPool { private BlockingQueue taskQueue = null; - private List threads = new ArrayList(); + private List threads = new ArrayList<>(); private boolean isStopped = false; + /** + * 线程池实例化的时候,线程就都启动了 + * @param numOfThreads + * @param maxNumOfTasks + */ public ThreadPool(int numOfThreads, int maxNumOfTasks){ taskQueue = new BlockingQueue(maxNumOfTasks); @@ -21,7 +26,12 @@ public ThreadPool(int numOfThreads, int maxNumOfTasks){ } } - public synchronized void execute(Task task) throws Exception{ + /** + * 往阻塞队列里面加task + * @param task + * @throws Exception + */ + public synchronized void execute(Task task) throws Exception{ if(this.isStopped) throw new IllegalStateException("ThreadPool is stopped"); diff --git a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/WorkerThread.java b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/WorkerThread.java index 1f1b08f55e..790e2a463f 100644 --- a/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/WorkerThread.java +++ b/students/812350401/src/main/java/com/coderising/myknowledgepoint/threadpool/WorkerThread.java @@ -17,13 +17,14 @@ public void run(){ } catch(Exception e){ //log or otherwise report exception, //but keep pool thread alive. + System.out.println("doStop"); } } } public synchronized void doStop(){ isStopped = true; - this.interrupt(); //break pool thread out of dequeue() call. + this.interrupt(); //break pool thread out of dequeue() call,可以令waiting状态的线程抛出异常从而跳出 } public synchronized boolean isStopped(){ From 0738eb4a60d14ef6af37817e31c50d7f5c2bf448 Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Tue, 27 Jun 2017 00:49:46 +0800 Subject: [PATCH 53/73] =?UTF-8?q?=E6=8A=95=E9=AA=B0=E5=AD=90-=E4=BB=A3?= =?UTF-8?q?=E7=A0=81=E9=83=A8=E5=88=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- students/812350401/pom.xml | 7 ++- .../java/com/coderising/ood/uml/Dice.java | 17 +++++++ .../java/com/coderising/ood/uml/DiceGame.java | 44 +++++++++++++++++++ .../java/com/coderising/ood/uml/GameTest.java | 15 +++++++ .../java/com/coderising/ood/uml/Player.java | 23 ++++++++++ 5 files changed, 105 insertions(+), 1 deletion(-) create mode 100644 students/812350401/src/main/java/com/coderising/ood/uml/Dice.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java create mode 100644 students/812350401/src/main/java/com/coderising/ood/uml/Player.java diff --git a/students/812350401/pom.xml b/students/812350401/pom.xml index 9a28365d2a..8f2f890209 100644 --- a/students/812350401/pom.xml +++ b/students/812350401/pom.xml @@ -34,7 +34,12 @@ junit 4.12 - + + com.google.collections + google-collections + 1.0 + + diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java b/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java new file mode 100644 index 0000000000..a6b49c7edf --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java @@ -0,0 +1,17 @@ +package com.coderising.ood.uml; + +import com.google.common.collect.ImmutableList; + +import java.util.Random; + +/** + * Created by thomas_young on 27/6/2017. + */ +public class Dice { + + private ImmutableList values = ImmutableList.of(0, 1, 2, 3, 4, 5, 6); + + public int roll() { + return values.get(new Random().nextInt(values.size())); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java b/students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java new file mode 100644 index 0000000000..afa322f909 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java @@ -0,0 +1,44 @@ +package com.coderising.ood.uml; + +/** + * Created by thomas_young on 27/6/2017. + */ +public class DiceGame { + private Player player1, player2; + private Dice dice1, dice2; + private static int WIN_POINT = 7; + + public void start() { + assert player1 != null; + assert player2 != null; + assert dice1 != null; + assert dice2 != null; + int player1Point; + int player2Point; + do { + player1Point = player1.roll(dice1, dice2); + player2Point = player2.roll(dice1, dice2); + System.out.print(player1 + " roll " + player1Point + ", "); + System.out.println(player2 + " roll " + player2Point + "."); + if (player1Point == player2Point) { + continue; + } + if (player1Point == WIN_POINT) { + System.out.println(player1 + " win!"); + break; + } + if (player2Point == WIN_POINT) { + System.out.println(player2 + " win!"); + break; + } + } while (true); + } + + public DiceGame(Player aPlayer1, Player aPlayer2, Dice aDice1, Dice aDice2) { + player1 = aPlayer1; + player2 = aPlayer2; + dice1 = aDice1; + dice2 = aDice2; + } + +} diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java b/students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java new file mode 100644 index 0000000000..75906c3661 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java @@ -0,0 +1,15 @@ +package com.coderising.ood.uml; + +/** + * Created by thomas_young on 27/6/2017. + */ +public class GameTest { + public static void main(String[] args) { + Player player1 = new Player("player1"); + Player player2 = new Player("player2"); + Dice dice1 = new Dice(); + Dice dice2 = new Dice(); + DiceGame game = new DiceGame(player1, player2, dice1, dice2); + game.start(); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/Player.java b/students/812350401/src/main/java/com/coderising/ood/uml/Player.java new file mode 100644 index 0000000000..c51d5e0868 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/ood/uml/Player.java @@ -0,0 +1,23 @@ +package com.coderising.ood.uml; + +/** + * Created by thomas_young on 27/6/2017. + */ +public class Player { + private String name; + + public Player(String name) { + this.name = name; + } + + @Override + public String toString() { + return name; + } + + public int roll(Dice dice1, Dice dice2) { + int first = dice1.roll(); + int second = dice2.roll(); + return first + second; + } +} From 2e94530b6620f2650ad010d509263c5ab3747ee9 Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Tue, 27 Jun 2017 00:51:32 +0800 Subject: [PATCH 54/73] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E9=AA=B0=E5=AD=90?= =?UTF-8?q?=E7=9A=84=E7=82=B9=E6=95=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../812350401/src/main/java/com/coderising/ood/uml/Dice.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java b/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java index a6b49c7edf..b805b44d68 100644 --- a/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java +++ b/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java @@ -9,7 +9,7 @@ */ public class Dice { - private ImmutableList values = ImmutableList.of(0, 1, 2, 3, 4, 5, 6); + private ImmutableList values = ImmutableList.of(1, 2, 3, 4, 5, 6); public int roll() { return values.get(new Random().nextInt(values.size())); From 68400304da7ea5ba0a7a046099690ba79ce43348 Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Tue, 27 Jun 2017 07:43:35 +0800 Subject: [PATCH 55/73] =?UTF-8?q?=E6=8A=95=E9=AA=B0=E5=AD=90uml=E5=9B=BE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...20\346\227\266\345\272\217\345\233\276.png" | Bin 0 -> 137601 bytes ...60\345\255\220\347\261\273\345\233\276.png" | Bin 0 -> 102615 bytes 2 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 "students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" create mode 100644 "students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" new file mode 100644 index 0000000000000000000000000000000000000000..578894269daf55c28a5e15c719f441d3d405c262 GIT binary patch literal 137601 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

E%}X^-6}dkjKfljCI(OB1 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 Y)Ix<}mpET8_}|90Th~OdvN-vF07zcKr2qf` literal 0 HcmV?d00001 diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" new file mode 100644 index 0000000000000000000000000000000000000000..4973c14277ba5c597fc3c8ce49914e5660595602 GIT binary patch literal 102615 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 z z{gdH)20ctMBiq2%jkZy-XdC+@k#A%U?D4(4kmKe=vZi-jAf^I&Wu^ETG&^W$m2lKe zH{qOB>C|b2&8Jt-p6wXyi6qWpP1ijgOAvO!k9zUNemBLt9)gaj9ze70;^?GifYAsP zuq`u@@nc`GLpd*~IU+!(*ip&mbC;#{bk`mjQx{YO7cSyt&n+iy2a6rUg>6Oc{2EKrKfM-mkPVNz0e?t}1zauG1@@s}jO zPsr@vk3rok(jK3@N>BL!{}uG(zZMo*&aVn=;-8H%)Fm1e7smXEr0k%qvTP72Jo%@r zPByH4OrO(_&tA{?Zq4Sn6F+7CRb+9bb8*uzsgRyZYCDx%X z1(gF2o{L8QIJa+`rWh2TQ#r0ELrHBfj_JjDJW&Vrcc^Hy&j6@G@) z50p)%KJuTK9Cmurc4*r)d3VhSu`?vC+WqQu0wcbWNuCTIDBpR_ZRK+P@>oO5i?S#5 z{59(k=SNU&!~BAyhABO*M2`!X{HQ^;Gzzt#wIDQs0GJbDM2X8UpwHkQf-!3(DCvaA zT^3A?PWbsT$g5)6qV91=){!T#YQ7WyGr0%&i``PS|-MfX_^o-aI~)Z(Kq3YFYzHL zjx&L;_s)Ts|9CFDQKR}!?IH(Z-n%g4EzZreszk! z{z5bOn2Kp^fWj>KA#lRq6KjwNeB(i}?HQa?3;>3A5RA;E$gLXzha^X^3T@$c_4o8pC`>_@;?-Kh5dKx=vSWiA&@3J^5D3ZQ%e2ULb%`}g zDI#2HjeWlKu1C0pKdCHLx*-Hu@{PI_J50TF8>&I=Ai9=DsHIyQZ3u&PWosS;%z6-7qY| zw=46aCAtOGB{2hS0P$Ql!Xelv6*O>mV*w?KAH)%*S`9~d&sTPUTpf=UqVJR&Cr%RBks)ZiOs|ZZG>D6;c7Nn8ix6@;SoH&QG67lj1qT z)%wLIT|Ts$xu53QsV?c*4+9|G|A0GS6u@#ZS$Q5n;c0I?^C^3J(MWar!exF+`nP&W N`T0_Os`o|z{4Z`k3Hbm3 literal 0 HcmV?d00001 From cf5b22c11b309ea06270ef5404c4814421dfaa8c Mon Sep 17 00:00:00 2001 From: sheng <1158154002@qq.com> Date: Tue, 27 Jun 2017 08:10:47 +0800 Subject: [PATCH 56/73] uml homework01 --- dicegame.png | Bin 0 -> 15130 bytes shopping.png | Bin 0 -> 12840 bytes 2 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 dicegame.png create mode 100644 shopping.png diff --git a/dicegame.png b/dicegame.png new file mode 100644 index 0000000000000000000000000000000000000000..1c1a40821ae9979ac0ab745a54fde3b2c9a462a7 GIT binary patch literal 15130 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 literal 0 HcmV?d00001 diff --git a/shopping.png b/shopping.png new file mode 100644 index 0000000000000000000000000000000000000000..6ef672f5f9b500242c3cf915dafc8d3ba40e84ee GIT binary patch literal 12840 zcmeHuc{r49*!RtZWGg+9h>{_DQ6!?0FhgqWI~hs|S+W~SRMue-vOQU|hKKA^3S+X3 z7P4p0Hul|o*RAJy-}m{x<2&AezvKAcKQhOC-RE`Q*L7akd7i&>>G{nY>TCy&9e^N+ zO;h6<27(xFLJFgu*y|2msbe)Akjp3+2;=)?nV(gzz-YeIvoV1U7=S259c(7m>?*C zk$D?Dbesqj06)is{%6wvQ-U}{#>v}qLQpZ!54R!A)orrN1qd2C>^6E?D68m%2sp9< zjZ^G{Qt8`STD79OPAz&6WaYQ%v~Hm}Y$G$mpwJPd1+JgL>)GIz1cV*n9bJ$Mv6}t$oYnToJKJYNM#p+s|OiHDD(b^*E1&()yFVmJYXa) zts%G(skMgb4>L26)(1Ee5@lqT@g=Aavo{dQf9#QT z;5&`nla+4;kw7wxZ0BYyD9+Vh7b--+O(&i@*HP^B{DT^*l{9-q6zIm|t5 zxE8g#leL`0%LNlK`T>HHB3J>#I^`Rrkn8@I%dHQ{K<%6(vv?kf<{H9^D10~3IzHN) z0jR6h<9`q1IK3*ky=lAKYZGghat1L;@f&ntWyfV_bQb3ppRWzhr@sBDtk}e|ZR+MJ zrmli3WrK(n9cLSM3EPhdv!C<=RYVtt+UMubHVN#C$c$X@ip#_?Ml~GRmW7pn5Y@!G zrMuXBtDIYwbvrvvd1WCs=}9Q5Ri10T+NiE^(On(hNL?h6<2PA+l-|*ef;u8iZo`Ke zs7t`u{_SEFWc_hlpR*Oa8MMJ%O6$uV?w!!=Za#N%Ag#uGqI&-R&ZGJOoIlM%YRvw9 zV}vfvIn8_j6D5_Li4#Ds#P5gJt>aNarV7;WZjIzPS23?_cK4#(|m*WP$h+t94Bay9;Hj94V^nuiyr z^7A2{-TeHYnO(Q{gHxypCvsHl3HIG8w_IJDIJm!Ep|&kkRX;jR>gKmwWhHK(KU+6p z8)I4PCq(FX4ulPQ2z8!%4^N5HRzHfh?<7J)&l9`5J~5 zuJczgiY~kq5AjmbER}oZ{Oavp%4g#@yzQ%DL=~}^IN4fZzg1-^jh%gAyjbJR1_^Hc%8Xl%W?%V=$fQLCk<;})K`oxMxONg+O=`o?

xvJxqg))u90|)nJRBX0jeA^G$v)Sf=w{* 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 Date: Wed, 28 Jun 2017 00:42:46 +0800 Subject: [PATCH 57/73] =?UTF-8?q?=E8=B4=AD=E7=89=A9=E7=BD=91=E7=AB=99?= =?UTF-8?q?=E7=94=A8=E4=BE=8B=E5=9B=BE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...31\347\224\250\344\276\213\345\233\276.png" | Bin 0 -> 216240 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 "students/812350401/src/main/java/com/coderising/ood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/ood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" new file mode 100644 index 0000000000000000000000000000000000000000..46addc04089fc81cb0a967f5118884f08c5c1dfb GIT binary patch literal 216240 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³vn+m^7ihl?xC|Wn$6`8BaXx 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 mh~tNr)$2uS9^6I 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 Date: Wed, 28 Jun 2017 00:52:46 +0800 Subject: [PATCH 58/73] =?UTF-8?q?=E6=94=BE=E5=A4=A7=E7=B1=BB=E5=9B=BE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...0\345\255\220\347\261\273\345\233\276.png" | Bin 102615 -> 285103 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" index 4973c14277ba5c597fc3c8ce49914e5660595602..587726bd6182f3d7d9c983eb94876e6a78180bda 100644 GIT binary patch literal 285103 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

Ay`etk5flv=d%*pJ`z5@s;SB5}ZBb{p;`$+vbWX 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 z z{gdH)20ctMBiq2%jkZy-XdC+@k#A%U?D4(4kmKe=vZi-jAf^I&Wu^ETG&^W$m2lKe zH{qOB>C|b2&8Jt-p6wXyi6qWpP1ijgOAvO!k9zUNemBLt9)gaj9ze70;^?GifYAsP zuq`u@@nc`GLpd*~IU+!(*ip&mbC;#{bk`mjQx{YO7cSyt&n+iy2a6rUg>6Oc{2EKrKfM-mkPVNz0e?t}1zauG1@@s}jO zPsr@vk3rok(jK3@N>BL!{}uG(zZMo*&aVn=;-8H%)Fm1e7smXEr0k%qvTP72Jo%@r zPByH4OrO(_&tA{?Zq4Sn6F+7CRb+9bb8*uzsgRyZYCDx%X z1(gF2o{L8QIJa+`rWh2TQ#r0ELrHBfj_JjDJW&Vrcc^Hy&j6@G@) z50p)%KJuTK9Cmurc4*r)d3VhSu`?vC+WqQu0wcbWNuCTIDBpR_ZRK+P@>oO5i?S#5 z{59(k=SNU&!~BAyhABO*M2`!X{HQ^;Gzzt#wIDQs0GJbDM2X8UpwHkQf-!3(DCvaA zT^3A?PWbsT$g5)6qV91=){!T#YQ7WyGr0%&i``PS|-MfX_^o-aI~)Z(Kq3YFYzHL zjx&L;_s)Ts|9CFDQKR}!?IH(Z-n%g4EzZreszk! z{z5bOn2Kp^fWj>KA#lRq6KjwNeB(i}?HQa?3;>3A5RA;E$gLXzha^X^3T@$c_4o8pC`>_@;?-Kh5dKx=vSWiA&@3J^5D3ZQ%e2ULb%`}g zDI#2HjeWlKu1C0pKdCHLx*-Hu@{PI_J50TF8>&I=Ai9=DsHIyQZ3u&PWosS;%z6-7qY| zw=46aCAtOGB{2hS0P$Ql!Xelv6*O>mV*w?KAH)%*S`9~d&sTPUTpf=UqVJR&Cr%RBks)ZiOs|ZZG>D6;c7Nn8ix6@;SoH&QG67lj1qT z)%wLIT|Ts$xu53QsV?c*4+9|G|A0GS6u@#ZS$Q5n;c0I?^C^3J(MWar!exF+`nP&W N`T0_Os`o|z{4Z`k3Hbm3 From 6d58113cbc2e545d4542b57105a18d493f577b48 Mon Sep 17 00:00:00 2001 From: eulerlcs Date: Sun, 2 Jul 2017 23:38:39 +0900 Subject: [PATCH 59/73] add regular expression project --- .../2.code/jmr-71-regularexpression/pom.xml | 111 ++++++++++++++++ .../regularexpression/ClassLoaderTree.java | 12 ++ .../eulerlcs/regularexpression/Utils.java | 27 ++++ .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 +++ .../src/test/java/.gitkeep | 0 .../ClassLoaderTreeTest.java | 119 ++++++++++++++++++ .../src/test/resources/.gitkeep | 0 .../src/test/resources/01_01.txt | 5 + 9 files changed, 290 insertions(+) create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/pom.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/.gitkeep create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01_01.txt diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/pom.xml b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/pom.xml new file mode 100644 index 0000000000..86657499f5 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/pom.xml @@ -0,0 +1,111 @@ + + 4.0.0 + com.github.eulerlcs + jmr-71-regularexpression + 0.0.1-SNAPSHOT + eulerlcs regular expression + + + + 1.7.24 + 4.12 + 2.17 + 1.8 + 1.8 + + + + + + org.projectlombok + lombok + 1.16.14 + provided + + + org.slf4j + slf4j-api + ${slf4j.version} + + + org.slf4j + slf4j-log4j12 + ${slf4j.version} + + + junit + junit + ${junit.version} + test + + + + + + + + + org.apache.maven.plugins + maven-source-plugin + 3.0.1 + + + attach-source + + jar-no-fork + + + + + + org.apache.maven.plugins + maven-compiler-plugin + 3.6.1 + + ${maven.compiler.source} + ${maven.compiler.target} + + + + org.apache.maven.plugins + maven-jar-plugin + 3.0.2 + + + org.apache.maven.plugins + maven-javadoc-plugin + 2.10.4 + + true + 1.8 + protected + UTF-8 + UTF-8 + UTF-8 + + + + org.apache.maven.plugins + maven-surefire-plugin + 2.19.1 + + + org.apache.maven.plugins + maven-surefire-report-plugin + 2.19.1 + + true + + + + + + + + org.apache.maven.plugins + maven-source-plugin + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java new file mode 100644 index 0000000000..2ea7809504 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java @@ -0,0 +1,12 @@ +package com.github.eulerlcs.regularexpression; + +public class ClassLoaderTree { + + public static void main(String[] args) { + ClassLoader loader = ClassLoaderTree.class.getClassLoader(); + while (loader != null) { + System.out.println(loader.toString()); + loader = loader.getParent(); + } + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java new file mode 100644 index 0000000000..aa5e45c5ed --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java @@ -0,0 +1,27 @@ +package com.github.eulerlcs.regularexpression; + +import java.io.IOException; +import java.net.URISyntaxException; +import java.nio.charset.StandardCharsets; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; + +public class Utils { + + public static String readAllFromResouce(String resourceName) { + byte[] fileContentBytes; + try { + Path path = Paths.get(ClassLoader.getSystemResource(resourceName).toURI()); + fileContentBytes = Files.readAllBytes(path); + String fileContentStr = new String(fileContentBytes, StandardCharsets.UTF_8); + + return fileContentStr; + } catch (IOException | URISyntaxException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + + return ""; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml new file mode 100644 index 0000000000..831b8d9ce3 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java new file mode 100644 index 0000000000..2e0b955bad --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java @@ -0,0 +1,119 @@ +package com.github.eulerlcs.regularexpression; + +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertTrue; + +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import org.junit.Test; + +public class ClassLoaderTreeTest { + + @Test + public void test01_01() { + String text = Utils.readAllFromResouce("01_01.txt"); + System.out.println("--orignal text start--"); + System.out.print(text); + System.out.println("--orignal text end --"); + + // 统一换行符 + String result = text.replaceAll("(\r\n)|\r", "\n"); + System.out.println("--统一换行符 start--"); + System.out.print(result); + System.out.println("--统一换行符 end --"); + + // 行单位前后trim + result = result.replaceAll("(?m)^\\s*(.*?)\\s*$", "$1"); + System.out.println("--行单位前后trim start--"); + System.out.print(result); + System.out.println("--行单位前后trim end --"); + + assertFalse(result.equals(text)); + } + + @Test + public void test01_02() { + + // ^ $ \A \E (?m) + String text = "123\r\nabc def"; + String regex = "\\Aabc"; + // Pattern p = Pattern.compile(regex); + Pattern p = Pattern.compile(regex, Pattern.MULTILINE); + + Matcher m = p.matcher(text); + + boolean result = m.find(); + if (result) { + System.out.println("found"); + } else { + System.out.println("not found"); + } + assertTrue(result); + } + + @Test + public void test01_03_dotall() { + Pattern p = null; + Matcher m = null; + + String text1 = "width height"; + String text2 = "width\nheight"; + // Pattern p = Pattern.compile("(?s)width.height"); + p = Pattern.compile("width.height", Pattern.DOTALL); + + m = p.matcher(text1); + boolean result1 = m.find(); + + m = p.matcher(text2); + boolean result2 = m.find(); + if (result2) { + System.out.println("found"); + } else { + System.out.println("not found"); + } + + assertTrue(result1); + assertTrue(result2); + } + + @Test + public void test01_04_Zz() { + Pattern p = null; + Matcher m = null; + boolean result1 = false; + boolean result2 = false; + boolean result3 = false; + + String text1 = "abc def"; + String text2 = "def abc"; + String text3 = "def abc\n"; + + p = Pattern.compile("abc\\z"); + + m = p.matcher(text1); + result1 = m.find(); + + m = p.matcher(text2); + result2 = m.find(); + + m = p.matcher(text3); + result3 = m.find(); + + p = Pattern.compile("abc\\Z"); + + m = p.matcher(text1); + result1 = m.find(); + + m = p.matcher(text2); + result2 = m.find(); + + m = p.matcher(text3); + result3 = m.find(); + + assertFalse(result1); + assertTrue(result2); + assertTrue(result3); + } + +} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01_01.txt b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01_01.txt new file mode 100644 index 0000000000..be72da22ea --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01_01.txt @@ -0,0 +1,5 @@ + abc +def + +gh + From e01d178dc45c21efd306d77f6d75c57cf6a55e3a Mon Sep 17 00:00:00 2001 From: yangzhm Date: Tue, 4 Jul 2017 21:02:12 +0800 Subject: [PATCH 60/73] add project of payment --- .../payment/src/Affiliation/Affiliation.java | 7 ++++ .../src/Affiliation/NonAffiliation.java | 12 ++++++ .../src/Affiliation/ServiceCharge.java | 20 +++++++++ .../src/Affiliation/UnionAffiliation.java | 27 ++++++++++++ .../OOD/payment/src/DateUtil/DateUtil.java | 37 +++++++++++++++++ .../OOD/payment/src/Employ/Employee.java | 41 +++++++++++++++++++ .../OOD/payment/src/PayCheck/PayCheck.java | 36 ++++++++++++++++ .../CommissionClassification.java | 23 +++++++++++ .../HourlyClassification.java | 38 +++++++++++++++++ .../PaymentClassification.java | 7 ++++ .../SalariedClassification.java | 12 ++++++ .../PaymentClassification/SalesReceipt.java | 20 +++++++++ .../src/PaymentClassification/TimeCard.java | 21 ++++++++++ .../payment/src/PaymentMethod/BankMethod.java | 13 ++++++ .../payment/src/PaymentMethod/HoldMethod.java | 13 ++++++ .../payment/src/PaymentMethod/MailMethod.java | 13 ++++++ .../src/PaymentMethod/PaymentMethod.java | 7 ++++ .../src/PaymentSchedule/BiWeeklySchedule.java | 19 +++++++++ .../src/PaymentSchedule/MothlySchedule.java | 19 +++++++++ .../src/PaymentSchedule/PaymentSchedule.java | 10 +++++ .../src/PaymentSchedule/WeeklySchedule.java | 18 ++++++++ 21 files changed, 413 insertions(+) create mode 100644 students/495232796/OOD/payment/src/Affiliation/Affiliation.java create mode 100644 students/495232796/OOD/payment/src/Affiliation/NonAffiliation.java create mode 100644 students/495232796/OOD/payment/src/Affiliation/ServiceCharge.java create mode 100644 students/495232796/OOD/payment/src/Affiliation/UnionAffiliation.java create mode 100644 students/495232796/OOD/payment/src/DateUtil/DateUtil.java create mode 100644 students/495232796/OOD/payment/src/Employ/Employee.java create mode 100644 students/495232796/OOD/payment/src/PayCheck/PayCheck.java create mode 100644 students/495232796/OOD/payment/src/PaymentClassification/CommissionClassification.java create mode 100644 students/495232796/OOD/payment/src/PaymentClassification/HourlyClassification.java create mode 100644 students/495232796/OOD/payment/src/PaymentClassification/PaymentClassification.java create mode 100644 students/495232796/OOD/payment/src/PaymentClassification/SalariedClassification.java create mode 100644 students/495232796/OOD/payment/src/PaymentClassification/SalesReceipt.java create mode 100644 students/495232796/OOD/payment/src/PaymentClassification/TimeCard.java create mode 100644 students/495232796/OOD/payment/src/PaymentMethod/BankMethod.java create mode 100644 students/495232796/OOD/payment/src/PaymentMethod/HoldMethod.java create mode 100644 students/495232796/OOD/payment/src/PaymentMethod/MailMethod.java create mode 100644 students/495232796/OOD/payment/src/PaymentMethod/PaymentMethod.java create mode 100644 students/495232796/OOD/payment/src/PaymentSchedule/BiWeeklySchedule.java create mode 100644 students/495232796/OOD/payment/src/PaymentSchedule/MothlySchedule.java create mode 100644 students/495232796/OOD/payment/src/PaymentSchedule/PaymentSchedule.java create mode 100644 students/495232796/OOD/payment/src/PaymentSchedule/WeeklySchedule.java diff --git a/students/495232796/OOD/payment/src/Affiliation/Affiliation.java b/students/495232796/OOD/payment/src/Affiliation/Affiliation.java new file mode 100644 index 0000000000..5e2dac8fa0 --- /dev/null +++ b/students/495232796/OOD/payment/src/Affiliation/Affiliation.java @@ -0,0 +1,7 @@ +package Affiliation; + +import PayCheck.PayCheck; + +public abstract class Affiliation { + public abstract double calculateDeduction(PayCheck pc); +} diff --git a/students/495232796/OOD/payment/src/Affiliation/NonAffiliation.java b/students/495232796/OOD/payment/src/Affiliation/NonAffiliation.java new file mode 100644 index 0000000000..d37c1e35ff --- /dev/null +++ b/students/495232796/OOD/payment/src/Affiliation/NonAffiliation.java @@ -0,0 +1,12 @@ +package Affiliation; + +import PayCheck.PayCheck; + +public class NonAffiliation extends Affiliation{ + + @Override + public double calculateDeduction(PayCheck pc) { + return 0.0; + } + +} diff --git a/students/495232796/OOD/payment/src/Affiliation/ServiceCharge.java b/students/495232796/OOD/payment/src/Affiliation/ServiceCharge.java new file mode 100644 index 0000000000..a7faa67adb --- /dev/null +++ b/students/495232796/OOD/payment/src/Affiliation/ServiceCharge.java @@ -0,0 +1,20 @@ +package Affiliation; + +import java.util.Date; + +public class ServiceCharge { + private Date date; + private double amount; + public double getAmount() { + return amount; + } + public void setAmount(double amount) { + this.amount = amount; + } + public Date getDate() { + return date; + } + public void setDate(Date date) { + this.date = date; + } +} diff --git a/students/495232796/OOD/payment/src/Affiliation/UnionAffiliation.java b/students/495232796/OOD/payment/src/Affiliation/UnionAffiliation.java new file mode 100644 index 0000000000..02e645ef1f --- /dev/null +++ b/students/495232796/OOD/payment/src/Affiliation/UnionAffiliation.java @@ -0,0 +1,27 @@ +package Affiliation; + +import java.util.Date; +import java.util.Map; + +import PayCheck.PayCheck; +import DateUtil.DateUtil; + +public class UnionAffiliation extends Affiliation{ + private String memId; + private double weeklyDue; + private Map serviceCharges; + @Override + public double calculateDeduction(PayCheck pc) { + int fridays = DateUtil.getFridays(pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate()); + double totalDue = fridays*this.weeklyDue; + + double totalCharges = 0.0; + for (ServiceCharge sc : serviceCharges.values()) { + if (DateUtil.between(sc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + totalCharges += sc.getAmount(); + } + } + return totalDue+totalCharges; + } + +} diff --git a/students/495232796/OOD/payment/src/DateUtil/DateUtil.java b/students/495232796/OOD/payment/src/DateUtil/DateUtil.java new file mode 100644 index 0000000000..6ed884bfa8 --- /dev/null +++ b/students/495232796/OOD/payment/src/DateUtil/DateUtil.java @@ -0,0 +1,37 @@ +package DateUtil; + +import java.util.Date; + +public class DateUtil { + public static boolean isFriday(Date d) { + return true; + } + + public static Date add(Date d, int days) { + return new Date(); + } + + public static boolean isLastDayofMonth(Date d) { + return false; + } + + public static Date getFirstDay(Date d) { + return new Date(); + } + + public static long getDaysBetween(Date start, Date end) { + return 0; + } + + public static Date parseDay(String dayStr) { + return new Date(); + } + + public static boolean between(Date d, Date start, Date end) { + return true; + } + + public static int getFridays(Date start, Date end) { + return 0; + } +} diff --git a/students/495232796/OOD/payment/src/Employ/Employee.java b/students/495232796/OOD/payment/src/Employ/Employee.java new file mode 100644 index 0000000000..b21eec7869 --- /dev/null +++ b/students/495232796/OOD/payment/src/Employ/Employee.java @@ -0,0 +1,41 @@ +package Employ; + +import java.util.Date; + +import Affiliation.Affiliation; +import PayCheck.PayCheck; +import PaymentClassification.PaymentClassification; +import PaymentMethod.PaymentMethod; +import PaymentSchedule.PaymentSchedule; + +public class Employee { + private String id; + private String name; + private String address; + PaymentClassification payment; + PaymentSchedule paySch; + PaymentMethod payMethod; + Affiliation af; + + public Employee(String name, String address) { + this.name = name; + this.address = address; + } + public boolean isPayDay(Date d) { + return this.paySch.isPayDay(d); + } + + public Date getPayPeriodStartDate(Date d) { + return this.paySch.getPayPeriodStartDate(d); + } + + public void payDay(PayCheck pc) { + double grossPay = payment.calculatePay(pc); + double dedutions = af.calculateDeduction(pc); + double netPay = grossPay - dedutions; + pc.setGrossPay(grossPay); + pc.setDeductions(dedutions); + pc.setNetPay(netPay); + payMethod.pay(pc); + } +} diff --git a/students/495232796/OOD/payment/src/PayCheck/PayCheck.java b/students/495232796/OOD/payment/src/PayCheck/PayCheck.java new file mode 100644 index 0000000000..ceea1e41fe --- /dev/null +++ b/students/495232796/OOD/payment/src/PayCheck/PayCheck.java @@ -0,0 +1,36 @@ +package PayCheck; + +import java.util.Date; + +public class PayCheck { + private int payPeriodStart; + private int payPeriodEnd; + private double grossPay; + private double deductions; + private double netPay; + public double getGrossPay() { + return grossPay; + } + public void setGrossPay(double grossPay) { + this.grossPay = grossPay; + } + public double getDeductions() { + return deductions; + } + public void setDeductions(double deductions) { + this.deductions = deductions; + } + public double getNetPay() { + return netPay; + } + public void setNetPay(double netPay) { + this.netPay = netPay; + } + + public Date getPayPeriodStartDate() { + return new Date(); + } + public Date getPayPeriodEndDate() { + return new Date(); + } +} diff --git a/students/495232796/OOD/payment/src/PaymentClassification/CommissionClassification.java b/students/495232796/OOD/payment/src/PaymentClassification/CommissionClassification.java new file mode 100644 index 0000000000..e1b9edab23 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentClassification/CommissionClassification.java @@ -0,0 +1,23 @@ +package PaymentClassification; + +import java.util.Date; +import java.util.Map; + +import PayCheck.PayCheck; +import DateUtil.DateUtil; + +public class CommissionClassification extends PaymentClassification{ + private double rate = 0.0; + private double salary = 0.0; + private Map receipts; + @Override + public double calculatePay(PayCheck pc) { + double commission = 0.0; + for (SalesReceipt sr : receipts.values()) { + if (DateUtil.between(sr.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + commission += sr.getAmount()*rate; + } + } + return commission+salary; + } +} diff --git a/students/495232796/OOD/payment/src/PaymentClassification/HourlyClassification.java b/students/495232796/OOD/payment/src/PaymentClassification/HourlyClassification.java new file mode 100644 index 0000000000..00ae430777 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentClassification/HourlyClassification.java @@ -0,0 +1,38 @@ +package PaymentClassification; + +import java.util.Date; +import java.util.Map; + +import DateUtil.DateUtil; +import PayCheck.PayCheck; + +public class HourlyClassification extends PaymentClassification{ + private double hourlyRate = 0.0; + private Map timeCards; + + public void addTimeCard(TimeCard tc) { + timeCards.put(tc.getDate(), tc); + } + + @Override + public double calculatePay(PayCheck pc) { + double total = 0.0; + + for (TimeCard tc : timeCards.values()) { + if (DateUtil.between(tc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + total += calculatePayForTimeCard(tc); + } + } + + return total; + } + + private double calculatePayForTimeCard(TimeCard tc) { + int hours = tc.getHours(); + if (hours > 8) { + return 8*this.hourlyRate + (hours - 8)*this.hourlyRate*1.5; + } else { + return 8*this.hourlyRate; + } + } +} diff --git a/students/495232796/OOD/payment/src/PaymentClassification/PaymentClassification.java b/students/495232796/OOD/payment/src/PaymentClassification/PaymentClassification.java new file mode 100644 index 0000000000..f9b06d744f --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentClassification/PaymentClassification.java @@ -0,0 +1,7 @@ +package PaymentClassification; + +import PayCheck.PayCheck; + +public abstract class PaymentClassification { + public abstract double calculatePay(PayCheck pc); +} diff --git a/students/495232796/OOD/payment/src/PaymentClassification/SalariedClassification.java b/students/495232796/OOD/payment/src/PaymentClassification/SalariedClassification.java new file mode 100644 index 0000000000..941bde9869 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentClassification/SalariedClassification.java @@ -0,0 +1,12 @@ +package PaymentClassification; + +import PayCheck.PayCheck; + +public class SalariedClassification extends PaymentClassification { + private double salary = 0.0; + + @Override + public double calculatePay(PayCheck pc) { + return salary; + } +} diff --git a/students/495232796/OOD/payment/src/PaymentClassification/SalesReceipt.java b/students/495232796/OOD/payment/src/PaymentClassification/SalesReceipt.java new file mode 100644 index 0000000000..a9f07140bd --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentClassification/SalesReceipt.java @@ -0,0 +1,20 @@ +package PaymentClassification; + +import java.util.Date; + +public class SalesReceipt { + private Date date; + private double amount; + public Date getDate() { + return date; + } + public void setDate(Date date) { + this.date = date; + } + public double getAmount() { + return amount; + } + public void setAmount(double amount) { + this.amount = amount; + } +} diff --git a/students/495232796/OOD/payment/src/PaymentClassification/TimeCard.java b/students/495232796/OOD/payment/src/PaymentClassification/TimeCard.java new file mode 100644 index 0000000000..e4396ee603 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentClassification/TimeCard.java @@ -0,0 +1,21 @@ +package PaymentClassification; + +import java.util.Date; + +public class TimeCard { + private Date date; + private int startTime; + private int endTime; + + public Date getDate() { + return date; + } + public void setDate(Date date) { + this.date = date; + } + + public int getHours() { + return endTime - startTime; + } + +} diff --git a/students/495232796/OOD/payment/src/PaymentMethod/BankMethod.java b/students/495232796/OOD/payment/src/PaymentMethod/BankMethod.java new file mode 100644 index 0000000000..1ef31f13ba --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentMethod/BankMethod.java @@ -0,0 +1,13 @@ +package PaymentMethod; + +import PayCheck.PayCheck; + +public class BankMethod extends PaymentMethod{ + private String bank; + private double account; + @Override + public void pay(PayCheck pc) { + // TODO Auto-generated method stub + + } +} diff --git a/students/495232796/OOD/payment/src/PaymentMethod/HoldMethod.java b/students/495232796/OOD/payment/src/PaymentMethod/HoldMethod.java new file mode 100644 index 0000000000..62d9b4439c --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentMethod/HoldMethod.java @@ -0,0 +1,13 @@ +package PaymentMethod; + +import PayCheck.PayCheck; + +public class HoldMethod extends PaymentMethod{ + + @Override + public void pay(PayCheck pc) { + // TODO Auto-generated method stub + + } + +} diff --git a/students/495232796/OOD/payment/src/PaymentMethod/MailMethod.java b/students/495232796/OOD/payment/src/PaymentMethod/MailMethod.java new file mode 100644 index 0000000000..f8a98e5113 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentMethod/MailMethod.java @@ -0,0 +1,13 @@ +package PaymentMethod; + +import PayCheck.PayCheck; + +public class MailMethod extends PaymentMethod{ + private String address; + + @Override + public void pay(PayCheck pc) { + // TODO Auto-generated method stub + + } +} diff --git a/students/495232796/OOD/payment/src/PaymentMethod/PaymentMethod.java b/students/495232796/OOD/payment/src/PaymentMethod/PaymentMethod.java new file mode 100644 index 0000000000..67093ae1a0 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentMethod/PaymentMethod.java @@ -0,0 +1,7 @@ +package PaymentMethod; + +import PayCheck.PayCheck; + +public abstract class PaymentMethod { + public abstract void pay(PayCheck pc); +} diff --git a/students/495232796/OOD/payment/src/PaymentSchedule/BiWeeklySchedule.java b/students/495232796/OOD/payment/src/PaymentSchedule/BiWeeklySchedule.java new file mode 100644 index 0000000000..ced0eb1d15 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentSchedule/BiWeeklySchedule.java @@ -0,0 +1,19 @@ +package PaymentSchedule; + +import java.util.Date; +import DateUtil.DateUtil; + +public class BiWeeklySchedule implements PaymentSchedule{ + Date firstFriday = DateUtil.parseDay("2017-01-01"); + @Override + public boolean isPayDay(Date date) { + long interval = DateUtil.getDaysBetween(firstFriday, date); + return interval%14 == 0; + } + + @Override + public Date getPayPeriodStartDate(Date date) { + return DateUtil.add(date, -13); + } + +} diff --git a/students/495232796/OOD/payment/src/PaymentSchedule/MothlySchedule.java b/students/495232796/OOD/payment/src/PaymentSchedule/MothlySchedule.java new file mode 100644 index 0000000000..edac34d480 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentSchedule/MothlySchedule.java @@ -0,0 +1,19 @@ +package PaymentSchedule; + +import java.util.Date; + +import DateUtil.DateUtil; + +public class MothlySchedule implements PaymentSchedule{ + + @Override + public boolean isPayDay(Date date) { + return DateUtil.isLastDayofMonth(date); + } + + @Override + public Date getPayPeriodStartDate(Date date) { + return DateUtil.getFirstDay(date); + } + +} diff --git a/students/495232796/OOD/payment/src/PaymentSchedule/PaymentSchedule.java b/students/495232796/OOD/payment/src/PaymentSchedule/PaymentSchedule.java new file mode 100644 index 0000000000..e1dea539f8 --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentSchedule/PaymentSchedule.java @@ -0,0 +1,10 @@ +package PaymentSchedule; + +import java.util.Date; + +public interface PaymentSchedule { + + public boolean isPayDay(Date date); + + public Date getPayPeriodStartDate(Date date); +} diff --git a/students/495232796/OOD/payment/src/PaymentSchedule/WeeklySchedule.java b/students/495232796/OOD/payment/src/PaymentSchedule/WeeklySchedule.java new file mode 100644 index 0000000000..9e8e4dfe9f --- /dev/null +++ b/students/495232796/OOD/payment/src/PaymentSchedule/WeeklySchedule.java @@ -0,0 +1,18 @@ +package PaymentSchedule; + +import java.util.Date; +import DateUtil.DateUtil; + +public class WeeklySchedule implements PaymentSchedule{ + + @Override + public boolean isPayDay(Date date) { + return DateUtil.isFriday(date); + } + + @Override + public Date getPayPeriodStartDate(Date date) { + return DateUtil.add(date, -6); + } + +} From b714cf009cbe6bdec3a38ed4183a30088a675436 Mon Sep 17 00:00:00 2001 From: Thomas Young Date: Tue, 4 Jul 2017 21:46:41 +0800 Subject: [PATCH 61/73] Payroll init --- .../{ood => myood}/ocp/DateUtil.java | 2 +- .../coderising/{ood => myood}/ocp/Logger.java | 2 +- .../{ood => myood}/ocp/MailUtil.java | 2 +- .../{ood => myood}/ocp/SMSUtil.java | 2 +- .../ocp/myocp/DateFormatter.java | 2 +- .../{ood => myood}/ocp/myocp/DateUtil.java | 2 +- .../{ood => myood}/ocp/myocp/EmailSender.java | 2 +- .../{ood => myood}/ocp/myocp/Formatter.java | 2 +- .../ocp/myocp/FormatterFactory.java | 2 +- .../{ood => myood}/ocp/myocp/LogDrive.java | 2 +- .../{ood => myood}/ocp/myocp/LogFactory.java | 2 +- .../{ood => myood}/ocp/myocp/Logger.java | 2 +- .../{ood => myood}/ocp/myocp/MailUtil.java | 2 +- .../{ood => myood}/ocp/myocp/PrintSender.java | 2 +- .../ocp/myocp/RawFormatter.java | 2 +- .../{ood => myood}/ocp/myocp/SMSUtil.java | 2 +- .../{ood => myood}/ocp/myocp/Sender.java | 2 +- .../ocp/myocp/SenderFactory.java | 2 +- .../{ood => myood}/ocp/myocp/SmsSender.java | 2 +- .../coderising/myood/payroll/Affiliation.java | 5 +++ .../coderising/myood/payroll/Employee.java | 42 ++++++++++++++++++ .../coderising/myood/payroll/Paycheck.java | 34 ++++++++++++++ .../myood/payroll/PaymentClassification.java | 5 +++ .../myood/payroll/PaymentMethod.java | 5 +++ .../myood/payroll/PaymentSchedule.java | 8 ++++ .../myood/payroll/SalesReceipt.java | 14 ++++++ .../coderising/myood/payroll/TimeCard.java | 15 +++++++ .../{ood => myood}/srp/Configuration.java | 2 +- .../{ood => myood}/srp/ConfigurationKeys.java | 2 +- .../coderising/{ood => myood}/srp/DBUtil.java | 2 +- .../{ood => myood}/srp/EmailParam.java | 2 +- .../{ood => myood}/srp/MailService.java | 2 +- .../{ood => myood}/srp/MailUtil.java | 2 +- .../{ood => myood}/srp/ProductInfo.java | 4 +- .../coderising/myood/srp/PromotionMail.java | 8 ++++ .../{ood => myood}/srp/UserDao.java | 2 +- .../srp/goodSrp/Configuration.java | 8 ++-- .../srp/goodSrp/ConfigurationKeys.java | 2 +- .../{ood => myood}/srp/goodSrp/DBUtil.java | 2 +- .../{ood => myood}/srp/goodSrp/Mail.java | 6 +-- .../srp/goodSrp/MailSender.java | 2 +- .../{ood => myood}/srp/goodSrp/MailUtil.java | 2 +- .../{ood => myood}/srp/goodSrp/Product.java | 2 +- .../srp/goodSrp/ProductService.java | 4 +- .../srp/goodSrp/PromotionJob.java | 2 +- .../{ood => myood}/srp/goodSrp/User.java | 2 +- .../srp/goodSrp/UserService.java | 2 +- .../goodSrp/template/MailBodyTemplate.java | 2 +- .../template/TextMailBodyTemplate.java | 2 +- .../{ood => myood}/srp/product_promotion.txt | 0 .../coderising/{ood => myood}/uml/Dice.java | 2 +- .../{ood => myood}/uml/DiceGame.java | 2 +- .../{ood => myood}/uml/GameTest.java | 2 +- .../coderising/{ood => myood}/uml/Player.java | 2 +- ...0\346\227\266\345\272\217\345\233\276.png" | Bin ...0\345\255\220\347\261\273\345\233\276.png" | Bin ...1\347\224\250\344\276\213\345\233\276.png" | Bin .../com/coderising/ood/srp/PromotionMail.java | 17 ------- 58 files changed, 187 insertions(+), 68 deletions(-) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/DateUtil.java (69%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/Logger.java (91%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/MailUtil.java (77%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/SMSUtil.java (76%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/DateFormatter.java (86%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/DateUtil.java (84%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/EmailSender.java (81%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/Formatter.java (73%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/FormatterFactory.java (93%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/LogDrive.java (90%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/LogFactory.java (91%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/Logger.java (82%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/MailUtil.java (75%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/PrintSender.java (82%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/RawFormatter.java (81%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/SMSUtil.java (74%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/Sender.java (72%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/SenderFactory.java (94%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/ocp/myocp/SmsSender.java (81%) create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/Affiliation.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/Employee.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/Paycheck.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/PaymentClassification.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/PaymentMethod.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/PaymentSchedule.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/SalesReceipt.java create mode 100644 students/812350401/src/main/java/com/coderising/myood/payroll/TimeCard.java rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/Configuration.java (94%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/ConfigurationKeys.java (86%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/DBUtil.java (93%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/EmailParam.java (96%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/MailService.java (99%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/MailUtil.java (93%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/ProductInfo.java (94%) create mode 100644 students/812350401/src/main/java/com/coderising/myood/srp/PromotionMail.java rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/UserDao.java (94%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/Configuration.java (60%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/ConfigurationKeys.java (83%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/DBUtil.java (92%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/Mail.java (79%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/MailSender.java (96%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/MailUtil.java (92%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/Product.java (90%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/ProductService.java (91%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/PromotionJob.java (93%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/User.java (95%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/UserService.java (94%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/template/MailBodyTemplate.java (52%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/goodSrp/template/TextMailBodyTemplate.java (90%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/srp/product_promotion.txt (100%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/uml/Dice.java (90%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/uml/DiceGame.java (97%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/uml/GameTest.java (91%) rename students/812350401/src/main/java/com/coderising/{ood => myood}/uml/Player.java (92%) rename "students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" => "students/812350401/src/main/java/com/coderising/myood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" (100%) rename "students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" => "students/812350401/src/main/java/com/coderising/myood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" (100%) rename "students/812350401/src/main/java/com/coderising/ood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" => "students/812350401/src/main/java/com/coderising/myood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" (100%) delete mode 100644 students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java b/students/812350401/src/main/java/com/coderising/myood/ocp/DateUtil.java similarity index 69% rename from students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/DateUtil.java index 0d0d01098f..d8997edc1f 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/DateUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/DateUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp; +package com.coderising.myood.ocp; public class DateUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java b/students/812350401/src/main/java/com/coderising/myood/ocp/Logger.java similarity index 91% rename from students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/Logger.java index aca173e665..1cdaba8482 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/Logger.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/Logger.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp; +package com.coderising.myood.ocp; public class Logger { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java b/students/812350401/src/main/java/com/coderising/myood/ocp/MailUtil.java similarity index 77% rename from students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/MailUtil.java index 88cd252cf4..3c1fcb650c 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/MailUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp; +package com.coderising.myood.ocp; public class MailUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java b/students/812350401/src/main/java/com/coderising/myood/ocp/SMSUtil.java similarity index 76% rename from students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/SMSUtil.java index 8e955ab085..f91558bfbf 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/SMSUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/SMSUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp; +package com.coderising.myood.ocp; public class SMSUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateFormatter.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/DateFormatter.java similarity index 86% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateFormatter.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/DateFormatter.java index b9c3f7b026..3e5145409a 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateFormatter.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/DateFormatter.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/DateUtil.java similarity index 84% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/DateUtil.java index d207c1d3c0..5f14aee788 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/DateUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/DateUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; import java.text.SimpleDateFormat; import java.util.Date; diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailSender.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/EmailSender.java similarity index 81% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailSender.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/EmailSender.java index bc91dc2d58..7ce76f3563 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/EmailSender.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/EmailSender.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Formatter.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Formatter.java similarity index 73% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Formatter.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Formatter.java index c831fcb369..4bca0709d4 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Formatter.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Formatter.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/FormatterFactory.java similarity index 93% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/FormatterFactory.java index 6c08688f5f..ab085a9022 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/FormatterFactory.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/FormatterFactory.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; public class FormatterFactory { public final int RAW_LOG = 1; diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/LogDrive.java similarity index 90% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/LogDrive.java index f0f8f3cf1e..c18bbd588a 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogDrive.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/LogDrive.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/LogFactory.java similarity index 91% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/LogFactory.java index 63b2d1b8e4..056243c17f 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/LogFactory.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/LogFactory.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Logger.java similarity index 82% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Logger.java index 94cbab377c..0a410f1350 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Logger.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Logger.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; public class Logger { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/MailUtil.java similarity index 75% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/MailUtil.java index b6ce02902c..49198f0ccc 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/MailUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; public class MailUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintSender.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/PrintSender.java similarity index 82% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintSender.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/PrintSender.java index 67a545f6fd..ad289c5113 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/PrintSender.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/PrintSender.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawFormatter.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/RawFormatter.java similarity index 81% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawFormatter.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/RawFormatter.java index f2218bf59d..6fcc3119bb 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/RawFormatter.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/RawFormatter.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SMSUtil.java similarity index 74% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SMSUtil.java index c127e204b8..fef42b1ab4 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SMSUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SMSUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; public class SMSUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Sender.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Sender.java similarity index 72% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Sender.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Sender.java index 939409612a..3420b17756 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/Sender.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/Sender.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SenderFactory.java similarity index 94% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SenderFactory.java index e068685b35..f5e2b38eb1 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SenderFactory.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SenderFactory.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; public class SenderFactory { public final int EMAIL_LOG = 1; diff --git a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsSender.java b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SmsSender.java similarity index 81% rename from students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsSender.java rename to students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SmsSender.java index 47f6b1a412..9ef0b9df1f 100644 --- a/students/812350401/src/main/java/com/coderising/ood/ocp/myocp/SmsSender.java +++ b/students/812350401/src/main/java/com/coderising/myood/ocp/myocp/SmsSender.java @@ -1,4 +1,4 @@ -package com.coderising.ood.ocp.myocp; +package com.coderising.myood.ocp.myocp; /** diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/Affiliation.java b/students/812350401/src/main/java/com/coderising/myood/payroll/Affiliation.java new file mode 100644 index 0000000000..0761abe820 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/Affiliation.java @@ -0,0 +1,5 @@ +package com.coderising.myood.payroll; + +public interface Affiliation { + public double calculateDeductions(Paycheck pc); +} diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/Employee.java b/students/812350401/src/main/java/com/coderising/myood/payroll/Employee.java new file mode 100644 index 0000000000..a8c1e19725 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/Employee.java @@ -0,0 +1,42 @@ +package com.coderising.myood.payroll; + +import java.util.Date; + +public class Employee { + String id; + String name; + String address; + Affiliation affiliation; + + + PaymentClassification classification; + PaymentSchedule schedule; + PaymentMethod paymentMethod; + + public Employee(String name, String address){ + this.name = name; + this.address = address; + } + public boolean isPayDay(Date d) { + return false; + } + + public Date getPayPeriodStartDate(Date d) { + return null; + } + + public void payDay(Paycheck pc){ + + } + + public void setClassification(PaymentClassification classification) { + this.classification = classification; + } + public void setSchedule(PaymentSchedule schedule) { + this.schedule = schedule; + } + public void setPaymentMethod(PaymentMethod paymentMethod) { + this.paymentMethod = paymentMethod; + } +} + diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/Paycheck.java b/students/812350401/src/main/java/com/coderising/myood/payroll/Paycheck.java new file mode 100644 index 0000000000..97a54a1bb4 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/Paycheck.java @@ -0,0 +1,34 @@ +package com.coderising.myood.payroll; + +import java.util.Date; + +public class Paycheck { + private Date payPeriodStart; + private Date payPeriodEnd; + private double grossPay; + private double netPay; + private double deductions; + + public Paycheck(Date payPeriodStart, Date payPeriodEnd){ + this.payPeriodStart = payPeriodStart; + this.payPeriodEnd = payPeriodEnd; + } + public void setGrossPay(double grossPay) { + this.grossPay = grossPay; + + } + public void setDeductions(double deductions) { + this.deductions = deductions; + } + public void setNetPay(double netPay){ + this.netPay = netPay; + } + public Date getPayPeriodEndDate() { + + return this.payPeriodEnd; + } + public Date getPayPeriodStartDate() { + + return this.payPeriodStart; + } +} diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentClassification.java b/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentClassification.java new file mode 100644 index 0000000000..c2faa50d53 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentClassification.java @@ -0,0 +1,5 @@ +package com.coderising.myood.payroll; + +public interface PaymentClassification { + public double calculatePay(Paycheck pc); +} diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentMethod.java b/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentMethod.java new file mode 100644 index 0000000000..1e1c6421cd --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentMethod.java @@ -0,0 +1,5 @@ +package com.coderising.myood.payroll; + +public interface PaymentMethod { + public void pay(Paycheck pc); +} diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentSchedule.java b/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentSchedule.java new file mode 100644 index 0000000000..71c36e3fd7 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/PaymentSchedule.java @@ -0,0 +1,8 @@ +package com.coderising.myood.payroll; + +import java.util.Date; + +public interface PaymentSchedule { + public boolean isPayDate(Date date); + public Date getPayPeriodStartDate(Date payPeriodEndDate); +} diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/SalesReceipt.java b/students/812350401/src/main/java/com/coderising/myood/payroll/SalesReceipt.java new file mode 100644 index 0000000000..176bb89807 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/SalesReceipt.java @@ -0,0 +1,14 @@ +package com.coderising.myood.payroll; + +import java.util.Date; + +public class SalesReceipt { + private Date saleDate; + private double amount; + public Date getSaleDate() { + return saleDate; + } + public double getAmount() { + return amount; + } +} diff --git a/students/812350401/src/main/java/com/coderising/myood/payroll/TimeCard.java b/students/812350401/src/main/java/com/coderising/myood/payroll/TimeCard.java new file mode 100644 index 0000000000..30ce0e6661 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/payroll/TimeCard.java @@ -0,0 +1,15 @@ +package com.coderising.myood.payroll; + +import java.util.Date; + +public class TimeCard { + private Date date; + private int hours; + + public Date getDate() { + return date; + } + public int getHours() { + return hours; + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java b/students/812350401/src/main/java/com/coderising/myood/srp/Configuration.java similarity index 94% rename from students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java rename to students/812350401/src/main/java/com/coderising/myood/srp/Configuration.java index f328c1816a..ff38f5a1b3 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/Configuration.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/Configuration.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; import java.util.HashMap; import java.util.Map; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/812350401/src/main/java/com/coderising/myood/srp/ConfigurationKeys.java similarity index 86% rename from students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java rename to students/812350401/src/main/java/com/coderising/myood/srp/ConfigurationKeys.java index 8695aed644..0ec546beee 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/ConfigurationKeys.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; public class ConfigurationKeys { diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/812350401/src/main/java/com/coderising/myood/srp/DBUtil.java similarity index 93% rename from students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java rename to students/812350401/src/main/java/com/coderising/myood/srp/DBUtil.java index fee83a770d..bf0db8a811 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/DBUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/DBUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; import java.util.ArrayList; import java.util.HashMap; import java.util.List; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java b/students/812350401/src/main/java/com/coderising/myood/srp/EmailParam.java similarity index 96% rename from students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java rename to students/812350401/src/main/java/com/coderising/myood/srp/EmailParam.java index 3a9fd4f2f0..71b5d30b40 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/EmailParam.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/EmailParam.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; /** diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/MailService.java b/students/812350401/src/main/java/com/coderising/myood/srp/MailService.java similarity index 99% rename from students/812350401/src/main/java/com/coderising/ood/srp/MailService.java rename to students/812350401/src/main/java/com/coderising/myood/srp/MailService.java index 7b01d47575..ec5809ba74 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/MailService.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/MailService.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; import java.io.IOException; import java.util.HashMap; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/812350401/src/main/java/com/coderising/myood/srp/MailUtil.java similarity index 93% rename from students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java rename to students/812350401/src/main/java/com/coderising/myood/srp/MailUtil.java index aa931433a9..25a0f64583 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/MailUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; public class MailUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java b/students/812350401/src/main/java/com/coderising/myood/srp/ProductInfo.java similarity index 94% rename from students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java rename to students/812350401/src/main/java/com/coderising/myood/srp/ProductInfo.java index 6d74acb3bf..1cca0338ec 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/ProductInfo.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/ProductInfo.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; import java.io.BufferedReader; import java.io.File; @@ -12,7 +12,7 @@ public class ProductInfo { private String productID = null; private String productDesc = null; - private static File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + private static File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/myood/srp/product_promotion.txt"); public ProductInfo() { try { diff --git a/students/812350401/src/main/java/com/coderising/myood/srp/PromotionMail.java b/students/812350401/src/main/java/com/coderising/myood/srp/PromotionMail.java new file mode 100644 index 0000000000..b6ecd6fc41 --- /dev/null +++ b/students/812350401/src/main/java/com/coderising/myood/srp/PromotionMail.java @@ -0,0 +1,8 @@ +package com.coderising.myood.srp; + +public class PromotionMail { + public static void main(String[] args) throws Exception { + MailService mailService = new MailService(); + mailService.sendMails(true); + } +} diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java b/students/812350401/src/main/java/com/coderising/myood/srp/UserDao.java similarity index 94% rename from students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java rename to students/812350401/src/main/java/com/coderising/myood/srp/UserDao.java index 49a0ce4040..d5f421a952 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/UserDao.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/UserDao.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp; +package com.coderising.myood.srp; import java.util.List; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Configuration.java similarity index 60% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Configuration.java index a9a4d3f207..b187686fc0 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Configuration.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Configuration.java @@ -1,6 +1,6 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; -import com.coderising.ood.srp.ConfigurationKeys; +import com.coderising.myood.srp.ConfigurationKeys; import java.util.HashMap; import java.util.Map; @@ -9,8 +9,8 @@ public class Configuration { static Map configurations = new HashMap<>(); static{ - configurations.put(com.coderising.ood.srp.ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); - configurations.put(com.coderising.ood.srp.ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(com.coderising.myood.srp.ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(com.coderising.myood.srp.ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); } /** diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/ConfigurationKeys.java similarity index 83% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/ConfigurationKeys.java index c39f1fcff9..c69fa86cbf 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ConfigurationKeys.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/ConfigurationKeys.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; public class ConfigurationKeys { diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/DBUtil.java similarity index 92% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/DBUtil.java index 53631cfa7f..4d8403d525 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/DBUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/DBUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; import java.util.ArrayList; import java.util.HashMap; import java.util.List; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Mail.java similarity index 79% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Mail.java index 858c154713..04472df8bc 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Mail.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Mail.java @@ -1,7 +1,7 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; -import com.coderising.ood.srp.goodSrp.template.MailBodyTemplate; -import com.coderising.ood.srp.goodSrp.template.TextMailBodyTemplate; +import com.coderising.myood.srp.goodSrp.template.MailBodyTemplate; +import com.coderising.myood.srp.goodSrp.template.TextMailBodyTemplate; import java.util.List; import java.util.stream.Collectors; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/MailSender.java similarity index 96% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/MailSender.java index 8ef8769291..70d2595e47 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailSender.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/MailSender.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; /** * Created by thomas_young on 24/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/MailUtil.java similarity index 92% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/MailUtil.java index 132ca6be87..77a26d8318 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/MailUtil.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/MailUtil.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; public class MailUtil { diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Product.java similarity index 90% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Product.java index dba13425c1..9373690bd7 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/Product.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/Product.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/ProductService.java similarity index 91% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/ProductService.java index 12ad38262e..26853bc4d3 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/ProductService.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/ProductService.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; import java.io.*; @@ -6,7 +6,7 @@ import java.util.List; public class ProductService { - private static File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt"); + private static File f = new File("/Users/thomas_young/Documents/code/liuxintraining/coding2017/students/812350401/src/main/java/com/coderising/myood/srp/product_promotion.txt"); public List getPromotionProducts() { //从文本文件中读取文件列表 String line; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/PromotionJob.java similarity index 93% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/PromotionJob.java index 59db8cdada..5b3ce7a1de 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/PromotionJob.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/PromotionJob.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; import java.util.List; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/User.java similarity index 95% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/User.java index 295345ae38..65383587d1 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/User.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/User.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; import java.util.List; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/UserService.java similarity index 94% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/UserService.java index a2bd152896..152d253ae3 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/UserService.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/UserService.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp; +package com.coderising.myood.srp.goodSrp; import java.util.LinkedList; import java.util.List; diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/template/MailBodyTemplate.java similarity index 52% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/template/MailBodyTemplate.java index 95eeff723f..2ff179ac7c 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/MailBodyTemplate.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/template/MailBodyTemplate.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp.template; +package com.coderising.myood.srp.goodSrp.template; public interface MailBodyTemplate { String render(); diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/template/TextMailBodyTemplate.java similarity index 90% rename from students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java rename to students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/template/TextMailBodyTemplate.java index 4dd174a3ce..b43561a04d 100644 --- a/students/812350401/src/main/java/com/coderising/ood/srp/goodSrp/template/TextMailBodyTemplate.java +++ b/students/812350401/src/main/java/com/coderising/myood/srp/goodSrp/template/TextMailBodyTemplate.java @@ -1,4 +1,4 @@ -package com.coderising.ood.srp.goodSrp.template; +package com.coderising.myood.srp.goodSrp.template; public class TextMailBodyTemplate implements MailBodyTemplate { diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/812350401/src/main/java/com/coderising/myood/srp/product_promotion.txt similarity index 100% rename from students/812350401/src/main/java/com/coderising/ood/srp/product_promotion.txt rename to students/812350401/src/main/java/com/coderising/myood/srp/product_promotion.txt diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java b/students/812350401/src/main/java/com/coderising/myood/uml/Dice.java similarity index 90% rename from students/812350401/src/main/java/com/coderising/ood/uml/Dice.java rename to students/812350401/src/main/java/com/coderising/myood/uml/Dice.java index b805b44d68..a48f7114ee 100644 --- a/students/812350401/src/main/java/com/coderising/ood/uml/Dice.java +++ b/students/812350401/src/main/java/com/coderising/myood/uml/Dice.java @@ -1,4 +1,4 @@ -package com.coderising.ood.uml; +package com.coderising.myood.uml; import com.google.common.collect.ImmutableList; diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java b/students/812350401/src/main/java/com/coderising/myood/uml/DiceGame.java similarity index 97% rename from students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java rename to students/812350401/src/main/java/com/coderising/myood/uml/DiceGame.java index afa322f909..386550fd67 100644 --- a/students/812350401/src/main/java/com/coderising/ood/uml/DiceGame.java +++ b/students/812350401/src/main/java/com/coderising/myood/uml/DiceGame.java @@ -1,4 +1,4 @@ -package com.coderising.ood.uml; +package com.coderising.myood.uml; /** * Created by thomas_young on 27/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java b/students/812350401/src/main/java/com/coderising/myood/uml/GameTest.java similarity index 91% rename from students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java rename to students/812350401/src/main/java/com/coderising/myood/uml/GameTest.java index 75906c3661..ee36709326 100644 --- a/students/812350401/src/main/java/com/coderising/ood/uml/GameTest.java +++ b/students/812350401/src/main/java/com/coderising/myood/uml/GameTest.java @@ -1,4 +1,4 @@ -package com.coderising.ood.uml; +package com.coderising.myood.uml; /** * Created by thomas_young on 27/6/2017. diff --git a/students/812350401/src/main/java/com/coderising/ood/uml/Player.java b/students/812350401/src/main/java/com/coderising/myood/uml/Player.java similarity index 92% rename from students/812350401/src/main/java/com/coderising/ood/uml/Player.java rename to students/812350401/src/main/java/com/coderising/myood/uml/Player.java index c51d5e0868..2add582970 100644 --- a/students/812350401/src/main/java/com/coderising/ood/uml/Player.java +++ b/students/812350401/src/main/java/com/coderising/myood/uml/Player.java @@ -1,4 +1,4 @@ -package com.coderising.ood.uml; +package com.coderising.myood.uml; /** * Created by thomas_young on 27/6/2017. diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/myood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" similarity index 100% rename from "students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" rename to "students/812350401/src/main/java/com/coderising/myood/uml/\346\212\225\351\252\260\345\255\220\346\227\266\345\272\217\345\233\276.png" diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/myood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" similarity index 100% rename from "students/812350401/src/main/java/com/coderising/ood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" rename to "students/812350401/src/main/java/com/coderising/myood/uml/\346\212\225\351\252\260\345\255\220\347\261\273\345\233\276.png" diff --git "a/students/812350401/src/main/java/com/coderising/ood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" "b/students/812350401/src/main/java/com/coderising/myood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" similarity index 100% rename from "students/812350401/src/main/java/com/coderising/ood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" rename to "students/812350401/src/main/java/com/coderising/myood/uml/\350\264\255\347\211\251\347\275\221\347\253\231\347\224\250\344\276\213\345\233\276.png" diff --git a/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java deleted file mode 100644 index bd635ea702..0000000000 --- a/students/812350401/src/main/java/com/coderising/ood/srp/PromotionMail.java +++ /dev/null @@ -1,17 +0,0 @@ -package com.coderising.ood.srp; - -import java.io.BufferedReader; -import java.io.File; -import java.io.FileReader; -import java.io.IOException; -import java.io.Serializable; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; - -public class PromotionMail { - public static void main(String[] args) throws Exception { - MailService mailService = new MailService(); - mailService.sendMails(true); - } -} From 5be0c63f09c5889380815534bee31a487c7e30ab Mon Sep 17 00:00:00 2001 From: sheng <1158154002@qq.com> Date: Sun, 9 Jul 2017 10:05:26 +0800 Subject: [PATCH 62/73] payroll --- .../AddCommissionEmployeeTransaction.java | 28 ++++++++ .../payroll/AddHourlyEmployeeTransaction.java | 27 ++++++++ .../AddSalariedEmployeeTransaction.java | 27 ++++++++ .../com/coderising/payroll/BankMethod.java | 15 +++++ .../coderising/payroll/BiWeeklySchedule.java | 22 +++++++ .../payroll/CommissionClassification.java | 34 ++++++++++ .../java/com/coderising/payroll/Employee.java | 55 ++++++++++++++++ .../com/coderising/payroll/HoldMethod.java | 12 ++++ .../payroll/HourlyClassification.java | 42 ++++++++++++ .../com/coderising/payroll/MailMethod.java | 13 ++++ .../coderising/payroll/MonthlySchedule.java | 20 ++++++ .../coderising/payroll/NonAffiliation.java | 12 ++++ .../java/com/coderising/payroll/Paycheck.java | 34 ++++++++++ .../payroll/SalariedClassification.java | 18 ++++++ .../com/coderising/payroll/SalesReceipt.java | 14 ++++ .../com/coderising/payroll/ServiceCharge.java | 16 +++++ .../java/com/coderising/payroll/TimeCard.java | 15 +++++ .../coderising/payroll/UnionAffiliation.java | 35 ++++++++++ .../coderising/payroll/WeeklySchedule.java | 21 ++++++ .../payroll/api/AddEmployeeTransaction.java | 34 ++++++++++ .../coderising/payroll/api/Affiliation.java | 7 ++ .../payroll/api/PaymentClassification.java | 7 ++ .../coderising/payroll/api/PaymentMethod.java | 7 ++ .../payroll/api/PaymentSchedule.java | 8 +++ .../payroll/service/PayrollService.java | 30 +++++++++ .../com/coderising/payroll/util/DateUtil.java | 64 +++++++++++++++++++ 26 files changed, 617 insertions(+) create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/Employee.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java new file mode 100644 index 0000000000..45b30ab31b --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java @@ -0,0 +1,28 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.AddEmployeeTransaction; +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class AddCommissionEmployeeTransaction extends AddEmployeeTransaction{ + private double rate; + private double salary; + public AddCommissionEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, + Affiliation affiliation) { + super(name, address, paymentMethod, affiliation); + this.rate=rate; + } + + @Override + public PaymentClassification getClassification() { + return new CommissionClassification(rate,salary); + } + + @Override + public PaymentSchedule getSchedule() { + return new WeeklySchedule(); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java new file mode 100644 index 0000000000..c7b92eafd3 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java @@ -0,0 +1,27 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.AddEmployeeTransaction; +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class AddHourlyEmployeeTransaction extends AddEmployeeTransaction{ + private double rate; + public AddHourlyEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, + Affiliation affiliation) { + super(name, address, paymentMethod, affiliation); + this.rate=rate; + } + + @Override + public PaymentClassification getClassification() { + return new HourlyClassification(rate); + } + + @Override + public PaymentSchedule getSchedule() { + return new WeeklySchedule(); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java new file mode 100644 index 0000000000..4edfbd0d1e --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java @@ -0,0 +1,27 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.AddEmployeeTransaction; +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class AddSalariedEmployeeTransaction extends AddEmployeeTransaction{ + private double salary; + public AddSalariedEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, + Affiliation affiliation) { + super(name, address, paymentMethod, affiliation); + this.salary=salary; + } + + @Override + public PaymentClassification getClassification() { + return new SalariedClassification(salary); + } + + @Override + public PaymentSchedule getSchedule() { + return new MonthlySchedule(); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java new file mode 100644 index 0000000000..2a37417717 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java @@ -0,0 +1,15 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentMethod; + +public class BankMethod implements PaymentMethod{ + + private String bank; + private String account; + + @Override + public void pay(Paycheck pc) { + System.out.println("BankMethod"); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java new file mode 100644 index 0000000000..39ab695425 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java @@ -0,0 +1,22 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class BiWeeklySchedule implements PaymentSchedule { + Date firstPayableFriday = DateUtil.parseDate("2017-06-02"); + + @Override + public boolean isPayDate(Date date) { + int interval = DateUtil.getDaysBetween(firstPayableFriday, date); + return interval % 14 == 0; + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.add(payPeriodEndDate, -13); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java new file mode 100644 index 0000000000..758e5e8ba8 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java @@ -0,0 +1,34 @@ +package com.coderising.payroll; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.util.DateUtil; + +public class CommissionClassification implements PaymentClassification{ + private double salary; + private double rate; + private Map receipts; + + public CommissionClassification(double rate, double salary) { + this.rate=rate; + this.salary=salary; + } + + public void addSalesReceipt(SalesReceipt sr) { + receipts.put(sr.getSaleDate(), sr); + } + + @Override + public double calculatePay(Paycheck pc) { + double commission=0; + for (SalesReceipt sr : receipts.values()) { + if (DateUtil.between(sr.getSaleDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + commission+=sr.getAmount()*rate; + } + } + return salary+commission; + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/Employee.java b/students/1158154002/src/main/java/com/coderising/payroll/Employee.java new file mode 100644 index 0000000000..45f503ab4a --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/Employee.java @@ -0,0 +1,55 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class Employee { + String id; + String name; + String address; + + Affiliation affiliation; + PaymentClassification classification; + PaymentSchedule schedule; + PaymentMethod paymentMethod; + + public Employee(String name, String address){ + this.name = name; + this.address = address; + } + public boolean isPayDay(Date d) { + return schedule.isPayDate(d); + } + + public Date getPayPeriodStartDate(Date d) { + return schedule.getPayPeriodStartDate(d); + } + + public void payDay(Paycheck pc){ + double grossPay=classification.calculatePay(pc); + double deductions=affiliation.calculateDeductions(pc); + double netPay=grossPay-deductions; + pc.setGrossPay(grossPay); + pc.setDeductions(deductions); + pc.setNetPay(netPay); + paymentMethod.pay(pc); + } + + public void setClassification(PaymentClassification classification) { + this.classification = classification; + } + public void setSchedule(PaymentSchedule schedule) { + this.schedule = schedule; + } + public void setPaymentMethod(PaymentMethod paymentMethod) { + this.paymentMethod = paymentMethod; + } + + public void setAffiliation(Affiliation affiliation) { + this.affiliation = affiliation; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java new file mode 100644 index 0000000000..ec0892eb6a --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java @@ -0,0 +1,12 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentMethod; + +public class HoldMethod implements PaymentMethod{ + + @Override + public void pay(Paycheck pc) { + System.out.println("HoldMethod"); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java new file mode 100644 index 0000000000..6d61cae25e --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java @@ -0,0 +1,42 @@ +package com.coderising.payroll; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.util.DateUtil; + +public class HourlyClassification implements PaymentClassification { + + private double rate; + private Map timeCards; + + public HourlyClassification(double rate) { + this.rate=rate; + } + + public void addTimeCard(TimeCard tc) { + timeCards.put(tc.getDate(), tc); + } + + @Override + public double calculatePay(Paycheck pc) { + double totalPay = 0; + for (TimeCard tc : timeCards.values()) { + if (DateUtil.between(tc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + totalPay+=calculatePayForTimeCard(tc); + } + } + return totalPay; + } + + private double calculatePayForTimeCard(TimeCard tc) { + int hours = tc.getHours(); + if (hours > 8) { + return 8 * rate + (hours - 8) * 1.5 * rate; + } else { + return 8 * rate; + } + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java new file mode 100644 index 0000000000..8cbcf755e0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java @@ -0,0 +1,13 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentMethod; + +public class MailMethod implements PaymentMethod{ + private String address; + + @Override + public void pay(Paycheck pc) { + System.out.println("MailMethod"); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java new file mode 100644 index 0000000000..4b96edd28e --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java @@ -0,0 +1,20 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class MonthlySchedule implements PaymentSchedule{ + + @Override + public boolean isPayDate(Date date) { + return DateUtil.isLasyDayOfMonth(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.getFirstDay(payPeriodEndDate); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java new file mode 100644 index 0000000000..ec8b6bc5a4 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java @@ -0,0 +1,12 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.Affiliation; + +public class NonAffiliation implements Affiliation{ + + @Override + public double calculateDeductions(Paycheck pc) { + return 0; + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java b/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java new file mode 100644 index 0000000000..5a7f0f87e0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java @@ -0,0 +1,34 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class Paycheck { + private Date payPeriodStart; + private Date payPeriodEnd; + private double grossPay; + private double netPay; + private double deductions; + + public Paycheck(Date payPeriodStart, Date payPeriodEnd){ + this.payPeriodStart = payPeriodStart; + this.payPeriodEnd = payPeriodEnd; + } + public void setGrossPay(double grossPay) { + this.grossPay = grossPay; + + } + public void setDeductions(double deductions) { + this.deductions = deductions; + } + public void setNetPay(double netPay){ + this.netPay = netPay; + } + public Date getPayPeriodEndDate() { + + return this.payPeriodEnd; + } + public Date getPayPeriodStartDate() { + + return this.payPeriodStart; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java new file mode 100644 index 0000000000..8bc025e1d8 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java @@ -0,0 +1,18 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentClassification; + +public class SalariedClassification implements PaymentClassification{ + private double salary; + + public SalariedClassification(double salary) { + this.salary=salary; + } + + @Override + public double calculatePay(Paycheck pc) { + // TODO Auto-generated method stub + return salary; + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java b/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java new file mode 100644 index 0000000000..25bbcd81bc --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java @@ -0,0 +1,14 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class SalesReceipt { + private Date saleDate; + private double amount; + public Date getSaleDate() { + return saleDate; + } + public double getAmount() { + return amount; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java b/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java new file mode 100644 index 0000000000..58acbc3701 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java @@ -0,0 +1,16 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class ServiceCharge { + private Date date; + private double amount; + + public Date getDate() { + return date; + } + + public double getAmount() { + return amount; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java b/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java new file mode 100644 index 0000000000..0ee88399c5 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java @@ -0,0 +1,15 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class TimeCard { + private Date date; + private int hours; + + public Date getDate() { + return date; + } + public int getHours() { + return hours; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java new file mode 100644 index 0000000000..7505b585a8 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java @@ -0,0 +1,35 @@ +package com.coderising.payroll; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.util.DateUtil; + +public class UnionAffiliation implements Affiliation{ + private String memberID; + private double weeklyDue; + private Map serviceCharges; + + public void addServiceCharge(ServiceCharge sc){ + serviceCharges.put(sc.getDate(), sc); + } + + @Override + public double calculateDeductions(Paycheck pc) { + double totalPay = 0; + for (ServiceCharge sc : serviceCharges.values()) { + if (DateUtil.between(sc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + totalPay+=sc.getAmount(); + } + } + return totalPay+calculatePayForWeeklyDue(pc); + } + + private double calculatePayForWeeklyDue(Paycheck pc) { + int interval=DateUtil.getDaysBetween( pc.getPayPeriodStartDate(),pc.getPayPeriodEndDate()); + return interval/7*weeklyDue; + } + + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java new file mode 100644 index 0000000000..93e96d2412 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java @@ -0,0 +1,21 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class WeeklySchedule implements PaymentSchedule{ + + @Override + public boolean isPayDate(Date date) { + + return DateUtil.isFriday(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.add(payPeriodEndDate, -6); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java new file mode 100644 index 0000000000..8537092b94 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java @@ -0,0 +1,34 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Employee; + +public abstract class AddEmployeeTransaction { + private String name; + private String address; + private PaymentMethod paymentMethod; + private Affiliation affiliation; + + + public AddEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, Affiliation affiliation) { + super(); + this.name = name; + this.address = address; + this.paymentMethod = paymentMethod; + this.affiliation = affiliation; + } + + public abstract PaymentClassification getClassification(); + + public abstract PaymentSchedule getSchedule(); + + public void execute(){ + PaymentClassification pc=getClassification(); + PaymentSchedule ps=getSchedule(); + Employee e=new Employee(name, address); + e.setClassification(pc); + e.setSchedule(ps); + e.setPaymentMethod(paymentMethod); + e.setAffiliation(affiliation); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java new file mode 100644 index 0000000000..9a28cd1c46 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java @@ -0,0 +1,7 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Paycheck; + +public interface Affiliation { + public double calculateDeductions(Paycheck pc); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java new file mode 100644 index 0000000000..66e1c6704f --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java @@ -0,0 +1,7 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Paycheck; + +public interface PaymentClassification { + public double calculatePay(Paycheck pc); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java new file mode 100644 index 0000000000..2be20094b0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java @@ -0,0 +1,7 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Paycheck; + +public interface PaymentMethod { + public void pay(Paycheck pc); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java new file mode 100644 index 0000000000..520b6a2e98 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java @@ -0,0 +1,8 @@ +package com.coderising.payroll.api; + +import java.util.Date; + +public interface PaymentSchedule { + public boolean isPayDate(Date date); + public Date getPayPeriodStartDate( Date payPeriodEndDate); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java b/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java new file mode 100644 index 0000000000..07e3ff6c4d --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java @@ -0,0 +1,30 @@ +package com.coderising.payroll.service; + +import java.util.Date; +import java.util.List; + +import com.coderising.payroll.Employee; +import com.coderising.payroll.Paycheck; + +public class PayrollService { + + public List getAllEmployees(){ + return null; + } + + public void savePayCheck(Paycheck pc){} + + public static void main(String[] args) { + PayrollService payrollService=new PayrollService(); + Date date=new Date(); + List employees=payrollService.getAllEmployees(); + for (Employee e : employees) { + if (e.isPayDay(date)) { + Paycheck pc=new Paycheck(e.getPayPeriodStartDate(date), date); + e.payDay(pc); + payrollService.savePayCheck(pc); + } + } + + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java b/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java new file mode 100644 index 0000000000..607088f9ee --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java @@ -0,0 +1,64 @@ +package com.coderising.payroll.util; + +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Calendar; +import java.util.Date; + +public class DateUtil { + public static boolean isLasyDayOfMonth(Date date) { + Calendar b = Calendar.getInstance(); + b.setTime(date); + int lastDay = b.getActualMaximum(Calendar.DAY_OF_MONTH); + int now = b.get(Calendar.DAY_OF_MONTH); + return now == lastDay; + } + + public static Date getFirstDay(Date payPeriodEndDate) { + Calendar c = Calendar.getInstance(); + c.add(Calendar.MONTH, 0); + c.set(Calendar.DAY_OF_MONTH, 1); + return c.getTime(); + } + + public static Date add(Date date, int num) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(Calendar.DATE, num); + return c.getTime(); + } + + public static Date parseDate(String date) { + SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); + Date time = null; + try { + time = sdf.parse(date); + } catch (ParseException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + return time; + } + + public static boolean isFriday(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.get(Calendar.DAY_OF_WEEK) == 6; + } + + public static int getDaysBetween(Date start, Date end) { + Calendar aCalendar = Calendar.getInstance(); + aCalendar.setTime(end); + + int day1 = aCalendar.get(Calendar.DAY_OF_YEAR); + aCalendar.setTime(start); + + int day2 = aCalendar.get(Calendar.DAY_OF_YEAR); + + return day1 - day2; + } + + public static boolean between(Date date,Date start,Date end){ + return date.getTime()>=start.getTime()&&date.getTime()<=end.getTime(); + } +} From b5f9d4892385c46aa9d5b5129e734bfe72b4672e Mon Sep 17 00:00:00 2001 From: sheng <1158154002@qq.com> Date: Sun, 9 Jul 2017 10:35:34 +0800 Subject: [PATCH 63/73] Revert "payroll" This reverts commit 5be0c63f09c5889380815534bee31a487c7e30ab. --- .../AddCommissionEmployeeTransaction.java | 28 -------- .../payroll/AddHourlyEmployeeTransaction.java | 27 -------- .../AddSalariedEmployeeTransaction.java | 27 -------- .../com/coderising/payroll/BankMethod.java | 15 ----- .../coderising/payroll/BiWeeklySchedule.java | 22 ------- .../payroll/CommissionClassification.java | 34 ---------- .../java/com/coderising/payroll/Employee.java | 55 ---------------- .../com/coderising/payroll/HoldMethod.java | 12 ---- .../payroll/HourlyClassification.java | 42 ------------ .../com/coderising/payroll/MailMethod.java | 13 ---- .../coderising/payroll/MonthlySchedule.java | 20 ------ .../coderising/payroll/NonAffiliation.java | 12 ---- .../java/com/coderising/payroll/Paycheck.java | 34 ---------- .../payroll/SalariedClassification.java | 18 ------ .../com/coderising/payroll/SalesReceipt.java | 14 ---- .../com/coderising/payroll/ServiceCharge.java | 16 ----- .../java/com/coderising/payroll/TimeCard.java | 15 ----- .../coderising/payroll/UnionAffiliation.java | 35 ---------- .../coderising/payroll/WeeklySchedule.java | 21 ------ .../payroll/api/AddEmployeeTransaction.java | 34 ---------- .../coderising/payroll/api/Affiliation.java | 7 -- .../payroll/api/PaymentClassification.java | 7 -- .../coderising/payroll/api/PaymentMethod.java | 7 -- .../payroll/api/PaymentSchedule.java | 8 --- .../payroll/service/PayrollService.java | 30 --------- .../com/coderising/payroll/util/DateUtil.java | 64 ------------------- 26 files changed, 617 deletions(-) delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/Employee.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java delete mode 100644 students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java deleted file mode 100644 index 45b30ab31b..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.AddEmployeeTransaction; -import com.coderising.payroll.api.Affiliation; -import com.coderising.payroll.api.PaymentClassification; -import com.coderising.payroll.api.PaymentMethod; -import com.coderising.payroll.api.PaymentSchedule; - -public class AddCommissionEmployeeTransaction extends AddEmployeeTransaction{ - private double rate; - private double salary; - public AddCommissionEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, - Affiliation affiliation) { - super(name, address, paymentMethod, affiliation); - this.rate=rate; - } - - @Override - public PaymentClassification getClassification() { - return new CommissionClassification(rate,salary); - } - - @Override - public PaymentSchedule getSchedule() { - return new WeeklySchedule(); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java deleted file mode 100644 index c7b92eafd3..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java +++ /dev/null @@ -1,27 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.AddEmployeeTransaction; -import com.coderising.payroll.api.Affiliation; -import com.coderising.payroll.api.PaymentClassification; -import com.coderising.payroll.api.PaymentMethod; -import com.coderising.payroll.api.PaymentSchedule; - -public class AddHourlyEmployeeTransaction extends AddEmployeeTransaction{ - private double rate; - public AddHourlyEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, - Affiliation affiliation) { - super(name, address, paymentMethod, affiliation); - this.rate=rate; - } - - @Override - public PaymentClassification getClassification() { - return new HourlyClassification(rate); - } - - @Override - public PaymentSchedule getSchedule() { - return new WeeklySchedule(); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java deleted file mode 100644 index 4edfbd0d1e..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java +++ /dev/null @@ -1,27 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.AddEmployeeTransaction; -import com.coderising.payroll.api.Affiliation; -import com.coderising.payroll.api.PaymentClassification; -import com.coderising.payroll.api.PaymentMethod; -import com.coderising.payroll.api.PaymentSchedule; - -public class AddSalariedEmployeeTransaction extends AddEmployeeTransaction{ - private double salary; - public AddSalariedEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, - Affiliation affiliation) { - super(name, address, paymentMethod, affiliation); - this.salary=salary; - } - - @Override - public PaymentClassification getClassification() { - return new SalariedClassification(salary); - } - - @Override - public PaymentSchedule getSchedule() { - return new MonthlySchedule(); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java deleted file mode 100644 index 2a37417717..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.PaymentMethod; - -public class BankMethod implements PaymentMethod{ - - private String bank; - private String account; - - @Override - public void pay(Paycheck pc) { - System.out.println("BankMethod"); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java deleted file mode 100644 index 39ab695425..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -import com.coderising.payroll.api.PaymentSchedule; -import com.coderising.payroll.util.DateUtil; - -public class BiWeeklySchedule implements PaymentSchedule { - Date firstPayableFriday = DateUtil.parseDate("2017-06-02"); - - @Override - public boolean isPayDate(Date date) { - int interval = DateUtil.getDaysBetween(firstPayableFriday, date); - return interval % 14 == 0; - } - - @Override - public Date getPayPeriodStartDate(Date payPeriodEndDate) { - return DateUtil.add(payPeriodEndDate, -13); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java deleted file mode 100644 index 758e5e8ba8..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java +++ /dev/null @@ -1,34 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; -import java.util.Map; - -import com.coderising.payroll.api.PaymentClassification; -import com.coderising.payroll.util.DateUtil; - -public class CommissionClassification implements PaymentClassification{ - private double salary; - private double rate; - private Map receipts; - - public CommissionClassification(double rate, double salary) { - this.rate=rate; - this.salary=salary; - } - - public void addSalesReceipt(SalesReceipt sr) { - receipts.put(sr.getSaleDate(), sr); - } - - @Override - public double calculatePay(Paycheck pc) { - double commission=0; - for (SalesReceipt sr : receipts.values()) { - if (DateUtil.between(sr.getSaleDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { - commission+=sr.getAmount()*rate; - } - } - return salary+commission; - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/Employee.java b/students/1158154002/src/main/java/com/coderising/payroll/Employee.java deleted file mode 100644 index 45f503ab4a..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/Employee.java +++ /dev/null @@ -1,55 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -import com.coderising.payroll.api.Affiliation; -import com.coderising.payroll.api.PaymentClassification; -import com.coderising.payroll.api.PaymentMethod; -import com.coderising.payroll.api.PaymentSchedule; - -public class Employee { - String id; - String name; - String address; - - Affiliation affiliation; - PaymentClassification classification; - PaymentSchedule schedule; - PaymentMethod paymentMethod; - - public Employee(String name, String address){ - this.name = name; - this.address = address; - } - public boolean isPayDay(Date d) { - return schedule.isPayDate(d); - } - - public Date getPayPeriodStartDate(Date d) { - return schedule.getPayPeriodStartDate(d); - } - - public void payDay(Paycheck pc){ - double grossPay=classification.calculatePay(pc); - double deductions=affiliation.calculateDeductions(pc); - double netPay=grossPay-deductions; - pc.setGrossPay(grossPay); - pc.setDeductions(deductions); - pc.setNetPay(netPay); - paymentMethod.pay(pc); - } - - public void setClassification(PaymentClassification classification) { - this.classification = classification; - } - public void setSchedule(PaymentSchedule schedule) { - this.schedule = schedule; - } - public void setPaymentMethod(PaymentMethod paymentMethod) { - this.paymentMethod = paymentMethod; - } - - public void setAffiliation(Affiliation affiliation) { - this.affiliation = affiliation; - } -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java deleted file mode 100644 index ec0892eb6a..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.PaymentMethod; - -public class HoldMethod implements PaymentMethod{ - - @Override - public void pay(Paycheck pc) { - System.out.println("HoldMethod"); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java deleted file mode 100644 index 6d61cae25e..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java +++ /dev/null @@ -1,42 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; -import java.util.Map; - -import com.coderising.payroll.api.PaymentClassification; -import com.coderising.payroll.util.DateUtil; - -public class HourlyClassification implements PaymentClassification { - - private double rate; - private Map timeCards; - - public HourlyClassification(double rate) { - this.rate=rate; - } - - public void addTimeCard(TimeCard tc) { - timeCards.put(tc.getDate(), tc); - } - - @Override - public double calculatePay(Paycheck pc) { - double totalPay = 0; - for (TimeCard tc : timeCards.values()) { - if (DateUtil.between(tc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { - totalPay+=calculatePayForTimeCard(tc); - } - } - return totalPay; - } - - private double calculatePayForTimeCard(TimeCard tc) { - int hours = tc.getHours(); - if (hours > 8) { - return 8 * rate + (hours - 8) * 1.5 * rate; - } else { - return 8 * rate; - } - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java deleted file mode 100644 index 8cbcf755e0..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.PaymentMethod; - -public class MailMethod implements PaymentMethod{ - private String address; - - @Override - public void pay(Paycheck pc) { - System.out.println("MailMethod"); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java deleted file mode 100644 index 4b96edd28e..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java +++ /dev/null @@ -1,20 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -import com.coderising.payroll.api.PaymentSchedule; -import com.coderising.payroll.util.DateUtil; - -public class MonthlySchedule implements PaymentSchedule{ - - @Override - public boolean isPayDate(Date date) { - return DateUtil.isLasyDayOfMonth(date); - } - - @Override - public Date getPayPeriodStartDate(Date payPeriodEndDate) { - return DateUtil.getFirstDay(payPeriodEndDate); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java deleted file mode 100644 index ec8b6bc5a4..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.Affiliation; - -public class NonAffiliation implements Affiliation{ - - @Override - public double calculateDeductions(Paycheck pc) { - return 0; - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java b/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java deleted file mode 100644 index 5a7f0f87e0..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java +++ /dev/null @@ -1,34 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -public class Paycheck { - private Date payPeriodStart; - private Date payPeriodEnd; - private double grossPay; - private double netPay; - private double deductions; - - public Paycheck(Date payPeriodStart, Date payPeriodEnd){ - this.payPeriodStart = payPeriodStart; - this.payPeriodEnd = payPeriodEnd; - } - public void setGrossPay(double grossPay) { - this.grossPay = grossPay; - - } - public void setDeductions(double deductions) { - this.deductions = deductions; - } - public void setNetPay(double netPay){ - this.netPay = netPay; - } - public Date getPayPeriodEndDate() { - - return this.payPeriodEnd; - } - public Date getPayPeriodStartDate() { - - return this.payPeriodStart; - } -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java deleted file mode 100644 index 8bc025e1d8..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java +++ /dev/null @@ -1,18 +0,0 @@ -package com.coderising.payroll; - -import com.coderising.payroll.api.PaymentClassification; - -public class SalariedClassification implements PaymentClassification{ - private double salary; - - public SalariedClassification(double salary) { - this.salary=salary; - } - - @Override - public double calculatePay(Paycheck pc) { - // TODO Auto-generated method stub - return salary; - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java b/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java deleted file mode 100644 index 25bbcd81bc..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java +++ /dev/null @@ -1,14 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -public class SalesReceipt { - private Date saleDate; - private double amount; - public Date getSaleDate() { - return saleDate; - } - public double getAmount() { - return amount; - } -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java b/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java deleted file mode 100644 index 58acbc3701..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java +++ /dev/null @@ -1,16 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -public class ServiceCharge { - private Date date; - private double amount; - - public Date getDate() { - return date; - } - - public double getAmount() { - return amount; - } -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java b/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java deleted file mode 100644 index 0ee88399c5..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -public class TimeCard { - private Date date; - private int hours; - - public Date getDate() { - return date; - } - public int getHours() { - return hours; - } -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java deleted file mode 100644 index 7505b585a8..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java +++ /dev/null @@ -1,35 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; -import java.util.Map; - -import com.coderising.payroll.api.Affiliation; -import com.coderising.payroll.util.DateUtil; - -public class UnionAffiliation implements Affiliation{ - private String memberID; - private double weeklyDue; - private Map serviceCharges; - - public void addServiceCharge(ServiceCharge sc){ - serviceCharges.put(sc.getDate(), sc); - } - - @Override - public double calculateDeductions(Paycheck pc) { - double totalPay = 0; - for (ServiceCharge sc : serviceCharges.values()) { - if (DateUtil.between(sc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { - totalPay+=sc.getAmount(); - } - } - return totalPay+calculatePayForWeeklyDue(pc); - } - - private double calculatePayForWeeklyDue(Paycheck pc) { - int interval=DateUtil.getDaysBetween( pc.getPayPeriodStartDate(),pc.getPayPeriodEndDate()); - return interval/7*weeklyDue; - } - - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java deleted file mode 100644 index 93e96d2412..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java +++ /dev/null @@ -1,21 +0,0 @@ -package com.coderising.payroll; - -import java.util.Date; - -import com.coderising.payroll.api.PaymentSchedule; -import com.coderising.payroll.util.DateUtil; - -public class WeeklySchedule implements PaymentSchedule{ - - @Override - public boolean isPayDate(Date date) { - - return DateUtil.isFriday(date); - } - - @Override - public Date getPayPeriodStartDate(Date payPeriodEndDate) { - return DateUtil.add(payPeriodEndDate, -6); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java deleted file mode 100644 index 8537092b94..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java +++ /dev/null @@ -1,34 +0,0 @@ -package com.coderising.payroll.api; - -import com.coderising.payroll.Employee; - -public abstract class AddEmployeeTransaction { - private String name; - private String address; - private PaymentMethod paymentMethod; - private Affiliation affiliation; - - - public AddEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, Affiliation affiliation) { - super(); - this.name = name; - this.address = address; - this.paymentMethod = paymentMethod; - this.affiliation = affiliation; - } - - public abstract PaymentClassification getClassification(); - - public abstract PaymentSchedule getSchedule(); - - public void execute(){ - PaymentClassification pc=getClassification(); - PaymentSchedule ps=getSchedule(); - Employee e=new Employee(name, address); - e.setClassification(pc); - e.setSchedule(ps); - e.setPaymentMethod(paymentMethod); - e.setAffiliation(affiliation); - } - -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java deleted file mode 100644 index 9a28cd1c46..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java +++ /dev/null @@ -1,7 +0,0 @@ -package com.coderising.payroll.api; - -import com.coderising.payroll.Paycheck; - -public interface Affiliation { - public double calculateDeductions(Paycheck pc); -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java deleted file mode 100644 index 66e1c6704f..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java +++ /dev/null @@ -1,7 +0,0 @@ -package com.coderising.payroll.api; - -import com.coderising.payroll.Paycheck; - -public interface PaymentClassification { - public double calculatePay(Paycheck pc); -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java deleted file mode 100644 index 2be20094b0..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java +++ /dev/null @@ -1,7 +0,0 @@ -package com.coderising.payroll.api; - -import com.coderising.payroll.Paycheck; - -public interface PaymentMethod { - public void pay(Paycheck pc); -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java deleted file mode 100644 index 520b6a2e98..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java +++ /dev/null @@ -1,8 +0,0 @@ -package com.coderising.payroll.api; - -import java.util.Date; - -public interface PaymentSchedule { - public boolean isPayDate(Date date); - public Date getPayPeriodStartDate( Date payPeriodEndDate); -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java b/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java deleted file mode 100644 index 07e3ff6c4d..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.coderising.payroll.service; - -import java.util.Date; -import java.util.List; - -import com.coderising.payroll.Employee; -import com.coderising.payroll.Paycheck; - -public class PayrollService { - - public List getAllEmployees(){ - return null; - } - - public void savePayCheck(Paycheck pc){} - - public static void main(String[] args) { - PayrollService payrollService=new PayrollService(); - Date date=new Date(); - List employees=payrollService.getAllEmployees(); - for (Employee e : employees) { - if (e.isPayDay(date)) { - Paycheck pc=new Paycheck(e.getPayPeriodStartDate(date), date); - e.payDay(pc); - payrollService.savePayCheck(pc); - } - } - - } -} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java b/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java deleted file mode 100644 index 607088f9ee..0000000000 --- a/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java +++ /dev/null @@ -1,64 +0,0 @@ -package com.coderising.payroll.util; - -import java.text.ParseException; -import java.text.SimpleDateFormat; -import java.util.Calendar; -import java.util.Date; - -public class DateUtil { - public static boolean isLasyDayOfMonth(Date date) { - Calendar b = Calendar.getInstance(); - b.setTime(date); - int lastDay = b.getActualMaximum(Calendar.DAY_OF_MONTH); - int now = b.get(Calendar.DAY_OF_MONTH); - return now == lastDay; - } - - public static Date getFirstDay(Date payPeriodEndDate) { - Calendar c = Calendar.getInstance(); - c.add(Calendar.MONTH, 0); - c.set(Calendar.DAY_OF_MONTH, 1); - return c.getTime(); - } - - public static Date add(Date date, int num) { - Calendar c = Calendar.getInstance(); - c.setTime(date); - c.add(Calendar.DATE, num); - return c.getTime(); - } - - public static Date parseDate(String date) { - SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); - Date time = null; - try { - time = sdf.parse(date); - } catch (ParseException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } - return time; - } - - public static boolean isFriday(Date date) { - Calendar c = Calendar.getInstance(); - c.setTime(date); - return c.get(Calendar.DAY_OF_WEEK) == 6; - } - - public static int getDaysBetween(Date start, Date end) { - Calendar aCalendar = Calendar.getInstance(); - aCalendar.setTime(end); - - int day1 = aCalendar.get(Calendar.DAY_OF_YEAR); - aCalendar.setTime(start); - - int day2 = aCalendar.get(Calendar.DAY_OF_YEAR); - - return day1 - day2; - } - - public static boolean between(Date date,Date start,Date end){ - return date.getTime()>=start.getTime()&&date.getTime()<=end.getTime(); - } -} From aba6c8605d0a97095ee312d2ba05de650c67b1ad Mon Sep 17 00:00:00 2001 From: sheng <1158154002@qq.com> Date: Sun, 9 Jul 2017 10:55:23 +0800 Subject: [PATCH 64/73] payroll --- .../AddCommissionEmployeeTransaction.java | 28 ++++++++ .../payroll/AddEmployeeTransaction.java | 37 +++++++++++ .../payroll/AddHourlyEmployeeTransaction.java | 27 ++++++++ .../AddSalariedEmployeeTransaction.java | 27 ++++++++ .../com/coderising/payroll/BankMethod.java | 15 +++++ .../coderising/payroll/BiWeeklySchedule.java | 22 +++++++ .../payroll/CommissionClassification.java | 34 ++++++++++ .../java/com/coderising/payroll/Employee.java | 55 ++++++++++++++++ .../com/coderising/payroll/HoldMethod.java | 12 ++++ .../payroll/HourlyClassification.java | 42 ++++++++++++ .../com/coderising/payroll/MailMethod.java | 13 ++++ .../coderising/payroll/MonthlySchedule.java | 20 ++++++ .../coderising/payroll/NonAffiliation.java | 12 ++++ .../java/com/coderising/payroll/Paycheck.java | 34 ++++++++++ .../payroll/SalariedClassification.java | 18 +++++ .../com/coderising/payroll/SalesReceipt.java | 14 ++++ .../com/coderising/payroll/ServiceCharge.java | 22 +++++++ .../java/com/coderising/payroll/TimeCard.java | 15 +++++ .../coderising/payroll/UnionAffiliation.java | 35 ++++++++++ .../coderising/payroll/WeeklySchedule.java | 21 ++++++ .../payroll/api/AddEmployeeTransaction.java | 34 ++++++++++ .../coderising/payroll/api/Affiliation.java | 7 ++ .../payroll/api/PaymentClassification.java | 7 ++ .../coderising/payroll/api/PaymentMethod.java | 7 ++ .../payroll/api/PaymentSchedule.java | 8 +++ .../com/coderising/payroll/package-info.java | 8 +++ .../payroll/service/PayrollService.java | 29 +++++++++ .../com/coderising/payroll/util/DateUtil.java | 65 +++++++++++++++++++ 28 files changed, 668 insertions(+) create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/Employee.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/package-info.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java create mode 100644 students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java new file mode 100644 index 0000000000..45b30ab31b --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddCommissionEmployeeTransaction.java @@ -0,0 +1,28 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.AddEmployeeTransaction; +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class AddCommissionEmployeeTransaction extends AddEmployeeTransaction{ + private double rate; + private double salary; + public AddCommissionEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, + Affiliation affiliation) { + super(name, address, paymentMethod, affiliation); + this.rate=rate; + } + + @Override + public PaymentClassification getClassification() { + return new CommissionClassification(rate,salary); + } + + @Override + public PaymentSchedule getSchedule() { + return new WeeklySchedule(); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddEmployeeTransaction.java new file mode 100644 index 0000000000..9a5ed30b31 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddEmployeeTransaction.java @@ -0,0 +1,37 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public abstract class AddEmployeeTransaction { + private String name; + private String address; + private PaymentMethod paymentMethod; + private Affiliation affiliation; + + + public AddEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, Affiliation affiliation) { + super(); + this.name = name; + this.address = address; + this.paymentMethod = paymentMethod; + this.affiliation = affiliation; + } + + public abstract PaymentClassification getClassification(); + + public abstract PaymentSchedule getSchedule(); + + public void execute(){ + PaymentClassification pc=getClassification(); + PaymentSchedule ps=getSchedule(); + Employee e=new Employee(name, address); + e.setClassification(pc); + e.setSchedule(ps); + e.setPaymentMethod(paymentMethod); + e.setAffiliation(affiliation); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java new file mode 100644 index 0000000000..c7b92eafd3 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddHourlyEmployeeTransaction.java @@ -0,0 +1,27 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.AddEmployeeTransaction; +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class AddHourlyEmployeeTransaction extends AddEmployeeTransaction{ + private double rate; + public AddHourlyEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, + Affiliation affiliation) { + super(name, address, paymentMethod, affiliation); + this.rate=rate; + } + + @Override + public PaymentClassification getClassification() { + return new HourlyClassification(rate); + } + + @Override + public PaymentSchedule getSchedule() { + return new WeeklySchedule(); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java new file mode 100644 index 0000000000..4edfbd0d1e --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/AddSalariedEmployeeTransaction.java @@ -0,0 +1,27 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.AddEmployeeTransaction; +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class AddSalariedEmployeeTransaction extends AddEmployeeTransaction{ + private double salary; + public AddSalariedEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, + Affiliation affiliation) { + super(name, address, paymentMethod, affiliation); + this.salary=salary; + } + + @Override + public PaymentClassification getClassification() { + return new SalariedClassification(salary); + } + + @Override + public PaymentSchedule getSchedule() { + return new MonthlySchedule(); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java new file mode 100644 index 0000000000..2a37417717 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/BankMethod.java @@ -0,0 +1,15 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentMethod; + +public class BankMethod implements PaymentMethod{ + + private String bank; + private String account; + + @Override + public void pay(Paycheck pc) { + System.out.println("BankMethod"); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java new file mode 100644 index 0000000000..39ab695425 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/BiWeeklySchedule.java @@ -0,0 +1,22 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class BiWeeklySchedule implements PaymentSchedule { + Date firstPayableFriday = DateUtil.parseDate("2017-06-02"); + + @Override + public boolean isPayDate(Date date) { + int interval = DateUtil.getDaysBetween(firstPayableFriday, date); + return interval % 14 == 0; + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.add(payPeriodEndDate, -13); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java new file mode 100644 index 0000000000..758e5e8ba8 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/CommissionClassification.java @@ -0,0 +1,34 @@ +package com.coderising.payroll; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.util.DateUtil; + +public class CommissionClassification implements PaymentClassification{ + private double salary; + private double rate; + private Map receipts; + + public CommissionClassification(double rate, double salary) { + this.rate=rate; + this.salary=salary; + } + + public void addSalesReceipt(SalesReceipt sr) { + receipts.put(sr.getSaleDate(), sr); + } + + @Override + public double calculatePay(Paycheck pc) { + double commission=0; + for (SalesReceipt sr : receipts.values()) { + if (DateUtil.between(sr.getSaleDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + commission+=sr.getAmount()*rate; + } + } + return salary+commission; + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/Employee.java b/students/1158154002/src/main/java/com/coderising/payroll/Employee.java new file mode 100644 index 0000000000..45f503ab4a --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/Employee.java @@ -0,0 +1,55 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.api.PaymentMethod; +import com.coderising.payroll.api.PaymentSchedule; + +public class Employee { + String id; + String name; + String address; + + Affiliation affiliation; + PaymentClassification classification; + PaymentSchedule schedule; + PaymentMethod paymentMethod; + + public Employee(String name, String address){ + this.name = name; + this.address = address; + } + public boolean isPayDay(Date d) { + return schedule.isPayDate(d); + } + + public Date getPayPeriodStartDate(Date d) { + return schedule.getPayPeriodStartDate(d); + } + + public void payDay(Paycheck pc){ + double grossPay=classification.calculatePay(pc); + double deductions=affiliation.calculateDeductions(pc); + double netPay=grossPay-deductions; + pc.setGrossPay(grossPay); + pc.setDeductions(deductions); + pc.setNetPay(netPay); + paymentMethod.pay(pc); + } + + public void setClassification(PaymentClassification classification) { + this.classification = classification; + } + public void setSchedule(PaymentSchedule schedule) { + this.schedule = schedule; + } + public void setPaymentMethod(PaymentMethod paymentMethod) { + this.paymentMethod = paymentMethod; + } + + public void setAffiliation(Affiliation affiliation) { + this.affiliation = affiliation; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java new file mode 100644 index 0000000000..ec0892eb6a --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/HoldMethod.java @@ -0,0 +1,12 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentMethod; + +public class HoldMethod implements PaymentMethod{ + + @Override + public void pay(Paycheck pc) { + System.out.println("HoldMethod"); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java new file mode 100644 index 0000000000..6d61cae25e --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/HourlyClassification.java @@ -0,0 +1,42 @@ +package com.coderising.payroll; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.api.PaymentClassification; +import com.coderising.payroll.util.DateUtil; + +public class HourlyClassification implements PaymentClassification { + + private double rate; + private Map timeCards; + + public HourlyClassification(double rate) { + this.rate=rate; + } + + public void addTimeCard(TimeCard tc) { + timeCards.put(tc.getDate(), tc); + } + + @Override + public double calculatePay(Paycheck pc) { + double totalPay = 0; + for (TimeCard tc : timeCards.values()) { + if (DateUtil.between(tc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + totalPay+=calculatePayForTimeCard(tc); + } + } + return totalPay; + } + + private double calculatePayForTimeCard(TimeCard tc) { + int hours = tc.getHours(); + if (hours > 8) { + return 8 * rate + (hours - 8) * 1.5 * rate; + } else { + return 8 * rate; + } + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java new file mode 100644 index 0000000000..8cbcf755e0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/MailMethod.java @@ -0,0 +1,13 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentMethod; + +public class MailMethod implements PaymentMethod{ + private String address; + + @Override + public void pay(Paycheck pc) { + System.out.println("MailMethod"); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java new file mode 100644 index 0000000000..4b96edd28e --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/MonthlySchedule.java @@ -0,0 +1,20 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class MonthlySchedule implements PaymentSchedule{ + + @Override + public boolean isPayDate(Date date) { + return DateUtil.isLasyDayOfMonth(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.getFirstDay(payPeriodEndDate); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java new file mode 100644 index 0000000000..ec8b6bc5a4 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/NonAffiliation.java @@ -0,0 +1,12 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.Affiliation; + +public class NonAffiliation implements Affiliation{ + + @Override + public double calculateDeductions(Paycheck pc) { + return 0; + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java b/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java new file mode 100644 index 0000000000..5a7f0f87e0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/Paycheck.java @@ -0,0 +1,34 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class Paycheck { + private Date payPeriodStart; + private Date payPeriodEnd; + private double grossPay; + private double netPay; + private double deductions; + + public Paycheck(Date payPeriodStart, Date payPeriodEnd){ + this.payPeriodStart = payPeriodStart; + this.payPeriodEnd = payPeriodEnd; + } + public void setGrossPay(double grossPay) { + this.grossPay = grossPay; + + } + public void setDeductions(double deductions) { + this.deductions = deductions; + } + public void setNetPay(double netPay){ + this.netPay = netPay; + } + public Date getPayPeriodEndDate() { + + return this.payPeriodEnd; + } + public Date getPayPeriodStartDate() { + + return this.payPeriodStart; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java new file mode 100644 index 0000000000..8bc025e1d8 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/SalariedClassification.java @@ -0,0 +1,18 @@ +package com.coderising.payroll; + +import com.coderising.payroll.api.PaymentClassification; + +public class SalariedClassification implements PaymentClassification{ + private double salary; + + public SalariedClassification(double salary) { + this.salary=salary; + } + + @Override + public double calculatePay(Paycheck pc) { + // TODO Auto-generated method stub + return salary; + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java b/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java new file mode 100644 index 0000000000..25bbcd81bc --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/SalesReceipt.java @@ -0,0 +1,14 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class SalesReceipt { + private Date saleDate; + private double amount; + public Date getSaleDate() { + return saleDate; + } + public double getAmount() { + return amount; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java b/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java new file mode 100644 index 0000000000..4630f71f17 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/ServiceCharge.java @@ -0,0 +1,22 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class ServiceCharge { + private Date date; + private double amount; + public Date getDate() { + return date; + } + public void setDate(Date date) { + this.date = date; + } + public double getAmount() { + return amount; + } + public void setAmount(double amount) { + this.amount = amount; + } + + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java b/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java new file mode 100644 index 0000000000..0ee88399c5 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/TimeCard.java @@ -0,0 +1,15 @@ +package com.coderising.payroll; + +import java.util.Date; + +public class TimeCard { + private Date date; + private int hours; + + public Date getDate() { + return date; + } + public int getHours() { + return hours; + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java new file mode 100644 index 0000000000..7505b585a8 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/UnionAffiliation.java @@ -0,0 +1,35 @@ +package com.coderising.payroll; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.api.Affiliation; +import com.coderising.payroll.util.DateUtil; + +public class UnionAffiliation implements Affiliation{ + private String memberID; + private double weeklyDue; + private Map serviceCharges; + + public void addServiceCharge(ServiceCharge sc){ + serviceCharges.put(sc.getDate(), sc); + } + + @Override + public double calculateDeductions(Paycheck pc) { + double totalPay = 0; + for (ServiceCharge sc : serviceCharges.values()) { + if (DateUtil.between(sc.getDate(), pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate())) { + totalPay+=sc.getAmount(); + } + } + return totalPay+calculatePayForWeeklyDue(pc); + } + + private double calculatePayForWeeklyDue(Paycheck pc) { + int interval=DateUtil.getDaysBetween( pc.getPayPeriodStartDate(),pc.getPayPeriodEndDate()); + return interval/7*weeklyDue; + } + + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java new file mode 100644 index 0000000000..93e96d2412 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/WeeklySchedule.java @@ -0,0 +1,21 @@ +package com.coderising.payroll; + +import java.util.Date; + +import com.coderising.payroll.api.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class WeeklySchedule implements PaymentSchedule{ + + @Override + public boolean isPayDate(Date date) { + + return DateUtil.isFriday(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.add(payPeriodEndDate, -6); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java b/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java new file mode 100644 index 0000000000..8537092b94 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/AddEmployeeTransaction.java @@ -0,0 +1,34 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Employee; + +public abstract class AddEmployeeTransaction { + private String name; + private String address; + private PaymentMethod paymentMethod; + private Affiliation affiliation; + + + public AddEmployeeTransaction(String name, String address, PaymentMethod paymentMethod, Affiliation affiliation) { + super(); + this.name = name; + this.address = address; + this.paymentMethod = paymentMethod; + this.affiliation = affiliation; + } + + public abstract PaymentClassification getClassification(); + + public abstract PaymentSchedule getSchedule(); + + public void execute(){ + PaymentClassification pc=getClassification(); + PaymentSchedule ps=getSchedule(); + Employee e=new Employee(name, address); + e.setClassification(pc); + e.setSchedule(ps); + e.setPaymentMethod(paymentMethod); + e.setAffiliation(affiliation); + } + +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java b/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java new file mode 100644 index 0000000000..9a28cd1c46 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/Affiliation.java @@ -0,0 +1,7 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Paycheck; + +public interface Affiliation { + public double calculateDeductions(Paycheck pc); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java new file mode 100644 index 0000000000..66e1c6704f --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentClassification.java @@ -0,0 +1,7 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Paycheck; + +public interface PaymentClassification { + public double calculatePay(Paycheck pc); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java new file mode 100644 index 0000000000..2be20094b0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentMethod.java @@ -0,0 +1,7 @@ +package com.coderising.payroll.api; + +import com.coderising.payroll.Paycheck; + +public interface PaymentMethod { + public void pay(Paycheck pc); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java new file mode 100644 index 0000000000..520b6a2e98 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/api/PaymentSchedule.java @@ -0,0 +1,8 @@ +package com.coderising.payroll.api; + +import java.util.Date; + +public interface PaymentSchedule { + public boolean isPayDate(Date date); + public Date getPayPeriodStartDate( Date payPeriodEndDate); +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/package-info.java b/students/1158154002/src/main/java/com/coderising/payroll/package-info.java new file mode 100644 index 0000000000..149c6a9f42 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/package-info.java @@ -0,0 +1,8 @@ +/** + * + */ +/** + * @author Administrator + * + */ +package com.coderising.payroll; \ No newline at end of file diff --git a/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java b/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java new file mode 100644 index 0000000000..188bca74b0 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/service/PayrollService.java @@ -0,0 +1,29 @@ +package com.coderising.payroll.service; + +import java.util.Date; +import java.util.List; + +import com.coderising.payroll.Employee; +import com.coderising.payroll.Paycheck; + +public class PayrollService { + public List getAllEmployees(){ + return null; + } + + public void savePayCheck(Paycheck pc){} + + public static void main(String[] args) { + PayrollService payrollService=new PayrollService(); + Date date=new Date(); + List employees=payrollService.getAllEmployees(); + for (Employee e : employees) { + if (e.isPayDay(date)) { + Paycheck pc=new Paycheck(e.getPayPeriodStartDate(date), date); + e.payDay(pc); + payrollService.savePayCheck(pc); + } + } + + } +} diff --git a/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java b/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java new file mode 100644 index 0000000000..f2a3269b63 --- /dev/null +++ b/students/1158154002/src/main/java/com/coderising/payroll/util/DateUtil.java @@ -0,0 +1,65 @@ +package com.coderising.payroll.util; + +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Calendar; +import java.util.Date; + +public class DateUtil { + public static boolean isLasyDayOfMonth(Date date) { + Calendar b = Calendar.getInstance(); + b.setTime(date); + int lastDay = b.getActualMaximum(Calendar.DAY_OF_MONTH); + int now = b.get(Calendar.DAY_OF_MONTH); + return now == lastDay; + } + + public static Date getFirstDay(Date payPeriodEndDate) { + Calendar c = Calendar.getInstance(); + c.add(Calendar.MONTH, 0); + c.set(Calendar.DAY_OF_MONTH, 1); + return c.getTime(); + } + + public static Date add(Date date, int num) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + c.add(Calendar.DATE, num); + return c.getTime(); + } + + public static Date parseDate(String date) { + SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); + Date time = null; + try { + time = sdf.parse(date); + } catch (ParseException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + return time; + } + + public static boolean isFriday(Date date) { + Calendar c = Calendar.getInstance(); + c.setTime(date); + return c.get(Calendar.DAY_OF_WEEK) == 6; + } + + public static int getDaysBetween(Date start, Date end) { + Calendar aCalendar = Calendar.getInstance(); + aCalendar.setTime(end); + + int day1 = aCalendar.get(Calendar.DAY_OF_YEAR); + aCalendar.setTime(start); + + int day2 = aCalendar.get(Calendar.DAY_OF_YEAR); + + return day1 - day2; + } + + public static boolean between(Date saleDate, Date payPeriodStartDate, Date payPeriodEndDate) { + + return saleDate.getTime()>=payPeriodStartDate.getTime()&&saleDate.getTime()<=payPeriodEndDate.getTime(); + } +} From c5cdc2183a0cb1a527f52563905989d7139bb41f Mon Sep 17 00:00:00 2001 From: onlyliuxin <14703250@qq.com> Date: Mon, 10 Jul 2017 15:23:37 +0800 Subject: [PATCH 65/73] payroll code --- .../payroll/affiliation/NonAffiliation.java | 10 ++++ .../payroll/affiliation/UnionAffiliation.java | 14 +++++ .../CommissionedClassification.java | 31 ++++++++++ .../classification/HourlyClassification.java | 43 ++++++++++++++ .../SalariedClassification.java | 16 ++++++ .../payroll/{ => domain}/Affiliation.java | 2 +- .../payroll/{ => domain}/Employee.java | 14 +++-- .../coderising/payroll/domain/HoldMethod.java | 11 ++++ .../payroll/{ => domain}/Paycheck.java | 4 +- .../payroll/domain/PaydayTransaction.java | 21 +++++++ .../{ => domain}/PaymentClassification.java | 2 +- .../payroll/{ => domain}/PaymentMethod.java | 2 +- .../payroll/{ => domain}/PaymentSchedule.java | 2 +- .../payroll/domain/PayrollService.java | 46 +++++++++++++++ .../payroll/{ => domain}/SalesReceipt.java | 2 +- .../payroll/{ => domain}/TimeCard.java | 2 +- .../payroll/schedule/BiweeklySchedule.java | 38 +++++++++++++ .../payroll/schedule/MonthlySchedule.java | 20 +++++++ .../payroll/schedule/WeeklySchedule.java | 19 +++++++ .../com/coderising/payroll/util/DateUtil.java | 56 +++++++++++++++++++ .../transaction/AddEmployeeTransaction.java | 29 ++++++++++ .../AddHourlyEmployeeTransaction.java | 25 +++++++++ 22 files changed, 397 insertions(+), 12 deletions(-) create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/NonAffiliation.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/UnionAffiliation.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/CommissionedClassification.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/HourlyClassification.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/SalariedClassification.java rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/Affiliation.java (68%) rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/Employee.java (65%) create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/HoldMethod.java rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/Paycheck.java (90%) create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/PaymentClassification.java (69%) rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/PaymentMethod.java (63%) rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/PaymentSchedule.java (80%) create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/SalesReceipt.java (83%) rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{ => domain}/TimeCard.java (82%) create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/BiweeklySchedule.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/MonthlySchedule.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/WeeklySchedule.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/util/DateUtil.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/NonAffiliation.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/NonAffiliation.java new file mode 100644 index 0000000000..3cb6228aa4 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/NonAffiliation.java @@ -0,0 +1,10 @@ +package com.coderising.payroll.affiliation; + +import com.coderising.payroll.domain.Affiliation; +import com.coderising.payroll.domain.Paycheck; + +public class NonAffiliation implements Affiliation{ + public double calculateDeductions(Paycheck pc){ + return 0.0; + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/UnionAffiliation.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/UnionAffiliation.java new file mode 100644 index 0000000000..bbce4fa317 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/affiliation/UnionAffiliation.java @@ -0,0 +1,14 @@ +package com.coderising.payroll.affiliation; + +import com.coderising.payroll.domain.Affiliation; +import com.coderising.payroll.domain.Paycheck; + +public class UnionAffiliation implements Affiliation { + + @Override + public double calculateDeductions(Paycheck pc) { + + return 0; + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/CommissionedClassification.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/CommissionedClassification.java new file mode 100644 index 0000000000..f6a7ab4a63 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/CommissionedClassification.java @@ -0,0 +1,31 @@ +package com.coderising.payroll.classification; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.domain.Paycheck; +import com.coderising.payroll.domain.PaymentClassification; +import com.coderising.payroll.domain.SalesReceipt; +import com.coderising.payroll.util.DateUtil; + +public class CommissionedClassification implements PaymentClassification { + double salary; + double rate; + public CommissionedClassification(double salary , double rate){ + this.salary = salary; + this.rate = rate; + } + Map receipts; + @Override + public double calculatePay(Paycheck pc) { + double commission = 0.0; + for(SalesReceipt sr : receipts.values()){ + if(DateUtil.between(sr.getSaleDate(), pc.getPayPeriodStartDate(), + pc.getPayPeriodEndDate())){ + commission += sr.getAmount() * rate; + } + } + return salary + commission; + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/HourlyClassification.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/HourlyClassification.java new file mode 100644 index 0000000000..1238ac84a6 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/HourlyClassification.java @@ -0,0 +1,43 @@ +package com.coderising.payroll.classification; + +import java.util.Date; +import java.util.Map; + +import com.coderising.payroll.domain.Paycheck; +import com.coderising.payroll.domain.PaymentClassification; +import com.coderising.payroll.domain.TimeCard; +import com.coderising.payroll.util.DateUtil; + +public class HourlyClassification implements PaymentClassification { + private double rate; + private Map timeCards; + + public HourlyClassification(double hourlyRate) { + this.rate = hourlyRate; + } + public void addTimeCard(TimeCard tc){ + timeCards.put(tc.getDate(), tc); + } + @Override + public double calculatePay(Paycheck pc) { + double totalPay = 0; + for(TimeCard tc : timeCards.values()){ + if(DateUtil.between(tc.getDate(), pc.getPayPeriodStartDate(), + pc.getPayPeriodEndDate())){ + totalPay += calculatePayForTimeCard(tc); + } + } + return totalPay; + + } + private double calculatePayForTimeCard(TimeCard tc) { + int hours = tc.getHours(); + + if(hours > 8){ + return 8*rate + (hours-8) * rate * 1.5; + } else{ + return 8*rate; + } + } +} + diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/SalariedClassification.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/SalariedClassification.java new file mode 100644 index 0000000000..796aae93f1 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/classification/SalariedClassification.java @@ -0,0 +1,16 @@ +package com.coderising.payroll.classification; + +import com.coderising.payroll.domain.Paycheck; +import com.coderising.payroll.domain.PaymentClassification; + +public class SalariedClassification implements PaymentClassification { + private double salary; + public SalariedClassification(double salary){ + this.salary = salary; + } + @Override + public double calculatePay(Paycheck pc) { + return salary; + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Affiliation.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Affiliation.java similarity index 68% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Affiliation.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Affiliation.java index 091165a2af..74a6b404bc 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Affiliation.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Affiliation.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; public interface Affiliation { public double calculateDeductions(Paycheck pc); diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Employee.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java similarity index 65% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Employee.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java index 923297c91a..9eb9af15f3 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Employee.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; import java.util.Date; @@ -18,15 +18,21 @@ public Employee(String name, String address){ this.address = address; } public boolean isPayDay(Date d) { - return false; + return this.schedule.isPayDate(d); } public Date getPayPeriodStartDate(Date d) { - return null; + return this.schedule.getPayPeriodStartDate(d); } public void payDay(Paycheck pc){ - + double grossPay = classification.calculatePay(pc); + double deductions = affiliation.calculateDeductions(pc); + double netPay = grossPay - deductions; + pc.setGrossPay(grossPay); + pc.setDeductions(deductions); + pc.setNetPay(netPay); + paymentMethod.pay(pc); } public void setClassification(PaymentClassification classification) { diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/HoldMethod.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/HoldMethod.java new file mode 100644 index 0000000000..0ce19e2291 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/HoldMethod.java @@ -0,0 +1,11 @@ +package com.coderising.payroll.domain; + +public class HoldMethod implements PaymentMethod { + + @Override + public void pay(Paycheck pc) { + + + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Paycheck.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Paycheck.java similarity index 90% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Paycheck.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Paycheck.java index 802c8b5c45..6f1ff99413 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/Paycheck.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Paycheck.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; import java.util.Date; import java.util.Map; @@ -9,7 +9,7 @@ public class Paycheck { private double grossPay; private double netPay; private double deductions; - + private Map itsFields; public Paycheck(Date payPeriodStart, Date payPeriodEnd){ this.payPeriodStart = payPeriodStart; this.payPeriodEnd = payPeriodEnd; diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java new file mode 100644 index 0000000000..2774b16b69 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java @@ -0,0 +1,21 @@ +package com.coderising.payroll.domain; + +import java.util.Date; +import java.util.List; + +public class PaydayTransaction { + private Date date; + private PayrollService payrollService; + + public void execute(){ + List employees = payrollService.getAllEmployees(); + for(Employee e : employees){ + if(e.isPayDay(date)){ + Paycheck pc = new Paycheck(e.getPayPeriodStartDate(date),date); + e.payDay(pc); + payrollService.savePaycheck(pc); + } + } + } +} + diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentClassification.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentClassification.java similarity index 69% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentClassification.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentClassification.java index f2bf2e26e9..b6f2120bdb 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentClassification.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentClassification.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; public interface PaymentClassification { public double calculatePay(Paycheck pc); diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentMethod.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentMethod.java similarity index 63% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentMethod.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentMethod.java index 5e549916b6..f07cc5354b 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentMethod.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentMethod.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; public interface PaymentMethod { public void pay(Paycheck pc); diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentSchedule.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentSchedule.java similarity index 80% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentSchedule.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentSchedule.java index 500d72404d..96788f4f80 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PaymentSchedule.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaymentSchedule.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; import java.util.Date; diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java new file mode 100644 index 0000000000..a6d244bbe0 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java @@ -0,0 +1,46 @@ +package com.coderising.payroll.domain; + +import java.util.List; + +import com.coderising.payroll.classification.CommissionedClassification; +import com.coderising.payroll.classification.HourlyClassification; +import com.coderising.payroll.classification.SalariedClassification; +import com.coderising.payroll.schedule.BiweeklySchedule; +import com.coderising.payroll.schedule.MonthlySchedule; +import com.coderising.payroll.schedule.WeeklySchedule; + +public class PayrollService { + public List getAllEmployees(){ + return null; + } + public void savePaycheck(Paycheck pc){ + + } + + public Employee addHourlyEmployee(String name, String address, double hourlyRate){ + Employee e = new Employee(name, address); + e.setClassification(new HourlyClassification(hourlyRate)); + e.setSchedule(new WeeklySchedule()); + e.setPaymentMethod(new HoldMethod()); + //保存员工到数据库.. 略 + return e; + } + + public Employee addSalariedEmployee(String name, String address, double salary){ + Employee e = new Employee(name, address); + e.setClassification(new SalariedClassification(salary)); + e.setSchedule(new MonthlySchedule()); + e.setPaymentMethod(new HoldMethod()); + //保存员工到数据库.. 略 + return e; + } + + public Employee addCommissionedEmployee(String name, String address, double salary, double saleRate){ + Employee e = new Employee(name, address); + e.setClassification(new CommissionedClassification(salary, saleRate)); + e.setSchedule(new BiweeklySchedule()); + e.setPaymentMethod(new HoldMethod()); + //保存员工到数据库.. 略 + return e; + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/SalesReceipt.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/SalesReceipt.java similarity index 83% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/SalesReceipt.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/SalesReceipt.java index fcd3b506fc..a7b0ba41ad 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/SalesReceipt.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/SalesReceipt.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; import java.util.Date; diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/TimeCard.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/TimeCard.java similarity index 82% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/TimeCard.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/TimeCard.java index 735cc17ac1..ebf6e17a4c 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/TimeCard.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/TimeCard.java @@ -1,4 +1,4 @@ -package com.coderising.payroll; +package com.coderising.payroll.domain; import java.util.Date; diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/BiweeklySchedule.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/BiweeklySchedule.java new file mode 100644 index 0000000000..35ec65c49c --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/BiweeklySchedule.java @@ -0,0 +1,38 @@ +package com.coderising.payroll.schedule; + +import java.text.SimpleDateFormat; +import java.util.Date; + +import com.coderising.payroll.domain.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class BiweeklySchedule implements PaymentSchedule { + Date firstPayableFriday = DateUtil.parseDate("2017-6-2"); + + @Override + public boolean isPayDate(Date date) { + + long interval = DateUtil.getDaysBetween(firstPayableFriday, date); + return interval % 14 == 0; + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.add(payPeriodEndDate, -13); + + } + + public static void main(String [] args) throws Exception{ + BiweeklySchedule schedule = new BiweeklySchedule(); + + SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd"); + Date d = sdf.parse("2017-06-30"); + + System.out.println(schedule.isPayDate(d)); + + System.out.println(DateUtil.isFriday(d)); + + System.out.println(schedule.getPayPeriodStartDate(d)); + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/MonthlySchedule.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/MonthlySchedule.java new file mode 100644 index 0000000000..dbbe732d2f --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/MonthlySchedule.java @@ -0,0 +1,20 @@ +package com.coderising.payroll.schedule; + +import java.util.Date; + +import com.coderising.payroll.domain.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class MonthlySchedule implements PaymentSchedule { + + @Override + public boolean isPayDate(Date date) { + return DateUtil.isLastDayOfMonth(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.getFirstDay(payPeriodEndDate); + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/WeeklySchedule.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/WeeklySchedule.java new file mode 100644 index 0000000000..54a22ab7db --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/schedule/WeeklySchedule.java @@ -0,0 +1,19 @@ +package com.coderising.payroll.schedule; + +import java.util.Date; + +import com.coderising.payroll.domain.PaymentSchedule; +import com.coderising.payroll.util.DateUtil; + +public class WeeklySchedule implements PaymentSchedule { + + @Override + public boolean isPayDate(Date date) { + return DateUtil.isFriday(date); + } + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.add(payPeriodEndDate, -6); + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/util/DateUtil.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/util/DateUtil.java new file mode 100644 index 0000000000..ffc26f31a1 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/util/DateUtil.java @@ -0,0 +1,56 @@ +package com.coderising.payroll.util; + +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Calendar; +import java.util.Date; + +public class DateUtil { + public static long getDaysBetween(Date d1, Date d2){ + + return (d2.getTime() - d1.getTime())/(24*60*60*1000); + } + + public static Date parseDate(String txtDate){ + SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd"); + try { + return sdf.parse(txtDate); + } catch (ParseException e) { + e.printStackTrace(); + return null; + } + } + public static boolean isFriday(Date d){ + Calendar calendar = Calendar.getInstance(); + return calendar.get(Calendar.DAY_OF_WEEK) == 5; + } + + public static Date add(Date d, int days){ + Calendar calendar = Calendar.getInstance(); + calendar.setTime(d); + calendar.add(Calendar.DATE, days); + return calendar.getTime(); + } + + public static boolean isLastDayOfMonth(Date d){ + Calendar calendar=Calendar.getInstance(); + calendar.setTime(d); + return calendar.get(Calendar.DATE)==calendar.getActualMaximum(Calendar.DAY_OF_MONTH); + } + public static Date getFirstDay(Date d){ + Calendar calendar=Calendar.getInstance(); + calendar.setTime(d); + int day = calendar.get(Calendar.DATE); + calendar.add(Calendar.DATE, -(day-1)); + return calendar.getTime(); + } + public static void main(String [] args) throws Exception{ + System.out.println(DateUtil.isLastDayOfMonth(DateUtil.parseDate("2017-6-29"))); + + System.out.println(DateUtil.getFirstDay(DateUtil.parseDate("2017-6-30"))); + } + + public static boolean between(Date d, Date date1, Date date2){ + return d.after(date1) && d.before(date2); + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java b/liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java new file mode 100644 index 0000000000..944f0deb78 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java @@ -0,0 +1,29 @@ +package transaction; + +import com.coderising.payroll.domain.Employee; +import com.coderising.payroll.domain.HoldMethod; +import com.coderising.payroll.domain.PaymentClassification; +import com.coderising.payroll.domain.PaymentMethod; +import com.coderising.payroll.domain.PaymentSchedule; + +public abstract class AddEmployeeTransaction { + private String name; + private String address; + public AddEmployeeTransaction(String name,String address){ + this.name = name; + this.address = address; + } + public abstract PaymentClassification getClassification(); + public abstract PaymentSchedule getSchedule(); + + public void execute(){ + PaymentClassification pc = getClassification(); + PaymentSchedule ps = getSchedule(); + PaymentMethod pm = new HoldMethod(); + Employee e = new Employee(name, address); + e.setClassification(pc); + e.setSchedule(ps); + e.setPaymentMethod(pm); + //保存到数据库, 略 + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java b/liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java new file mode 100644 index 0000000000..1c0ab3c57b --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java @@ -0,0 +1,25 @@ +package transaction; + +import com.coderising.payroll.classification.HourlyClassification; +import com.coderising.payroll.domain.PaymentClassification; +import com.coderising.payroll.domain.PaymentSchedule; +import com.coderising.payroll.schedule.WeeklySchedule; + +public class AddHourlyEmployeeTransaction extends AddEmployeeTransaction{ + private double rate; + AddHourlyEmployeeTransaction(String name, String address, double hourlyRate) { + super(name, address); + this.rate = hourlyRate; + } + @Override + public PaymentClassification getClassification() { + return new HourlyClassification(rate); + } + + @Override + public PaymentSchedule getSchedule() { + + return new WeeklySchedule(); + } +} + From 323a02aa6dd75df1b2e6e53f48f69bb76dc312a7 Mon Sep 17 00:00:00 2001 From: onlyliuxin <14703250@qq.com> Date: Mon, 10 Jul 2017 15:26:10 +0800 Subject: [PATCH 66/73] payroll code --- .../coderising/payroll}/transaction/AddEmployeeTransaction.java | 2 +- .../payroll}/transaction/AddHourlyEmployeeTransaction.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) rename liuxin/ood/ood-assignment/src/main/java/{ => com/coderising/payroll}/transaction/AddEmployeeTransaction.java (95%) rename liuxin/ood/ood-assignment/src/main/java/{ => com/coderising/payroll}/transaction/AddHourlyEmployeeTransaction.java (93%) diff --git a/liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/transaction/AddEmployeeTransaction.java similarity index 95% rename from liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/transaction/AddEmployeeTransaction.java index 944f0deb78..39b268486b 100644 --- a/liuxin/ood/ood-assignment/src/main/java/transaction/AddEmployeeTransaction.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/transaction/AddEmployeeTransaction.java @@ -1,4 +1,4 @@ -package transaction; +package com.coderising.payroll.transaction; import com.coderising.payroll.domain.Employee; import com.coderising.payroll.domain.HoldMethod; diff --git a/liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/transaction/AddHourlyEmployeeTransaction.java similarity index 93% rename from liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/transaction/AddHourlyEmployeeTransaction.java index 1c0ab3c57b..2039734479 100644 --- a/liuxin/ood/ood-assignment/src/main/java/transaction/AddHourlyEmployeeTransaction.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/transaction/AddHourlyEmployeeTransaction.java @@ -1,4 +1,4 @@ -package transaction; +package com.coderising.payroll.transaction; import com.coderising.payroll.classification.HourlyClassification; import com.coderising.payroll.domain.PaymentClassification; From 22d8938cccf95b0bf770f3cd836535ec0e9036ec Mon Sep 17 00:00:00 2001 From: onlyliuxin <14703250@qq.com> Date: Mon, 10 Jul 2017 15:27:24 +0800 Subject: [PATCH 67/73] paroll code --- .../com/coderising/payroll/{domain => }/PayrollService.java | 5 ++++- .../com/coderising/payroll/domain/PaydayTransaction.java | 2 ++ 2 files changed, 6 insertions(+), 1 deletion(-) rename liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/{domain => }/PayrollService.java (89%) diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PayrollService.java similarity index 89% rename from liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java rename to liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PayrollService.java index a6d244bbe0..b0b4fec82f 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PayrollService.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/PayrollService.java @@ -1,10 +1,13 @@ -package com.coderising.payroll.domain; +package com.coderising.payroll; import java.util.List; import com.coderising.payroll.classification.CommissionedClassification; import com.coderising.payroll.classification.HourlyClassification; import com.coderising.payroll.classification.SalariedClassification; +import com.coderising.payroll.domain.Employee; +import com.coderising.payroll.domain.HoldMethod; +import com.coderising.payroll.domain.Paycheck; import com.coderising.payroll.schedule.BiweeklySchedule; import com.coderising.payroll.schedule.MonthlySchedule; import com.coderising.payroll.schedule.WeeklySchedule; diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java index 2774b16b69..e066e46263 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/PaydayTransaction.java @@ -3,6 +3,8 @@ import java.util.Date; import java.util.List; +import com.coderising.payroll.PayrollService; + public class PaydayTransaction { private Date date; private PayrollService payrollService; From 3aa27a392f54d440c342abb80a69a66719011946 Mon Sep 17 00:00:00 2001 From: onlyliuxin <14703250@qq.com> Date: Mon, 10 Jul 2017 16:05:38 +0800 Subject: [PATCH 68/73] payroll code --- .../com/coderising/dp/builder/TagBuilder.java | 37 +++++++++ .../coderising/dp/builder/TagBuilderTest.java | 40 +++++++++ .../com/coderising/dp/builder/TagNode.java | 82 +++++++++++++++++++ .../com/coderising/dp/decorator/Email.java | 6 ++ .../dp/decorator/EmailDecorator.java | 5 ++ .../coderising/dp/decorator/EmailImpl.java | 12 +++ .../coderising/ood/srp/good1/MailSender.java | 1 + .../coderising/ood/srp/product_promotion.txt | 5 ++ .../coderising/payroll/domain/Employee.java | 14 ++-- 9 files changed, 195 insertions(+), 7 deletions(-) create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilderTest.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagNode.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/Email.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailDecorator.java create mode 100644 liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailImpl.java diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java new file mode 100644 index 0000000000..daa431f139 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java @@ -0,0 +1,37 @@ +package com.coderising.dp.builder; + +public class TagBuilder { + private TagNode rootNode; + private TagNode currentNode; + private TagNode parentNode; + public TagBuilder(String rootTagName){ + rootNode = new TagNode(rootTagName); + currentNode = rootNode; + parentNode = null; + } + + public TagBuilder addChild(String childTagName){ + parentNode = this.currentNode; + this.currentNode = new TagNode(childTagName); + parentNode.add(currentNode); + return this; + } + public TagBuilder addSibling(String siblingTagName){ + + this.currentNode = new TagNode(siblingTagName); + parentNode.add(this.currentNode); + return this; + + } + public TagBuilder setAttribute(String name, String value){ + this.currentNode.setAttribute(name, value); + return this; + } + public TagBuilder setText(String value){ + this.currentNode.setValue(value); + return this; + } + public String toXML(){ + return this.rootNode.toXML(); + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilderTest.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilderTest.java new file mode 100644 index 0000000000..e30d20285b --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilderTest.java @@ -0,0 +1,40 @@ +package com.coderising.dp.builder; + +import static org.junit.Assert.*; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +public class TagBuilderTest { + + @Before + public void setUp() throws Exception { + } + + @After + public void tearDown() throws Exception { + } + + @Test + public void testToXML() { + + TagBuilder builder = new TagBuilder("order"); + + String xml = builder.addChild("line-items") + .addChild("line-item").setAttribute("pid", "P3677").setAttribute("qty", "3") + .addSibling("line-item").setAttribute("pid", "P9877").setAttribute("qty", "10") + .toXML(); + + String expected = "" + + "" + + "" + + "" + + "" + + ""; + + System.out.println(xml); + assertEquals(expected, xml); + } + +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagNode.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagNode.java new file mode 100644 index 0000000000..7763ee9d0a --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagNode.java @@ -0,0 +1,82 @@ +package com.coderising.dp.builder; + +import java.util.ArrayList; +import java.util.List; + +public class TagNode { + private String tagName; + private String tagValue; + private List children = new ArrayList<>(); + private List attributes = new ArrayList<>(); + + public TagNode(String name){ + this.tagName = name; + } + public void add(TagNode child){ + this.children.add(child); + } + public void setAttribute(String name, String value) { + Attribute attr = findAttribute(name); + if(attr != null){ + attr.value = value; + } + + attributes.add(new Attribute(name,value)); + } + private Attribute findAttribute(String name){ + for(Attribute attr : attributes){ + if(attr.name.equals(name)){ + return attr; + } + } + return null; + } + public void setValue(String value) { + this.tagValue = value; + + } + public String getTagName() { + return tagName; + } + public List getChildren() { + return children; + } + + private static class Attribute{ + public Attribute(String name, String value) { + this.name = name; + this.value = value; + } + String name; + String value; + + } + public String toXML(){ + return toXML(this); + } + private String toXML(TagNode node){ + StringBuilder buffer = new StringBuilder(); + buffer.append("<").append(node.tagName); + if(node.attributes.size()> 0){ + for(int i=0;i"); + return buffer.toString(); + } + buffer.append(">"); + for(TagNode childNode : node.children){ + buffer.append(toXML(childNode)); + } + buffer.append(""); + + + return buffer.toString(); + } + private String toXML(Attribute attr){ + return attr.name+"=\""+attr.value + "\""; + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/Email.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/Email.java new file mode 100644 index 0000000000..064de1e837 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/Email.java @@ -0,0 +1,6 @@ +package com.coderising.dp.decorator; + +public interface Email { + public String getContent(); +} + diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailDecorator.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailDecorator.java new file mode 100644 index 0000000000..d5379b0dd9 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailDecorator.java @@ -0,0 +1,5 @@ +package com.coderising.dp.decorator; + +public abstract class EmailDecorator implements Email{ + +} \ No newline at end of file diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailImpl.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailImpl.java new file mode 100644 index 0000000000..640aef6da3 --- /dev/null +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/decorator/EmailImpl.java @@ -0,0 +1,12 @@ +package com.coderising.dp.decorator; + +public class EmailImpl implements Email { + private String content; + + public EmailImpl(String content) { + this.content = content; + } + public String getContent() { + return content; + } +} diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/good1/MailSender.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/good1/MailSender.java index 0503d1a88b..ffd0543e22 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/good1/MailSender.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/good1/MailSender.java @@ -1,5 +1,6 @@ package com.coderising.ood.srp.good1; + public class MailSender { private String fromAddress ; diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt index 0c0124cc61..618f02b102 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -1,3 +1,8 @@ + + + + + P8756 iPhone8 P3946 XiaoMi10 P8904 Oppo_R15 diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java index 9eb9af15f3..204180a672 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/payroll/domain/Employee.java @@ -3,15 +3,15 @@ import java.util.Date; public class Employee { - String id; - String name; - String address; - Affiliation affiliation; + private String id; + private String name; + private String address; + private Affiliation affiliation; - PaymentClassification classification; - PaymentSchedule schedule; - PaymentMethod paymentMethod; + private PaymentClassification classification; + private PaymentSchedule schedule; + private PaymentMethod paymentMethod; public Employee(String name, String address){ this.name = name; From a98dea43a6c2e380ac86b5fc00c24f16194689bb Mon Sep 17 00:00:00 2001 From: onlyliuxin <14703250@qq.com> Date: Mon, 10 Jul 2017 16:10:13 +0800 Subject: [PATCH 69/73] tag builder --- .../com/coderising/dp/builder/TagBuilder.java | 29 +++++++------------ 1 file changed, 11 insertions(+), 18 deletions(-) diff --git a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java index daa431f139..fe8673ec30 100644 --- a/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java +++ b/liuxin/ood/ood-assignment/src/main/java/com/coderising/dp/builder/TagBuilder.java @@ -1,37 +1,30 @@ package com.coderising.dp.builder; public class TagBuilder { - private TagNode rootNode; - private TagNode currentNode; - private TagNode parentNode; + public TagBuilder(String rootTagName){ - rootNode = new TagNode(rootTagName); - currentNode = rootNode; - parentNode = null; + } public TagBuilder addChild(String childTagName){ - parentNode = this.currentNode; - this.currentNode = new TagNode(childTagName); - parentNode.add(currentNode); - return this; + + return null; } public TagBuilder addSibling(String siblingTagName){ - this.currentNode = new TagNode(siblingTagName); - parentNode.add(this.currentNode); - return this; + + return null; } public TagBuilder setAttribute(String name, String value){ - this.currentNode.setAttribute(name, value); - return this; + + return null; } public TagBuilder setText(String value){ - this.currentNode.setValue(value); - return this; + + return null; } public String toXML(){ - return this.rootNode.toXML(); + return null; } } From e69f85c05753d876dd21a0f6e5f0045bbaafbd6b Mon Sep 17 00:00:00 2001 From: readke Date: Tue, 11 Jul 2017 01:31:03 +0800 Subject: [PATCH 70/73] =?UTF-8?q?=E7=AC=AC=E4=B8=80=E6=AC=A1=E4=BD=9C?= =?UTF-8?q?=E4=B8=9Alinxin=E7=9B=AE=E5=BD=95=E4=B8=8B=E6=96=87=E4=BB=B6?= =?UTF-8?q?=E4=BF=AE=E6=94=B9=E8=AF=AF=E6=8F=90=E4=BA=A4=EF=BC=8C=E7=8E=B0?= =?UTF-8?q?=E5=9C=A8=E9=87=8D=E6=8F=90=E4=BA=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../724222786/ood/ood-assignment/.gitignore | 4 + students/724222786/ood/ood-assignment/pom.xml | 38 ++++ .../java/com/coderising/ood/answer/Test.java | 23 ++ .../ood/answer/config/config.properties | 5 + .../ood/answer/config/product_promotion.txt | 4 + .../ood/answer/entity/MailMessage.java | 63 ++++++ .../coderising/ood/answer/entity/Product.java | 38 ++++ .../coderising/ood/answer/entity/User.java | 35 +++ .../ood/answer/service/MailService.java | 27 +++ .../ood/answer/utils/ConfigUtils.java | 48 +++++ .../coderising/ood/answer/utils/DBUtils.java | 32 +++ .../ood/answer/utils/FileUtils.java | 39 ++++ .../ood/answer/utils/MailUtils.java | 49 +++++ .../ood/answer/utils/ProductUtils.java | 52 +++++ .../com/coderising/ood/srp/Configuration.java | 23 ++ .../coderising/ood/srp/ConfigurationKeys.java | 9 + .../java/com/coderising/ood/srp/DBUtil.java | 25 +++ .../java/com/coderising/ood/srp/MailUtil.java | 18 ++ .../com/coderising/ood/srp/PromotionMail.java | 199 ++++++++++++++++++ .../coderising/ood/srp/product_promotion.txt | 4 + .../ood-assignment/src/main/java/log4j2.xml | 13 ++ 21 files changed, 748 insertions(+) create mode 100644 students/724222786/ood/ood-assignment/.gitignore create mode 100644 students/724222786/ood/ood-assignment/pom.xml create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/Test.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/config.properties create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/product_promotion.txt create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/MailMessage.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/Product.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/User.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/service/MailService.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ConfigUtils.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/DBUtils.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/FileUtils.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/MailUtils.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ProductUtils.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java create mode 100644 students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt create mode 100644 students/724222786/ood/ood-assignment/src/main/java/log4j2.xml diff --git a/students/724222786/ood/ood-assignment/.gitignore b/students/724222786/ood/ood-assignment/.gitignore new file mode 100644 index 0000000000..c948edfead --- /dev/null +++ b/students/724222786/ood/ood-assignment/.gitignore @@ -0,0 +1,4 @@ +.settings\ +target\ +.classpath +.project \ No newline at end of file diff --git a/students/724222786/ood/ood-assignment/pom.xml b/students/724222786/ood/ood-assignment/pom.xml new file mode 100644 index 0000000000..a4d92e7f05 --- /dev/null +++ b/students/724222786/ood/ood-assignment/pom.xml @@ -0,0 +1,38 @@ + + 4.0.0 + + com.coderising + ood-assignment + 0.0.1-SNAPSHOT + jar + + ood-assignment + http://maven.apache.org + + + UTF-8 + + + + + + junit + junit + 4.12 + + + + org.apache.logging.log4j + log4j-core + 2.8.2 + + + + + diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/Test.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/Test.java new file mode 100644 index 0000000000..8dc90b701e --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/Test.java @@ -0,0 +1,23 @@ +package com.coderising.ood.answer; + +import java.util.List; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +import com.coderising.ood.answer.entity.Product; +import com.coderising.ood.answer.service.MailService; +import com.coderising.ood.answer.utils.FileUtils; +import com.coderising.ood.answer.utils.ProductUtils; + +public class Test { + private static final Logger log = LogManager.getLogger(Test.class); + public static void main(String[] args) { + MailService service = new MailService(); + List list = ProductUtils.getList(FileUtils.readFile()); + service.sendMail(list); + + } + + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/config.properties b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/config.properties new file mode 100644 index 0000000000..b798e9274a --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/config.properties @@ -0,0 +1,5 @@ +smtp.server=smtp.163.com +alt.smtp.server=smtp1.163.com +email.admin=admin@company.com + +product.txt=com/coderising/ood/answer/config/product_promotion.txt \ No newline at end of file diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/product_promotion.txt b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/config/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/MailMessage.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/MailMessage.java new file mode 100644 index 0000000000..cb95f6296c --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/MailMessage.java @@ -0,0 +1,63 @@ +package com.coderising.ood.answer.entity; + +import java.io.Serializable; + +import com.coderising.ood.answer.utils.ConfigUtils; + +/** + * 邮件类 + * @author readke + * + */ +public class MailMessage implements Serializable{ + + private static final long serialVersionUID = -3221160075625357827L; + + private String toAddr; + private String fromAddr; + private String subject; + private String content; + + public static MailMessage getMessage(String from,String subject,String content,Product p,User u){ + MailMessage m = new MailMessage(); + if(content != null && !content.isEmpty()) + content = "尊敬的 "+u.getName()+", 您关注的产品 " + p.getpDec() + " 降价了,欢迎购买!" ; + if(subject != null && !subject.isEmpty()){ + subject = "您关注的产品降价了"; + } + if(from != null && !from.isEmpty()){ + from = ConfigUtils.getProperty("smtp.server"); + } + m.setFromAddr(from); + m.setToAddr(u.getEmail()); + m.setSubject(subject); + m.setContent(content); + return m; + } + + public String getToAddr() { + return toAddr; + } + public void setToAddr(String toAddr) { + this.toAddr = toAddr; + } + public String getFromAddr() { + return fromAddr; + } + public void setFromAddr(String fromAddr) { + this.fromAddr = fromAddr; + } + public String getSubject() { + return subject; + } + public void setSubject(String subject) { + this.subject = subject; + } + public String getContent() { + return content; + } + public void setContent(String content) { + this.content = content; + } + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/Product.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/Product.java new file mode 100644 index 0000000000..2b4a81535e --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/Product.java @@ -0,0 +1,38 @@ +package com.coderising.ood.answer.entity; + +import java.io.Serializable; + +/** + * 产品类 + * @author readke + * + */ +public class Product implements Serializable{ + private static final long serialVersionUID = 409352331475497580L; + + private String pId; + private String pDec; + + public Product() { + + } + public Product(String pId, String pDec) { + super(); + this.pId = pId; + this.pDec = pDec; + } + public String getpId() { + return pId; + } + public void setpId(String pId) { + this.pId = pId; + } + public String getpDec() { + return pDec; + } + public void setpDec(String pDec) { + this.pDec = pDec; + } + + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/User.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/User.java new file mode 100644 index 0000000000..dd71a8e26f --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/entity/User.java @@ -0,0 +1,35 @@ +package com.coderising.ood.answer.entity; + +import java.io.Serializable; + +/** + * 用户类 + * @author readke + * + */ +public class User implements Serializable{ + private static final long serialVersionUID = -7916484660512326120L; + + private String id; + private String name; + private String email; + public String getId() { + return id; + } + public void setId(String id) { + this.id = id; + } + public String getName() { + return name; + } + public void setName(String name) { + this.name = name; + } + public String getEmail() { + return email; + } + public void setEmail(String email) { + this.email = email; + } + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/service/MailService.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/service/MailService.java new file mode 100644 index 0000000000..cb63b8a2d1 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/service/MailService.java @@ -0,0 +1,27 @@ +package com.coderising.ood.answer.service; + +import java.util.List; + +import com.coderising.ood.answer.entity.MailMessage; +import com.coderising.ood.answer.entity.Product; +import com.coderising.ood.answer.entity.User; +import com.coderising.ood.answer.utils.DBUtils; +import com.coderising.ood.answer.utils.MailUtils; + +/** + * 邮件发送服务 + * @author readke + * + */ +public class MailService { + public void sendMail(List list){ + + for(Product p: list){ + List uList = DBUtils.queryByProductID(p.getpId()); + for(User u : uList){ + MailMessage m = MailMessage.getMessage("","", "", p, u); + MailUtils.sendMail(m); + } + } + } +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ConfigUtils.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ConfigUtils.java new file mode 100644 index 0000000000..3b67cbf5fb --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ConfigUtils.java @@ -0,0 +1,48 @@ +package com.coderising.ood.answer.utils; + +import java.io.IOException; +import java.io.InputStream; +import java.util.Properties; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +/** + * 配置文件读取工具 + * @author readke + * + */ +public class ConfigUtils { + + private static final Logger log = LogManager.getLogger(ConfigUtils.class); + private static Properties prop = null; + + static { + InputStream in = ConfigUtils.class.getResourceAsStream("../config/config.properties"); + prop = new Properties(); + //System.out.println(in); + try { + prop.load(in); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + }finally { + if(in != null){ + try { + in.close(); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + } + } + + public static String getProperty(String key){ + return prop.getProperty(key); + } + + public static void main(String[] args) { + log.info(ConfigUtils.getProperty("smtp.server")); + } +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/DBUtils.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/DBUtils.java new file mode 100644 index 0000000000..757098ef6c --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/DBUtils.java @@ -0,0 +1,32 @@ +package com.coderising.ood.answer.utils; + +import java.util.ArrayList; +import java.util.List; + +import com.coderising.ood.answer.entity.User; + +/** + * db工具 + * @author readke + * + */ +public class DBUtils { + + public static List queryByProductID(String productID){ + /** + * sql = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + */ + List userList = new ArrayList(); + + for (int i = 1; i <= 3; i++) { + User userInfo = new User(); + userInfo.setName("User" + i); + userInfo.setEmail("aa@bb.com"); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/FileUtils.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/FileUtils.java new file mode 100644 index 0000000000..03dfcfe66d --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/FileUtils.java @@ -0,0 +1,39 @@ +package com.coderising.ood.answer.utils; + +import java.io.BufferedReader; +import java.io.File; +import java.net.URI; +import java.net.URL; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +/** + * 文件读取工具 + * @author readke + * + */ +public class FileUtils { + private static final Logger log = LogManager.getLogger(FileUtils.class); + public static File readFile(){ + + File file = null; + BufferedReader br = null; + + try { + URL url = FileUtils.class.getClassLoader().getResource(ConfigUtils.getProperty("product.txt")); + log.info(url.getPath()); + URI uri = url.toURI(); + file = new File(uri); + + }catch (Exception e) { + // TODO: handle exception + e.printStackTrace(); + } + return file; + } + + public static void main(String[] args) { + readFile(); + } +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/MailUtils.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/MailUtils.java new file mode 100644 index 0000000000..6d08cd7968 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/MailUtils.java @@ -0,0 +1,49 @@ +package com.coderising.ood.answer.utils; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +import com.coderising.ood.answer.entity.MailMessage; + +/** + * 邮件发送工具 + * @author readke + * + */ +public class MailUtils { + private static final Logger log = LogManager.getLogger(MailUtils.class); + + private static final String SMTP_SERVER = ConfigUtils.getProperty("smtp.server"); + private static final String ALT_SMTP_SERVER = ConfigUtils.getProperty("alt.smtp.server"); + + public static void sendMail(MailMessage email){ + try{ + sendMail(email, SMTP_SERVER); + log.info("使用主服务器发送邮件"); + log.info("发送成功"); + }catch (Exception e) { + try{ + sendMail(email, ALT_SMTP_SERVER); + log.info("使用备用服务器发送邮件"); + }catch (Exception e1){ + log.error("发送失败"); + } + } + } + + public static void sendMail(MailMessage email,String server) throws Exception{ + sendMail(email.getFromAddr(), email.getToAddr(), + server, email.getSubject(), email.getContent()); + } + + public static void sendMail(String from,String to,String server,String subject,String content) throws Exception{ + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(from).append("\n"); + buffer.append("To:").append(to).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(content).append("\n"); + System.out.println(buffer.toString()); + } + + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ProductUtils.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ProductUtils.java new file mode 100644 index 0000000000..1b854bfeb7 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/answer/utils/ProductUtils.java @@ -0,0 +1,52 @@ +package com.coderising.ood.answer.utils; + +import java.io.BufferedInputStream; +import java.io.BufferedReader; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.FileReader; +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +import com.coderising.ood.answer.entity.Product; + +/** + * 产品工具 + * @author readke + * + */ +public class ProductUtils { + private static final Logger log = LogManager.getLogger(ProductUtils.class); + + public static List getList(File file){ + List list = null; + BufferedReader br = null; + + try { + list = new ArrayList<>(); + br = new BufferedReader(new FileReader(file)); + while(br.ready()){ + Product p = new Product(); + String temp = br.readLine(); + String[] data = temp.split(" "); + p.setpId(data[0]); + p.setpDec(data[1]); + list.add(p); + } + + } catch (FileNotFoundException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + + return list; + } + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java new file mode 100644 index 0000000000..f328c1816a --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/Configuration.java @@ -0,0 +1,23 @@ +package com.coderising.ood.srp; +import java.util.HashMap; +import java.util.Map; + +public class Configuration { + + static Map configurations = new HashMap<>(); + static{ + configurations.put(ConfigurationKeys.SMTP_SERVER, "smtp.163.com"); + configurations.put(ConfigurationKeys.ALT_SMTP_SERVER, "smtp1.163.com"); + configurations.put(ConfigurationKeys.EMAIL_ADMIN, "admin@company.com"); + } + /** + * 应该从配置文件读, 但是这里简化为直接从一个map 中去读 + * @param key + * @return + */ + public String getProperty(String key) { + + return configurations.get(key); + } + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java new file mode 100644 index 0000000000..8695aed644 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/ConfigurationKeys.java @@ -0,0 +1,9 @@ +package com.coderising.ood.srp; + +public class ConfigurationKeys { + + public static final String SMTP_SERVER = "smtp.server"; + public static final String ALT_SMTP_SERVER = "alt.smtp.server"; + public static final String EMAIL_ADMIN = "email.admin"; + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java new file mode 100644 index 0000000000..82e9261d18 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/DBUtil.java @@ -0,0 +1,25 @@ +package com.coderising.ood.srp; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; + +public class DBUtil { + + /** + * 应该从数据库读, 但是简化为直接生成。 + * @param sql + * @return + */ + public static List query(String sql){ + + List userList = new ArrayList(); + for (int i = 1; i <= 3; i++) { + HashMap userInfo = new HashMap(); + userInfo.put("NAME", "User" + i); + userInfo.put("EMAIL", "aa@bb.com"); + userList.add(userInfo); + } + + return userList; + } +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java new file mode 100644 index 0000000000..9f9e749af7 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/MailUtil.java @@ -0,0 +1,18 @@ +package com.coderising.ood.srp; + +public class MailUtil { + + public static void sendEmail(String toAddress, String fromAddress, String subject, String message, String smtpHost, + boolean debug) { + //假装发了一封邮件 + StringBuilder buffer = new StringBuilder(); + buffer.append("From:").append(fromAddress).append("\n"); + buffer.append("To:").append(toAddress).append("\n"); + buffer.append("Subject:").append(subject).append("\n"); + buffer.append("Content:").append(message).append("\n"); + System.out.println(buffer.toString()); + + } + + +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java new file mode 100644 index 0000000000..781587a846 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/PromotionMail.java @@ -0,0 +1,199 @@ +package com.coderising.ood.srp; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.io.Serializable; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; + +public class PromotionMail { + + + protected String sendMailQuery = null; + + + protected String smtpHost = null; + protected String altSmtpHost = null; + protected String fromAddress = null; + protected String toAddress = null; + protected String subject = null; + protected String message = null; + + protected String productID = null; + protected String productDesc = null; + + private static Configuration config; + + + + private static final String NAME_KEY = "NAME"; + private static final String EMAIL_KEY = "EMAIL"; + + + public static void main(String[] args) throws Exception { + + File f = new File("C:\\coderising\\workspace_ds\\ood-example\\src\\product_promotion.txt"); + boolean emailDebug = false; + + PromotionMail pe = new PromotionMail(f, emailDebug); + + } + + + public PromotionMail(File file, boolean mailDebug) throws Exception { + + //读取配置文件, 文件中只有一行用空格隔开, 例如 P8756 iPhone8 + readFile(file); + + + config = new Configuration(); + + setSMTPHost(); + setAltSMTPHost(); + + + setFromAddress(); + + + setLoadQuery(); + + sendEMails(mailDebug, loadMailingList()); + + + } + + + + + protected void setProductID(String productID) + { + this.productID = productID; + + } + + protected String getproductID() + { + return productID; + } + + protected void setLoadQuery() throws Exception { + + sendMailQuery = "Select name from subscriptions " + + "where product_id= '" + productID +"' " + + "and send_mail=1 "; + + + System.out.println("loadQuery set"); + } + + + protected void setSMTPHost() + { + smtpHost = config.getProperty(ConfigurationKeys.SMTP_SERVER); + } + + + protected void setAltSMTPHost() + { + altSmtpHost = config.getProperty(ConfigurationKeys.ALT_SMTP_SERVER); + + } + + + protected void setFromAddress() + { + fromAddress = config.getProperty(ConfigurationKeys.EMAIL_ADMIN); + } + + protected void setMessage(HashMap userInfo) throws IOException + { + + String name = (String) userInfo.get(NAME_KEY); + + subject = "您关注的产品降价了"; + message = "尊敬的 "+name+", 您关注的产品 " + productDesc + " 降价了,欢迎购买!" ; + + + + } + + + protected void readFile(File file) throws IOException // @02C + { + BufferedReader br = null; + try { + br = new BufferedReader(new FileReader(file)); + String temp = br.readLine(); + String[] data = temp.split(" "); + + setProductID(data[0]); + setProductDesc(data[1]); + + System.out.println("产品ID = " + productID + "\n"); + System.out.println("产品描述 = " + productDesc + "\n"); + + } catch (IOException e) { + throw new IOException(e.getMessage()); + } finally { + br.close(); + } + } + + private void setProductDesc(String desc) { + this.productDesc = desc; + } + + + protected void configureEMail(HashMap userInfo) throws IOException + { + toAddress = (String) userInfo.get(EMAIL_KEY); + if (toAddress.length() > 0) + setMessage(userInfo); + } + + protected List loadMailingList() throws Exception { + return DBUtil.query(this.sendMailQuery); + } + + + protected void sendEMails(boolean debug, List mailingList) throws IOException + { + + System.out.println("开始发送邮件"); + + + if (mailingList != null) { + Iterator iter = mailingList.iterator(); + while (iter.hasNext()) { + configureEMail((HashMap) iter.next()); + try + { + if (toAddress.length() > 0) + MailUtil.sendEmail(toAddress, fromAddress, subject, message, smtpHost, debug); + } + catch (Exception e) + { + + try { + MailUtil.sendEmail(toAddress, fromAddress, subject, message, altSmtpHost, debug); + + } catch (Exception e2) + { + System.out.println("通过备用 SMTP服务器发送邮件失败: " + e2.getMessage()); + } + } + } + + + } + + else { + System.out.println("没有邮件发送"); + + } + + } +} diff --git a/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt new file mode 100644 index 0000000000..b7a974adb3 --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/com/coderising/ood/srp/product_promotion.txt @@ -0,0 +1,4 @@ +P8756 iPhone8 +P3946 XiaoMi10 +P8904 Oppo_R15 +P4955 Vivo_X20 \ No newline at end of file diff --git a/students/724222786/ood/ood-assignment/src/main/java/log4j2.xml b/students/724222786/ood/ood-assignment/src/main/java/log4j2.xml new file mode 100644 index 0000000000..6fc38d8b1b --- /dev/null +++ b/students/724222786/ood/ood-assignment/src/main/java/log4j2.xml @@ -0,0 +1,13 @@ + + + + + + + + + + + + + \ No newline at end of file From 34e00d5da5e410edeaedaaa0e125a59e74bcf30c Mon Sep 17 00:00:00 2001 From: Liu Zengzeng Date: Tue, 11 Jul 2017 12:51:04 +0800 Subject: [PATCH 71/73] uml homework pay homework --- .../com/coderising/ood/payroll/Employee.java | 64 + .../com/coderising/ood/payroll/Paycheck.java | 34 + .../ood/payroll/affiliation/Affiliation.java | 7 + .../payroll/affiliation/NonAffiliation.java | 15 + .../payroll/affiliation/ServiceCharge.java | 28 + .../payroll/affiliation/UnionAffiliation.java | 53 + .../CommissionClassification.java | 17 + .../classfication/HourlyClassification.java | 36 + .../classfication/PaymentClassification.java | 7 + .../classfication/SalariedClassification.java | 30 + .../payroll/classfication/SalesReceipt.java | 14 + .../ood/payroll/classfication/TimeCard.java | 15 + .../com/coderising/ood/payroll/db/MockDB.java | 38 + .../ood/payroll/method/BankMethod.java | 18 + .../ood/payroll/method/HoldMethod.java | 18 + .../ood/payroll/method/MailMethod.java | 17 + .../ood/payroll/method/PaymentMethod.java | 7 + .../schedule/BiWeeklyPaymentSchedule.java | 28 + .../schedule/MonthlyPaymentSchedule.java | 22 + .../ood/payroll/schedule/PaymentSchedule.java | 15 + .../schedule/WeeklyPaymentSchedule.java | 22 + .../coderising/ood/payroll/util/DateUtil.java | 96 + .../uml\344\275\234\344\270\232.mdj" | 10991 ++++++++++++++++ 23 files changed, 11592 insertions(+) create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Employee.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Paycheck.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/Affiliation.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/NonAffiliation.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/ServiceCharge.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/UnionAffiliation.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/CommissionClassification.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/HourlyClassification.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/PaymentClassification.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalariedClassification.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalesReceipt.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/TimeCard.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/db/MockDB.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/BankMethod.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/HoldMethod.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/MailMethod.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/PaymentMethod.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/BiWeeklyPaymentSchedule.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/MonthlyPaymentSchedule.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/PaymentSchedule.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/WeeklyPaymentSchedule.java create mode 100644 students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/util/DateUtil.java create mode 100644 "students/2816977791/ood/ood-assignment/uml\344\275\234\344\270\232.mdj" diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Employee.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Employee.java new file mode 100644 index 0000000000..a19e993424 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Employee.java @@ -0,0 +1,64 @@ +package com.coderising.ood.payroll; + +import com.coderising.ood.payroll.affiliation.Affiliation; +import com.coderising.ood.payroll.classfication.PaymentClassification; +import com.coderising.ood.payroll.method.PaymentMethod; +import com.coderising.ood.payroll.schedule.PaymentSchedule; + +import java.util.Date; + +public class Employee { + int id; + String name; + String address; + Affiliation affiliation; + + + PaymentClassification classification; + PaymentSchedule schedule; + PaymentMethod paymentMethod; + + public Employee(String name, String address) { + this.name = name; + this.address = address; + } + + public boolean isPayDay(Date d) { + return schedule.isPayDate(id, d); + } + + public boolean isPayed(Date d) { + return schedule.isPayed(id, d); + } + + public Date getPayPeriodStartDate(Date d) { + return schedule.getPayPeriodStartDate(d); + } + + public void payDay(Paycheck pc) { + + if (isPayDay(new Date()) && isPayed(new Date())) { + double grossPay = classification.calculatePay(pc); + double deduction = affiliation.calculateDeductions(pc); + double netPay = grossPay - deduction; + pc.setGrossPay(grossPay); + pc.setDeductions(deduction); + pc.setNetPay(netPay); + + paymentMethod.pay(pc, id); + } + } + + public void setClassification(PaymentClassification classification) { + this.classification = classification; + } + + public void setSchedule(PaymentSchedule schedule) { + this.schedule = schedule; + } + + public void setPaymentMethod(PaymentMethod paymentMethod) { + this.paymentMethod = paymentMethod; + } +} + diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Paycheck.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Paycheck.java new file mode 100644 index 0000000000..8704ba58c7 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/Paycheck.java @@ -0,0 +1,34 @@ +package com.coderising.ood.payroll; + +import java.util.Date; + +public class Paycheck { + private Date payPeriodStart; + private Date payPeriodEnd; + private double grossPay; + private double netPay; + private double deductions; + + public Paycheck(Date payPeriodStart, Date payPeriodEnd){ + this.payPeriodStart = payPeriodStart; + this.payPeriodEnd = payPeriodEnd; + } + public void setGrossPay(double grossPay) { + this.grossPay = grossPay; + + } + public void setDeductions(double deductions) { + this.deductions = deductions; + } + public void setNetPay(double netPay){ + this.netPay = netPay; + } + public Date getPayPeriodEndDate() { + + return this.payPeriodEnd; + } + public Date getPayPeriodStartDate() { + + return this.payPeriodStart; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/Affiliation.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/Affiliation.java new file mode 100644 index 0000000000..2b427068ae --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/Affiliation.java @@ -0,0 +1,7 @@ +package com.coderising.ood.payroll.affiliation; + +import com.coderising.ood.payroll.Paycheck; + +public interface Affiliation { + public double calculateDeductions(Paycheck pc); +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/NonAffiliation.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/NonAffiliation.java new file mode 100644 index 0000000000..cab1542a14 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/NonAffiliation.java @@ -0,0 +1,15 @@ +package com.coderising.ood.payroll.affiliation; + +import com.coderising.ood.payroll.Paycheck; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class NonAffiliation implements Affiliation { + + @Override + public double calculateDeductions(Paycheck pc) { + return 0; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/ServiceCharge.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/ServiceCharge.java new file mode 100644 index 0000000000..25847d650a --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/ServiceCharge.java @@ -0,0 +1,28 @@ +package com.coderising.ood.payroll.affiliation; + +import java.util.Date; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class ServiceCharge { + private Date date; + private double amount; + + public Date getDate() { + return date; + } + + public void setDate(Date date) { + this.date = date; + } + + public double getAmount() { + return amount; + } + + public void setAmount(double amount) { + this.amount = amount; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/UnionAffiliation.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/UnionAffiliation.java new file mode 100644 index 0000000000..50e19e985f --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/affiliation/UnionAffiliation.java @@ -0,0 +1,53 @@ +package com.coderising.ood.payroll.affiliation; + +import com.coderising.ood.payroll.Paycheck; +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.List; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class UnionAffiliation implements Affiliation{ + private int memberId; + private double weeklyDue; + private List serviceChargeList; + + @Override + public double calculateDeductions(Paycheck pc) { + int fridays = DateUtil.getFridayNumber(pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate()); + double totalDue = fridays * weeklyDue; + double totalCharge = 0.0d; + for (ServiceCharge serviceCharge : serviceChargeList){ + if (DateUtil.isDuring(pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate(), serviceCharge.getDate())){ + totalCharge += serviceCharge.getAmount(); + } + } + return totalCharge + totalDue; + } + + public int getMemberId() { + return memberId; + } + + public void setMemberId(int memberId) { + this.memberId = memberId; + } + + public double getWeeklyDue() { + return weeklyDue; + } + + public void setWeeklyDue(double weeklyDue) { + this.weeklyDue = weeklyDue; + } + + public List getServiceChargeList() { + return serviceChargeList; + } + + public void setServiceChargeList(List serviceChargeList) { + this.serviceChargeList = serviceChargeList; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/CommissionClassification.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/CommissionClassification.java new file mode 100644 index 0000000000..992b8142c1 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/CommissionClassification.java @@ -0,0 +1,17 @@ +package com.coderising.ood.payroll.classfication; + +import com.coderising.ood.payroll.Paycheck; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class CommissionClassification implements PaymentClassification { + + private double salary; + + @Override + public double calculatePay(Paycheck pc) { + return salary; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/HourlyClassification.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/HourlyClassification.java new file mode 100644 index 0000000000..de8ac05ae4 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/HourlyClassification.java @@ -0,0 +1,36 @@ +package com.coderising.ood.payroll.classfication; + +import com.coderising.ood.payroll.Paycheck; +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.Date; +import java.util.Map; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class HourlyClassification implements PaymentClassification { + private double rate; + private Map timeCards; + + public void addTimeCard(TimeCard tc) { + timeCards.put(tc.getDate(), tc); + } + + @Override + public double calculatePay(Paycheck pc) { + double daysMoney = 0.0; + for (Date date : timeCards.keySet()) { + if (DateUtil.isDuring(pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate(), date)) { + daysMoney += calculateHours(timeCards.get(date).getHours()); + } + } + return daysMoney; + } + + private double calculateHours(int hour) { + int extendHour = hour - 8 >= 0 ? hour - 8 : 0; + return hour * rate + extendHour * rate * 1.5; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/PaymentClassification.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/PaymentClassification.java new file mode 100644 index 0000000000..90cd991f75 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/PaymentClassification.java @@ -0,0 +1,7 @@ +package com.coderising.ood.payroll.classfication; + +import com.coderising.ood.payroll.Paycheck; + +public interface PaymentClassification { + public double calculatePay(Paycheck pc); +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalariedClassification.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalariedClassification.java new file mode 100644 index 0000000000..50c3a70d92 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalariedClassification.java @@ -0,0 +1,30 @@ +package com.coderising.ood.payroll.classfication; + +import com.coderising.ood.payroll.Paycheck; +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.Date; +import java.util.Map; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class SalariedClassification implements PaymentClassification { + private double salary; + private double rate; + private Map salesReceiptMap; + + + @Override + public double calculatePay(Paycheck pc) { + double commission = 0.0; + for (Date date : salesReceiptMap.keySet()) { + if (DateUtil.isDuring(pc.getPayPeriodStartDate(), pc.getPayPeriodEndDate(), date)) { + commission += salesReceiptMap.get(date).getAmount() * rate; + } + } + + return salary + commission; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalesReceipt.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalesReceipt.java new file mode 100644 index 0000000000..5194c317c4 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/SalesReceipt.java @@ -0,0 +1,14 @@ +package com.coderising.ood.payroll.classfication; + +import java.util.Date; + +public class SalesReceipt { + private Date saleDate; + private double amount; + public Date getSaleDate() { + return saleDate; + } + public double getAmount() { + return amount; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/TimeCard.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/TimeCard.java new file mode 100644 index 0000000000..c0c70e95f8 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/classfication/TimeCard.java @@ -0,0 +1,15 @@ +package com.coderising.ood.payroll.classfication; + +import java.util.Date; + +public class TimeCard { + private Date date; + private int hours; + + public Date getDate() { + return date; + } + public int getHours() { + return hours; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/db/MockDB.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/db/MockDB.java new file mode 100644 index 0000000000..9529963626 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/db/MockDB.java @@ -0,0 +1,38 @@ +package com.coderising.ood.payroll.db; + +import com.coderising.ood.payroll.Paycheck; + +import java.util.HashMap; +import java.util.Map; +import java.util.Stack; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class MockDB { + + private static Map> map; + + static { + map = new HashMap>(); + } + + public static void put(int id, Paycheck pc) { + if (map.containsKey(id)) { + Stack stack = map.get(id); + stack.push(pc); + } else { + Stack stack = new Stack<>(); + stack.push(pc); + map.put(id, stack); + } + } + + public static Paycheck peek(int id) { + if (map.containsKey(id)) { + return map.get(id).peek(); + } + return null; + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/BankMethod.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/BankMethod.java new file mode 100644 index 0000000000..257476c8b1 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/BankMethod.java @@ -0,0 +1,18 @@ +package com.coderising.ood.payroll.method; + +import com.coderising.ood.payroll.Paycheck; +import com.coderising.ood.payroll.db.MockDB; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class BankMethod implements PaymentMethod { + + @Override + public void pay(Paycheck pc, int employId) { + //pay to bank + System.out.println("pay to bank " + employId); + MockDB.put(employId, pc); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/HoldMethod.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/HoldMethod.java new file mode 100644 index 0000000000..92f1b08830 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/HoldMethod.java @@ -0,0 +1,18 @@ +package com.coderising.ood.payroll.method; + +import com.coderising.ood.payroll.Paycheck; +import com.coderising.ood.payroll.db.MockDB; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class HoldMethod implements PaymentMethod { + + @Override + public void pay(Paycheck pc, int employId) { + //hold the paycheck + System.out.println("hold paycheck " + employId); + MockDB.put(employId, pc); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/MailMethod.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/MailMethod.java new file mode 100644 index 0000000000..1cff304dc7 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/MailMethod.java @@ -0,0 +1,17 @@ +package com.coderising.ood.payroll.method; + +import com.coderising.ood.payroll.Paycheck; +import com.coderising.ood.payroll.db.MockDB; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class MailMethod implements PaymentMethod { + @Override + public void pay(Paycheck pc, int employId) { + //mail to employee + System.out.println("mail to employee " + employId); + MockDB.put(employId, pc); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/PaymentMethod.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/PaymentMethod.java new file mode 100644 index 0000000000..b0c88c21fa --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/method/PaymentMethod.java @@ -0,0 +1,7 @@ +package com.coderising.ood.payroll.method; + +import com.coderising.ood.payroll.Paycheck; + +public interface PaymentMethod{ + public void pay(Paycheck pc, int employId); +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/BiWeeklyPaymentSchedule.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/BiWeeklyPaymentSchedule.java new file mode 100644 index 0000000000..b36968d68b --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/BiWeeklyPaymentSchedule.java @@ -0,0 +1,28 @@ +package com.coderising.ood.payroll.schedule; + +import com.coderising.ood.payroll.db.MockDB; +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.Date; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class BiWeeklyPaymentSchedule implements PaymentSchedule { + + @Override + public boolean isPayDate(int employedId, Date date) { + Date payedDate = MockDB.peek(employedId).getPayPeriodEndDate(); + if (payedDate == null) { + return DateUtil.isFriday(date); + } else { + return DateUtil.getInterval(payedDate, date) % 14 == 0; + } + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.getStartDate(payPeriodEndDate, -13); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/MonthlyPaymentSchedule.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/MonthlyPaymentSchedule.java new file mode 100644 index 0000000000..b54682ab83 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/MonthlyPaymentSchedule.java @@ -0,0 +1,22 @@ +package com.coderising.ood.payroll.schedule; + +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.Date; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class MonthlyPaymentSchedule implements PaymentSchedule { + + @Override + public boolean isPayDate(int employId, Date date) { + return DateUtil.isLastWorkDay(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.getStartOfMonth(); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/PaymentSchedule.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/PaymentSchedule.java new file mode 100644 index 0000000000..4fce5bac18 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/PaymentSchedule.java @@ -0,0 +1,15 @@ +package com.coderising.ood.payroll.schedule; + +import com.coderising.ood.payroll.db.MockDB; +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.Date; + +public interface PaymentSchedule { + public boolean isPayDate(int employId, Date date); + public Date getPayPeriodStartDate(Date payPeriodEndDate); + + default public boolean isPayed(int employedId, Date date){ + return DateUtil.equalDay(MockDB.peek(employedId).getPayPeriodEndDate(), date); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/WeeklyPaymentSchedule.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/WeeklyPaymentSchedule.java new file mode 100644 index 0000000000..988b8c23ea --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/schedule/WeeklyPaymentSchedule.java @@ -0,0 +1,22 @@ +package com.coderising.ood.payroll.schedule; + +import com.coderising.ood.payroll.util.DateUtil; + +import java.util.Date; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class WeeklyPaymentSchedule implements PaymentSchedule { + + @Override + public boolean isPayDate(int employId,Date date) { + return DateUtil.isFriday(date); + } + + @Override + public Date getPayPeriodStartDate(Date payPeriodEndDate) { + return DateUtil.getStartDate(payPeriodEndDate, -6); + } +} diff --git a/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/util/DateUtil.java b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/util/DateUtil.java new file mode 100644 index 0000000000..b742fabef5 --- /dev/null +++ b/students/2816977791/ood/ood-assignment/src/main/java/com/coderising/ood/payroll/util/DateUtil.java @@ -0,0 +1,96 @@ +package com.coderising.ood.payroll.util; + +import java.util.Calendar; +import java.util.Date; + +/** + * @author nvarchar + * date 2017/7/10 + */ +public class DateUtil { + + public static boolean isDuring(Date start, Date end, Date date) { + long oneDay = 24 * 60 * 60 * 1000; + long d1 = start.getTime() / oneDay; + long d2 = end.getTime() / oneDay; + long d = date.getTime() / oneDay; + + if (d1 <= d && d <= d2) { + return true; + } + + return false; + } + + + public static int getFridayNumber(Date start, Date end) { + Calendar starCalendar = Calendar.getInstance(); + starCalendar.setTime(start); + Calendar endCalendar = Calendar.getInstance(); + endCalendar.setTime(end); + int result = 0; + while (starCalendar.before(endCalendar)) { + + starCalendar.add(Calendar.DATE, 1); + + if (starCalendar.get(Calendar.DAY_OF_WEEK) == Calendar.FRIDAY) { + result++; + starCalendar.add(Calendar.DATE, 6); + } + + } + return result; + } + + public static boolean isFriday(Date date) { + Calendar calendar = Calendar.getInstance(); + calendar.setTime(date); + if (calendar.get(Calendar.DAY_OF_WEEK) == Calendar.FRIDAY) { + return true; + } + return false; + } + + public static boolean isLastWorkDay(Date date) { + + Calendar calToday = Calendar.getInstance(); + calToday.setTime(date); + + Calendar cal = Calendar.getInstance(); + cal.set(Calendar.DATE, cal.getActualMaximum(Calendar.DATE)); + while (cal.get(Calendar.DAY_OF_WEEK) == Calendar.SATURDAY && + cal.get(Calendar.DAY_OF_WEEK) == Calendar.SUNDAY) { + cal.add(Calendar.DATE, -1); + } + + return cal.get(Calendar.DAY_OF_MONTH) == calToday.get(Calendar.DAY_OF_MONTH); + } + + public static Date getStartDate(Date endDate, int duringDay) { + Calendar cal = Calendar.getInstance(); + cal.setTime(endDate); + cal.add(Calendar.DATE, duringDay); + return cal.getTime(); + } + + public static Date getStartOfMonth() { + Calendar cal = Calendar.getInstance(); + cal.set(Calendar.DATE, cal.getActualMinimum(Calendar.DATE)); + return cal.getTime(); + } + + public static boolean equalDay(Date date1, Date date2) { + long oneDay = 24 * 60 * 60 * 1000; + long d1 = date1.getTime() / oneDay; + long d2 = date2.getTime() / oneDay; + return d1 == d2; + } + + public static long getInterval(Date start, Date end) { + long oneDay = 24 * 60 * 60 * 1000; + long d1 = start.getTime() / oneDay; + long d2 = end.getTime() / oneDay; + return d2 - d1; + } +} + diff --git "a/students/2816977791/ood/ood-assignment/uml\344\275\234\344\270\232.mdj" "b/students/2816977791/ood/ood-assignment/uml\344\275\234\344\270\232.mdj" new file mode 100644 index 0000000000..07a8fd5223 --- /dev/null +++ "b/students/2816977791/ood/ood-assignment/uml\344\275\234\344\270\232.mdj" @@ -0,0 +1,10991 @@ +{ + "_type": "Project", + "_id": "AAAAAAFF+h6SjaM2Hec=", + "name": "UML", + "ownedElements": [ + { + "_type": "UMLModel", + "_id": "AAAAAAFdF8bUGpzmKj4=", + "_parent": { + "$ref": "AAAAAAFF+h6SjaM2Hec=" + }, + "name": "UML", + "ownedElements": [ + { + "_type": "UMLClassDiagram", + "_id": "AAAAAAFdF8bUG5znYro=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "掷骰子类图", + "visible": true, + "defaultDiagram": false, + "ownedViews": [ + { + "_type": "UMLClassView", + "_id": "AAAAAAFdF9Jh5p1e1kg=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdF9Jh551fLcE=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5p1e1kg=" + }, + "model": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF9Jh551gGOA=", + "_parent": { + "$ref": "AAAAAAFdF9Jh551fLcE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -64, + "top": -64, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9Jh6J1hmaI=", + "_parent": { + "$ref": "AAAAAAFdF9Jh551fLcE=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 93, + "top": 143, + "width": 136, + "height": 13, + "autoResize": false, + "underline": false, + "text": "Player", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9Jh6J1iK1E=", + "_parent": { + "$ref": "AAAAAAFdF9Jh551fLcE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -64, + "top": -64, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9Jh6J1jC4c=", + "_parent": { + "$ref": "AAAAAAFdF9Jh551fLcE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -64, + "top": -64, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 88, + "top": 136, + "width": 146, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdF9Jh551gGOA=" + }, + "nameLabel": { + "$ref": "AAAAAAFdF9Jh6J1hmaI=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdF9Jh6J1iK1E=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF9Jh6J1jC4c=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdF9Jh6J1k2zs=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5p1e1kg=" + }, + "model": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 88, + "top": 161, + "width": 146, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdF9Jh6Z1lcZE=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5p1e1kg=" + }, + "model": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 88, + "top": 171, + "width": 146, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdF9Jh6Z1mfBE=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5p1e1kg=" + }, + "model": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -32, + "top": -32, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdF9Jh6p1n2Rs=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5p1e1kg=" + }, + "model": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -32, + "top": -32, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 88, + "top": 136, + "width": 146, + "height": 137, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdF9Jh551fLcE=" + }, + "wordWrap": false, + "suppressAttributes": false, + "suppressOperations": false, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdF9Jh6J1k2zs=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdF9Jh6Z1lcZE=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdF9Jh6Z1mfBE=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdF9Jh6p1n2Rs=" + } + }, + { + "_type": "UMLClassView", + "_id": "AAAAAAFdF9NBMZ2L3Y0=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdF9NBMp2MHjA=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "model": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF9NBMp2N/fY=", + "_parent": { + "$ref": "AAAAAAFdF9NBMp2MHjA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 352, + "top": -32, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9NBMp2OfKA=", + "_parent": { + "$ref": "AAAAAAFdF9NBMp2MHjA=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 301, + "top": 159, + "width": 110, + "height": 13, + "autoResize": false, + "underline": false, + "text": "DiceGame", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9NBMp2P328=", + "_parent": { + "$ref": "AAAAAAFdF9NBMp2MHjA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 352, + "top": -32, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9NBMp2QlM4=", + "_parent": { + "$ref": "AAAAAAFdF9NBMp2MHjA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 352, + "top": -32, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 296, + "top": 152, + "width": 120, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdF9NBMp2N/fY=" + }, + "nameLabel": { + "$ref": "AAAAAAFdF9NBMp2OfKA=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdF9NBMp2P328=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF9NBMp2QlM4=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdF9NBM52Rwlo=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "model": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 296, + "top": 177, + "width": 120, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdF9NBM52Sw5c=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "model": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "subViews": [ + { + "_type": "UMLOperationView", + "_id": "AAAAAAFdF9tkjZ8WQz4=", + "_parent": { + "$ref": "AAAAAAFdF9NBM52Sw5c=" + }, + "model": { + "$ref": "AAAAAAFdF9tkT58TEw0=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 301, + "top": 192, + "width": 110, + "height": 13, + "autoResize": false, + "underline": false, + "text": "+play()", + "horizontalAlignment": 0, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 296, + "top": 187, + "width": 120, + "height": 23, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdF9NBM52TM2c=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "model": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 176, + "top": -16, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdF9NBM52UQZA=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "model": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 176, + "top": -16, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 296, + "top": 152, + "width": 120, + "height": 105, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdF9NBMp2MHjA=" + }, + "wordWrap": false, + "suppressAttributes": false, + "suppressOperations": false, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdF9NBM52Rwlo=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdF9NBM52Sw5c=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdF9NBM52TM2c=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdF9NBM52UQZA=" + } + }, + { + "_type": "UMLClassView", + "_id": "AAAAAAFdF9RF6p27dz8=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdF9RF6p285OM=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p27dz8=" + }, + "model": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF9RF6p290EI=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p285OM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 832, + "top": -64, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9RF652+dtM=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p285OM=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 541, + "top": 143, + "width": 95, + "height": 13, + "autoResize": false, + "underline": false, + "text": "Dice", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9RF652/xQQ=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p285OM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 832, + "top": -64, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9RF653A46U=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p285OM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 832, + "top": -64, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 536, + "top": 136, + "width": 105, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdF9RF6p290EI=" + }, + "nameLabel": { + "$ref": "AAAAAAFdF9RF652+dtM=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdF9RF652/xQQ=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF9RF653A46U=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdF9RF653BO3M=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p27dz8=" + }, + "model": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 536, + "top": 161, + "width": 105, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdF9RF653Cqww=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p27dz8=" + }, + "model": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "subViews": [ + { + "_type": "UMLOperationView", + "_id": "AAAAAAFdF9yO5Z8ojEk=", + "_parent": { + "$ref": "AAAAAAFdF9RF653Cqww=" + }, + "model": { + "$ref": "AAAAAAFdF9yOrp8l+p4=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 541, + "top": 176, + "width": 95, + "height": 13, + "autoResize": false, + "underline": false, + "text": "+roll()", + "horizontalAlignment": 0, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 536, + "top": 171, + "width": 105, + "height": 23, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdF9RF653DNB8=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p27dz8=" + }, + "model": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 416, + "top": -32, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdF9RF653EiHA=", + "_parent": { + "$ref": "AAAAAAFdF9RF6p27dz8=" + }, + "model": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 416, + "top": -32, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 536, + "top": 136, + "width": 105, + "height": 129, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdF9RF6p285OM=" + }, + "wordWrap": false, + "suppressAttributes": false, + "suppressOperations": false, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdF9RF653BO3M=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdF9RF653Cqww=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdF9RF653DNB8=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdF9RF653EiHA=" + } + }, + { + "_type": "UMLClassView", + "_id": "AAAAAAFdG6RIw5sj01s=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdG6RIw5skjDw=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5sj01s=" + }, + "model": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdG6RIxJslAao=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5skjDw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 64, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdG6RIxJsm7oQ=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5skjDw=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 317, + "top": 343, + "width": 83, + "height": 13, + "autoResize": false, + "underline": false, + "text": "Display", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdG6RIxJsn/Ho=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5skjDw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 64, + "top": 0, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdG6RIxJsowro=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5skjDw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 64, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 312, + "top": 336, + "width": 93, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdG6RIxJslAao=" + }, + "nameLabel": { + "$ref": "AAAAAAFdG6RIxJsm7oQ=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdG6RIxJsn/Ho=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdG6RIxJsowro=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdG6RIxJsppN8=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5sj01s=" + }, + "model": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 312, + "top": 361, + "width": 93, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdG6RIxJsqh8o=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5sj01s=" + }, + "model": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "subViews": [ + { + "_type": "UMLOperationView", + "_id": "AAAAAAFdG6UFHpx+fFk=", + "_parent": { + "$ref": "AAAAAAFdG6RIxJsqh8o=" + }, + "model": { + "$ref": "AAAAAAFdG6UEzJx4aDY=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 317, + "top": 376, + "width": 83, + "height": 13, + "autoResize": false, + "underline": false, + "text": "+showResult()", + "horizontalAlignment": 0, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 312, + "top": 371, + "width": 93, + "height": 23, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdG6RIxZsrp4I=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5sj01s=" + }, + "model": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 32, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdG6RIxZssrB4=", + "_parent": { + "$ref": "AAAAAAFdG6RIw5sj01s=" + }, + "model": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 32, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 312, + "top": 336, + "width": 93, + "height": 58, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdG6RIw5skjDw=" + }, + "wordWrap": false, + "suppressAttributes": false, + "suppressOperations": false, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdG6RIxJsppN8=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdG6RIxJsqh8o=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdG6RIxZsrp4I=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdG6RIxZssrB4=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdG6S2ipuwjkI=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZusc0s=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5uxbfQ=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZusc0s=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 475, + "top": 210, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5uyfR4=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZusc0s=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 475, + "top": 225, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5uz2QY=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZusc0s=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 474, + "top": 181, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5u0CCg=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZutrMs=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 509, + "top": 210, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5u1a6s=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZutrMs=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 507, + "top": 223, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5u2OxE=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZutrMs=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 513, + "top": 182, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5u3NnY=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZuu5hA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 442, + "top": 211, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5u4bS4=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZuu5hA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 444, + "top": 224, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6S2i5u5L50=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZuu5hA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 437, + "top": 184, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdG6S2i5u6s+4=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZutrMs=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdG6S2i5u7PHQ=", + "_parent": { + "$ref": "AAAAAAFdG6S2ipuwjkI=" + }, + "model": { + "$ref": "AAAAAAFdG6S2iZuu5hA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "tail": { + "$ref": "AAAAAAFdF9RF6p27dz8=" + }, + "lineStyle": 1, + "points": "535:201;416:203", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdG6S2i5uxbfQ=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdG6S2i5uyfR4=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdG6S2i5uz2QY=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdG6S2i5u0CCg=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdG6S2i5u1a6s=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdG6S2i5u2OxE=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdG6S2i5u3NnY=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdG6S2i5u4bS4=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdG6S2i5u5L50=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdG6S2i5u6s+4=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdG6S2i5u7PHQ=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdG6TzIZwbrTI=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwX5cs=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwcpKE=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwX5cs=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 370, + "top": 289, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwdOEs=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwX5cs=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 385, + "top": 289, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZweT1I=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwX5cs=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 341, + "top": 290, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwf28Q=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwYZJ8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 371, + "top": 276, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwgt2E=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwYZJ8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 384, + "top": 278, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwhoAc=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwYZJ8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 343, + "top": 272, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwixsg=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwZeVE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 371, + "top": 302, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwj9mY=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwZeVE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 384, + "top": 300, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6TzIZwk3hI=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwZeVE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 344, + "top": 307, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdG6TzIZwlZ4U=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwYZJ8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdG6TzIZwmWlA=", + "_parent": { + "$ref": "AAAAAAFdG6TzIZwbrTI=" + }, + "model": { + "$ref": "AAAAAAFdG6TzIJwZeVE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdG6RIw5sj01s=" + }, + "tail": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "lineStyle": 1, + "points": "356:257;357:335", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdG6TzIZwcpKE=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdG6TzIZwdOEs=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdG6TzIZweT1I=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdG6TzIZwf28Q=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdG6TzIZwgt2E=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdG6TzIZwhoAc=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdG6TzIZwixsg=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdG6TzIZwj9mY=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdG6TzIZwk3hI=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdG6TzIZwlZ4U=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdG6TzIZwmWlA=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdG6VR1p1K29k=", + "_parent": { + "$ref": "AAAAAAFdF8bUG5znYro=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1Gsno=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151Ll90=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1Gsno=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 264, + "top": 183, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151MEwk=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1Gsno=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 264, + "top": 168, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151N38E=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1Gsno=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 264, + "top": 213, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151OVG8=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1HuPE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 259, + "top": 183, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151PBXI=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1HuPE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 262, + "top": 169, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151Qxb0=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1HuPE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 255, + "top": 210, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151RWSE=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1IHBQ=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 269, + "top": 183, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151SI6M=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1IHBQ=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 266, + "top": 169, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdG6VR151Tzp0=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1IHBQ=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 273, + "top": 210, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdG6VR2J1U3mw=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1HuPE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdG6VR2J1VdIc=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1K29k=" + }, + "model": { + "$ref": "AAAAAAFdG6VR1p1IHBQ=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdF9NBMZ2L3Y0=" + }, + "tail": { + "$ref": "AAAAAAFdF9Jh5p1e1kg=" + }, + "lineStyle": 1, + "points": "234:204;295:204", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdG6VR151Ll90=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdG6VR151MEwk=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdG6VR151N38E=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdG6VR151OVG8=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdG6VR151PBXI=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdG6VR151Qxb0=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdG6VR151RWSE=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdG6VR151SI6M=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdG6VR151Tzp0=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdG6VR2J1U3mw=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdG6VR2J1VdIc=" + } + } + ] + }, + { + "_type": "UMLUseCaseDiagram", + "_id": "AAAAAAFdF8yd/5z3Wwc=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "购物网站", + "visible": true, + "defaultDiagram": false, + "ownedViews": [ + { + "_type": "UMLActorView", + "_id": "AAAAAAFdGAKakqRiXVU=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdGAKakqRjG98=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "model": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdGAKalKRkgoU=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRjG98=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 80, + "top": 432, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAKalaRlXyo=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRjG98=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 125, + "top": 549, + "width": 40, + "height": 13, + "autoResize": false, + "underline": false, + "text": "用户", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAKalqRm2U4=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRjG98=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 80, + "top": 432, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAKalqRnExY=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRjG98=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 80, + "top": 432, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 120, + "top": 542, + "width": 50, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdGAKalKRkgoU=" + }, + "nameLabel": { + "$ref": "AAAAAAFdGAKalaRlXyo=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdGAKalqRm2U4=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdGAKalqRnExY=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdGAKalqRoke0=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "model": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 40, + "top": 216, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdGAKalqRpCx8=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "model": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 40, + "top": 216, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdGAKalqRq+G8=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "model": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 40, + "top": 216, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdGAKal6Rr7ig=", + "_parent": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "model": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 40, + "top": 216, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 120, + "top": 488, + "width": 50, + "height": 80, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdGAKakqRjG98=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdGAKalqRoke0=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdGAKalqRpCx8=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdGAKalqRq+G8=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdGAKal6Rr7ig=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdGAO/iqSO/fU=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdGAO/i6SPYmM=", + "_parent": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdGAO/i6SQA1I=", + "_parent": { + "$ref": "AAAAAAFdGAO/i6SPYmM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 96, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAO/jKSRG4E=", + "_parent": { + "$ref": "AAAAAAFdGAO/i6SPYmM=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 363.5, + "top": 299.5, + "width": 59, + "height": 13, + "autoResize": false, + "underline": false, + "text": "搜索产品", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAO/jKSSM84=", + "_parent": { + "$ref": "AAAAAAFdGAO/i6SPYmM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 96, + "top": 0, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAO/jKSTyrk=", + "_parent": { + "$ref": "AAAAAAFdGAO/i6SPYmM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 96, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 358.5, + "top": 292.5, + "width": 69, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdGAO/i6SQA1I=" + }, + "nameLabel": { + "$ref": "AAAAAAFdGAO/jKSRG4E=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdGAO/jKSSM84=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdGAO/jKSTyrk=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdGAO/jKSULYo=", + "_parent": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 48, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdGAO/jKSVv9A=", + "_parent": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 48, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdGAO/jaSWaoI=", + "_parent": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 48, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdGAO/jaSXnr0=", + "_parent": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 48, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdGAO/jaSYrk8=", + "_parent": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "model": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 48, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 344, + "top": 288, + "width": 98, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdGAO/i6SPYmM=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdGAO/jKSULYo=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdGAO/jKSVv9A=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdGAO/jaSWaoI=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdGAO/jaSXnr0=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdGAO/jaSYrk8=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdGAW4LqTsTLE=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdGAW4LqTtPZc=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdGAW4LqTuTJk=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTtPZc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -48, + "top": 192, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAW4LqTvhiU=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTtPZc=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 283.5, + "top": 547.5, + "width": 59, + "height": 13, + "autoResize": false, + "underline": false, + "text": "登录", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAW4LqTwLGA=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTtPZc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -48, + "top": 192, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAW4LqTxlcc=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTtPZc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -48, + "top": 192, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 278.5, + "top": 540.5, + "width": 69, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdGAW4LqTuTJk=" + }, + "nameLabel": { + "$ref": "AAAAAAFdGAW4LqTvhiU=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdGAW4LqTwLGA=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdGAW4LqTxlcc=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdGAW4L6Ty/cY=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -24, + "top": 96, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdGAW4L6TzO8g=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -24, + "top": 96, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdGAW4L6T0ZYo=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -24, + "top": 96, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdGAW4L6T1z/U=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -24, + "top": 96, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdGAW4L6T22yQ=", + "_parent": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "model": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -24, + "top": 96, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 264, + "top": 536, + "width": 98, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdGAW4LqTtPZc=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdGAW4L6Ty/cY=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdGAW4L6TzO8g=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdGAW4L6T0ZYo=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdGAW4L6T1z/U=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdGAW4L6T22yQ=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdGAXoA6UbzVQ=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdGAXoA6UcL8A=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdGAXoA6UdkQA=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UcL8A=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 512, + "top": -256, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAXoBKUe/lA=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UcL8A=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 557, + "top": 379.5, + "width": 64, + "height": 13, + "autoResize": false, + "underline": false, + "text": "加入购物车", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAXoBKUftL0=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UcL8A=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 512, + "top": -256, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAXoBKUgLYU=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UcL8A=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 512, + "top": -256, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 552, + "top": 372.5, + "width": 75, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdGAXoA6UdkQA=" + }, + "nameLabel": { + "$ref": "AAAAAAFdGAXoBKUe/lA=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdGAXoBKUftL0=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdGAXoBKUgLYU=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdGAXoBKUhVMo=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": -128, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdGAXoBKUiMzs=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": -128, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdGAXoBKUj3f8=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": -128, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdGAXoBKUk5Oc=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": -128, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdGAXoBKUlCmw=", + "_parent": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "model": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": -128, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 536, + "top": 368, + "width": 106, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdGAXoA6UcL8A=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdGAXoBKUhVMo=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdGAXoBKUiMzs=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdGAXoBKUj3f8=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdGAXoBKUk5Oc=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdGAXoBKUlCmw=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdGAY0uaVJfPE=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdGAY0uqVKVek=", + "_parent": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdGAY0uqVLTx8=", + "_parent": { + "$ref": "AAAAAAFdGAY0uqVKVek=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 384, + "top": -224, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAY0uqVMq7M=", + "_parent": { + "$ref": "AAAAAAFdGAY0uqVKVek=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 491.5, + "top": 459.5, + "width": 59, + "height": 13, + "autoResize": false, + "underline": false, + "text": "下订单", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAY0uqVNyeI=", + "_parent": { + "$ref": "AAAAAAFdGAY0uqVKVek=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 384, + "top": -224, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdGAY0uqVOXIE=", + "_parent": { + "$ref": "AAAAAAFdGAY0uqVKVek=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 384, + "top": -224, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 486.5, + "top": 452.5, + "width": 69, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdGAY0uqVLTx8=" + }, + "nameLabel": { + "$ref": "AAAAAAFdGAY0uqVMq7M=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdGAY0uqVNyeI=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdGAY0uqVOXIE=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdGAY0u6VPDCs=", + "_parent": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 192, + "top": -112, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdGAY0u6VQoxY=", + "_parent": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 192, + "top": -112, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdGAY0vKVR6Lo=", + "_parent": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 192, + "top": -112, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdGAY0vKVS8fI=", + "_parent": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 192, + "top": -112, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdGAY0vKVTC5U=", + "_parent": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "model": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 192, + "top": -112, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 472, + "top": 448, + "width": 98, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdGAY0uqVKVek=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdGAY0u6VPDCs=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdGAY0u6VQoxY=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdGAY0vKVR6Lo=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdGAY0vKVS8fI=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdGAY0vKVTC5U=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdGBgGqqbtA6o=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabpFws=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGqqbulzY=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabpFws=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 261, + "top": 395, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGqqbvRns=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabpFws=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 251, + "top": 384, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGqqbw+8Q=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabpFws=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 280, + "top": 418, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGqqbx1Oo=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabqC0k=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 179, + "top": 469, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGqqby2Nw=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabqC0k=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 172, + "top": 458, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGq6bzark=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabqC0k=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 194, + "top": 492, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGq6b0+5A=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabrjBY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 342, + "top": 323, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGq6b1X1E=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabrjBY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 332, + "top": 314, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdGBgGq6b22tU=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabrjBY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 364, + "top": 340, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdGBgGq6b3GEg=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabqC0k=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdGBgGq6b4aEw=", + "_parent": { + "$ref": "AAAAAAFdGBgGqqbtA6o=" + }, + "model": { + "$ref": "AAAAAAFdGBgGqabrjBY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "tail": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "lineStyle": 1, + "points": "170:504;372:323", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdGBgGqqbulzY=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdGBgGqqbvRns=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdGBgGqqbw+8Q=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdGBgGqqbx1Oo=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdGBgGqqby2Nw=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdGBgGq6bzark=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdGBgGq6b0+5A=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdGBgGq6b1X1E=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdGBgGq6b22tU=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdGBgGq6b3GEg=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdGBgGq6b4aEw=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdHQ4fLp+/lbg=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdHQ4fL5/A/FM=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ4fL5/ByjE=", + "_parent": { + "$ref": "AAAAAAFdHQ4fL5/A/FM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ4fL5/Cees=", + "_parent": { + "$ref": "AAAAAAFdHQ4fL5/A/FM=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 567.5, + "top": 283.5, + "width": 77, + "height": 13, + "autoResize": false, + "underline": false, + "text": "查看产品详情", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ4fL5/Dl2s=", + "_parent": { + "$ref": "AAAAAAFdHQ4fL5/A/FM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ4fL5/ELok=", + "_parent": { + "$ref": "AAAAAAFdHQ4fL5/A/FM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 562.5, + "top": 276.5, + "width": 88, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ4fL5/ByjE=" + }, + "nameLabel": { + "$ref": "AAAAAAFdHQ4fL5/Cees=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdHQ4fL5/Dl2s=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ4fL5/ELok=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdHQ4fL5/FyyE=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdHQ4fMJ/GK3o=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdHQ4fMJ/Hh90=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdHQ4fMJ/I0dw=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdHQ4fMJ/Jrj0=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "model": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 544, + "top": 272, + "width": 124, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdHQ4fL5/A/FM=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdHQ4fL5/FyyE=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdHQ4fMJ/GK3o=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdHQ4fMJ/Hh90=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdHQ4fMJ/I0dw=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdHQ4fMJ/Jrj0=" + } + }, + { + "_type": "UMLExtendView", + "_id": "AAAAAAFdHQ57DaAqNs0=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ57DaAopRI=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ57DqAr1sM=", + "_parent": { + "$ref": "AAAAAAFdHQ57DaAqNs0=" + }, + "model": { + "$ref": "AAAAAAFdHQ57DaAopRI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 493, + "top": 305, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ57DaAqNs0=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ57DqAshCo=", + "_parent": { + "$ref": "AAAAAAFdHQ57DaAqNs0=" + }, + "model": { + "$ref": "AAAAAAFdHQ57DaAopRI=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 464, + "top": 279, + "width": 53, + "height": 13, + "autoResize": false, + "alpha": -1.4707737086130512, + "distance": 11.180339887498949, + "hostEdge": { + "$ref": "AAAAAAFdHQ57DaAqNs0=" + }, + "edgePosition": 1, + "underline": false, + "text": "«extend»", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ57DqAt9cs=", + "_parent": { + "$ref": "AAAAAAFdHQ57DaAqNs0=" + }, + "model": { + "$ref": "AAAAAAFdHQ57DaAopRI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 490, + "top": 276, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ57DaAqNs0=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "tail": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "lineStyle": 1, + "points": "543:294;442:301", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHQ57DqAr1sM=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ57DqAshCo=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ57DqAt9cs=" + } + }, + { + "_type": "UMLExtendView", + "_id": "AAAAAAFdHQ7gj6GpG4g=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ7gj6Gn9wA=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ7gj6GqUSs=", + "_parent": { + "$ref": "AAAAAAFdHQ7gj6GpG4g=" + }, + "model": { + "$ref": "AAAAAAFdHQ7gj6Gn9wA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 484, + "top": 352, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ7gj6GpG4g=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ7gj6Grtfg=", + "_parent": { + "$ref": "AAAAAAFdHQ7gj6GpG4g=" + }, + "model": { + "$ref": "AAAAAAFdHQ7gj6Gn9wA=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 440, + "top": 344, + "width": 53, + "height": 13, + "autoResize": false, + "alpha": 0.5922712548213971, + "distance": 24.515301344262525, + "hostEdge": { + "$ref": "AAAAAAFdHQ7gj6GpG4g=" + }, + "edgePosition": 1, + "underline": false, + "text": "«extend»", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ7gj6Gs0Zk=", + "_parent": { + "$ref": "AAAAAAFdHQ7gj6GpG4g=" + }, + "model": { + "$ref": "AAAAAAFdHQ7gj6Gn9wA=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 495, + "top": 325, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ7gj6GpG4g=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdGAO/iqSO/fU=" + }, + "tail": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "lineStyle": 1, + "points": "544:367;436:323", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHQ7gj6GqUSs=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ7gj6Grtfg=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ7gj6Gs0Zk=" + } + }, + { + "_type": "UMLExtendView", + "_id": "AAAAAAFdHQ8AdqIMIpQ=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ8AdqIKyBQ=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ8AdqINQDI=", + "_parent": { + "$ref": "AAAAAAFdHQ8AdqIMIpQ=" + }, + "model": { + "$ref": "AAAAAAFdHQ8AdqIKyBQ=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 581, + "top": 328, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ8AdqIMIpQ=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ8AdqIOOpY=", + "_parent": { + "$ref": "AAAAAAFdHQ8AdqIMIpQ=" + }, + "model": { + "$ref": "AAAAAAFdHQ8AdqIKyBQ=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 540, + "top": 325, + "width": 53, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ8AdqIMIpQ=" + }, + "edgePosition": 1, + "underline": false, + "text": "«extend»", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ8AdqIP3rw=", + "_parent": { + "$ref": "AAAAAAFdHQ8AdqIMIpQ=" + }, + "model": { + "$ref": "AAAAAAFdHQ8AdqIKyBQ=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 610, + "top": 333, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ8AdqIMIpQ=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdHQ4fLp+/lbg=" + }, + "tail": { + "$ref": "AAAAAAFdGAXoA6UbzVQ=" + }, + "lineStyle": 1, + "points": "591:367;602:307", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHQ8AdqINQDI=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ8AdqIOOpY=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ8AdqIP3rw=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdHQ882aKZU8U=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdHQ882aKagds=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ882aKbCFY=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKagds=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -144, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ882aKcJss=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKagds=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 333, + "top": 419.5, + "width": 64, + "height": 13, + "autoResize": false, + "underline": false, + "text": "显示购物车", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ882aKdAj4=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKagds=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -144, + "top": 0, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ882aKeFk8=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKagds=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -144, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 328, + "top": 412.5, + "width": 75, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ882aKbCFY=" + }, + "nameLabel": { + "$ref": "AAAAAAFdHQ882aKcJss=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdHQ882aKdAj4=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ882aKeFk8=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdHQ882aKfXY8=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -72, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdHQ882qKgImc=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -72, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdHQ882qKhtB0=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -72, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdHQ882qKiU5Q=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -72, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdHQ882qKj6Uw=", + "_parent": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "model": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -72, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 312, + "top": 408, + "width": 106, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdHQ882aKagds=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdHQ882aKfXY8=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdHQ882qKgImc=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdHQ882qKhtB0=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdHQ882qKiU5Q=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdHQ882qKj6Uw=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdHQ9cP6L6Aeo=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL2MKE=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cP6L7zvs=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL2MKE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 240, + "top": 459, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQaL8CqM=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL2MKE=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 234, + "top": 445, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqL9dnk=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL2MKE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 253, + "top": 486, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqL+ddA=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL3JSg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 187, + "top": 484, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqL/dNg=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL3JSg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 183, + "top": 471, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqMATrE=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL3JSg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 194, + "top": 511, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqMBCKU=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL4Obc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 295, + "top": 434, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqMCH3Y=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL4Obc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 287, + "top": 423, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ9cQqMDqB8=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL4Obc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 310, + "top": 457, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdHQ9cQqMEVYQ=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL3JSg=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdHQ9cQ6MFMeQ=", + "_parent": { + "$ref": "AAAAAAFdHQ9cP6L6Aeo=" + }, + "model": { + "$ref": "AAAAAAFdHQ9cPqL4Obc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "tail": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "lineStyle": 1, + "points": "170:515;325:443", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHQ9cP6L7zvs=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ9cQaL8CqM=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ9cQqL9dnk=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdHQ9cQqL+ddA=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdHQ9cQqL/dNg=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdHQ9cQqMATrE=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdHQ9cQqMBCKU=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdHQ9cQqMCH3Y=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdHQ9cQqMDqB8=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdHQ9cQqMEVYQ=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdHQ9cQ6MFMeQ=" + } + }, + { + "_type": "UMLExtendView", + "_id": "AAAAAAFdHQ+6bqQX4zM=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ+6bqQVrTI=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ+6b6QYXyk=", + "_parent": { + "$ref": "AAAAAAFdHQ+6bqQX4zM=" + }, + "model": { + "$ref": "AAAAAAFdHQ+6bqQVrTI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 440, + "top": 453, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ+6bqQX4zM=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ+6b6QZrOI=", + "_parent": { + "$ref": "AAAAAAFdHQ+6bqQX4zM=" + }, + "model": { + "$ref": "AAAAAAFdHQ+6bqQVrTI=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 408, + "top": 448, + "width": 53, + "height": 13, + "autoResize": false, + "alpha": 0.9596145313479303, + "distance": 13.45362404707371, + "hostEdge": { + "$ref": "AAAAAAFdHQ+6bqQX4zM=" + }, + "edgePosition": 1, + "underline": false, + "text": "«extend»", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ+6b6QaSio=", + "_parent": { + "$ref": "AAAAAAFdHQ+6bqQX4zM=" + }, + "model": { + "$ref": "AAAAAAFdHQ+6bqQVrTI=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 447, + "top": 424, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ+6bqQX4zM=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdHQ882aKZU8U=" + }, + "tail": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "lineStyle": 1, + "points": "471:452;418:439", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHQ+6b6QYXyk=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ+6b6QZrOI=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ+6b6QaSio=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdHQ/nDaSMkME=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SIpV8=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDaSNdP4=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SIpV8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 218, + "top": 517, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDaSO7po=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SIpV8=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 220, + "top": 502, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSPPvg=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SIpV8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 213, + "top": 546, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSQ5n8=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SJEfc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 197, + "top": 514, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSRoK0=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SJEfc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 202, + "top": 501, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSSHNE=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SJEfc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 189, + "top": 540, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSTDv4=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SKfbM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 239, + "top": 520, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSUKEc=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SKfbM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 239, + "top": 506, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQ/nDqSV+BU=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SKfbM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 239, + "top": 548, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdHQ/nDqSW3i8=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SJEfc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdHQ/nDqSXffo=", + "_parent": { + "$ref": "AAAAAAFdHQ/nDaSMkME=" + }, + "model": { + "$ref": "AAAAAAFdHQ/nC6SKfbM=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "tail": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "lineStyle": 1, + "points": "170:531;263:545", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHQ/nDaSNdP4=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ/nDaSO7po=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ/nDqSPPvg=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdHQ/nDqSQ5n8=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdHQ/nDqSRoK0=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdHQ/nDqSSHNE=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdHQ/nDqSTDv4=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdHQ/nDqSUKEc=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdHQ/nDqSV+BU=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdHQ/nDqSW3i8=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdHQ/nDqSXffo=" + } + }, + { + "_type": "UMLUseCaseView", + "_id": "AAAAAAFdHQ/+ZqTrAgU=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdHQ/+ZqTsUt0=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ/+Z6TtsU0=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTsUt0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -32, + "top": -16, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ/+Z6TuoEc=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTsUt0=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 283.5, + "top": 619.5, + "width": 59, + "height": 13, + "autoResize": false, + "underline": false, + "text": "注册", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ/+Z6TvnVY=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTsUt0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -32, + "top": -16, + "width": 65, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from UML)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQ/+Z6TwpEY=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTsUt0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -32, + "top": -16, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 278.5, + "top": 612.5, + "width": 69, + "height": 25, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQ/+Z6TtsU0=" + }, + "nameLabel": { + "$ref": "AAAAAAFdHQ/+Z6TuoEc=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdHQ/+Z6TvnVY=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQ/+Z6TwpEY=" + } + }, + { + "_type": "UMLAttributeCompartmentView", + "_id": "AAAAAAFdHQ/+Z6Tx1GQ=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -16, + "top": -8, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLOperationCompartmentView", + "_id": "AAAAAAFdHQ/+aKTyY7E=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -16, + "top": -8, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLReceptionCompartmentView", + "_id": "AAAAAAFdHQ/+aKTzGEk=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -16, + "top": -8, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLTemplateParameterCompartmentView", + "_id": "AAAAAAFdHQ/+aKT0jnU=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -16, + "top": -8, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLExtensionPointCompartmentView", + "_id": "AAAAAAFdHQ/+aKT1dBo=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "model": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -16, + "top": -8, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": true, + "containerExtending": false, + "left": 264, + "top": 608, + "width": 98, + "height": 35, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdHQ/+ZqTsUt0=" + }, + "wordWrap": false, + "suppressAttributes": true, + "suppressOperations": true, + "suppressReceptions": true, + "showMultiplicity": true, + "showOperationSignature": true, + "attributeCompartment": { + "$ref": "AAAAAAFdHQ/+Z6Tx1GQ=" + }, + "operationCompartment": { + "$ref": "AAAAAAFdHQ/+aKTyY7E=" + }, + "receptionCompartment": { + "$ref": "AAAAAAFdHQ/+aKTzGEk=" + }, + "templateParameterCompartment": { + "$ref": "AAAAAAFdHQ/+aKT0jnU=" + }, + "extensionPointCompartment": { + "$ref": "AAAAAAFdHQ/+aKT1dBo=" + } + }, + { + "_type": "UMLExtendView", + "_id": "AAAAAAFdHRAkKaVi4M8=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHRAkKaVg3zE=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRAkKaVjtmc=", + "_parent": { + "$ref": "AAAAAAFdHRAkKaVi4M8=" + }, + "model": { + "$ref": "AAAAAAFdHRAkKaVg3zE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 297, + "top": 582, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHRAkKaVi4M8=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRAkKqVk7LU=", + "_parent": { + "$ref": "AAAAAAFdHRAkKaVi4M8=" + }, + "model": { + "$ref": "AAAAAAFdHRAkKaVg3zE=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": 582, + "width": 53, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHRAkKaVi4M8=" + }, + "edgePosition": 1, + "underline": false, + "text": "«extend»", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRAkKqVlFnA=", + "_parent": { + "$ref": "AAAAAAFdHRAkKaVi4M8=" + }, + "model": { + "$ref": "AAAAAAFdHRAkKaVg3zE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 326, + "top": 583, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHRAkKaVi4M8=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "tail": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "lineStyle": 1, + "points": "312:607;312:571", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHRAkKaVjtmc=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHRAkKqVk7LU=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHRAkKqVlFnA=" + } + }, + { + "_type": "UMLAssociationView", + "_id": "AAAAAAFdHRA1LqWixAs=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWeYgw=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WjkHo=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWeYgw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 232, + "top": 555, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WkyuM=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWeYgw=" + }, + "visible": null, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 240, + "top": 542, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6Wl/Us=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWeYgw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 217, + "top": 580, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6Wm/vw=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWfgCc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 199, + "top": 536, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WnyBs=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWfgCc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 208, + "top": 525, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WollM=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWfgCc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 182, + "top": 557, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 2, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WpMj4=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWgex0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 266, + "top": 574, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.5235987755982988, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WqZWg=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWgex0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 270, + "top": 562, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -0.7853981633974483, + "distance": 40, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRA1L6WrUmo=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWgex0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 256, + "top": 600, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 0.5235987755982988, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "edgePosition": 0, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdHRA1L6WsvHA=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWfgCc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + }, + { + "_type": "UMLQualifierCompartmentView", + "_id": "AAAAAAFdHRA1L6WtjWo=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWixAs=" + }, + "model": { + "$ref": "AAAAAAFdHRA1LqWgex0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 0, + "top": 0, + "width": 10, + "height": 10, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdHQ/+ZqTrAgU=" + }, + "tail": { + "$ref": "AAAAAAFdGAKakqRiXVU=" + }, + "lineStyle": 1, + "points": "170:542;281:607", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHRA1L6WjkHo=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHRA1L6WkyuM=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHRA1L6Wl/Us=" + }, + "showMultiplicity": true, + "showType": true, + "tailRoleNameLabel": { + "$ref": "AAAAAAFdHRA1L6Wm/vw=" + }, + "tailPropertyLabel": { + "$ref": "AAAAAAFdHRA1L6WnyBs=" + }, + "tailMultiplicityLabel": { + "$ref": "AAAAAAFdHRA1L6WollM=" + }, + "headRoleNameLabel": { + "$ref": "AAAAAAFdHRA1L6WpMj4=" + }, + "headPropertyLabel": { + "$ref": "AAAAAAFdHRA1L6WqZWg=" + }, + "headMultiplicityLabel": { + "$ref": "AAAAAAFdHRA1L6WrUmo=" + }, + "tailQualifiersCompartment": { + "$ref": "AAAAAAFdHRA1L6WsvHA=" + }, + "headQualifiersCompartment": { + "$ref": "AAAAAAFdHRA1L6WtjWo=" + } + }, + { + "_type": "UMLIncludeView", + "_id": "AAAAAAFdHRBbZKYcUQM=", + "_parent": { + "$ref": "AAAAAAFdF8yd/5z3Wwc=" + }, + "model": { + "$ref": "AAAAAAFdHRBbZKYaDv0=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRBbZaYdj30=", + "_parent": { + "$ref": "AAAAAAFdHRBbZKYcUQM=" + }, + "model": { + "$ref": "AAAAAAFdHRBbZKYaDv0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 421, + "top": 516, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHRBbZKYcUQM=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRBbZaYeH/M=", + "_parent": { + "$ref": "AAAAAAFdHRBbZKYcUQM=" + }, + "model": { + "$ref": "AAAAAAFdHRBbZKYaDv0=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 400, + "top": 530, + "width": 55, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 30, + "hostEdge": { + "$ref": "AAAAAAFdHRBbZKYcUQM=" + }, + "edgePosition": 1, + "underline": false, + "text": "«include»", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHRBbZaYfqBU=", + "_parent": { + "$ref": "AAAAAAFdHRBbZKYcUQM=" + }, + "model": { + "$ref": "AAAAAAFdHRBbZKYaDv0=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 410, + "top": 489, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 15, + "hostEdge": { + "$ref": "AAAAAAFdHRBbZKYcUQM=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdGAW4LqTsTLE=" + }, + "tail": { + "$ref": "AAAAAAFdGAY0uaVJfPE=" + }, + "lineStyle": 1, + "points": "477:483;355:535", + "stereotypeDisplay": "label", + "showVisibility": true, + "showProperty": true, + "nameLabel": { + "$ref": "AAAAAAFdHRBbZaYdj30=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHRBbZaYeH/M=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHRBbZaYfqBU=" + } + } + ] + }, + { + "_type": "UMLClass", + "_id": "AAAAAAFdF9Jh5Z1ciZA=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "Player", + "ownedElements": [ + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdF9dc2J3pDD0=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdF9dc2J3qoKU=", + "_parent": { + "$ref": "AAAAAAFdF9dc2J3pDD0=" + }, + "reference": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "visibility": "public", + "navigable": false, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdF9dc2Z3rpO4=", + "_parent": { + "$ref": "AAAAAAFdF9dc2J3pDD0=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdG6VR1p1Gsno=", + "_parent": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6VR1p1HuPE=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1Gsno=" + }, + "reference": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6VR1p1IHBQ=", + "_parent": { + "$ref": "AAAAAAFdG6VR1p1Gsno=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + } + ], + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false, + "isActive": false + }, + { + "_type": "UMLClass", + "_id": "AAAAAAFdF9NBMZ2Jv50=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "DiceGame", + "ownedElements": [ + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdF99KOaCQNwo=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdF99KOaCRrPU=", + "_parent": { + "$ref": "AAAAAAFdF99KOaCQNwo=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdF99KOaCSiy0=", + "_parent": { + "$ref": "AAAAAAFdF99KOaCQNwo=" + }, + "reference": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "composite", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdG6MH7Zmtypw=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6MH7ZmuDN4=", + "_parent": { + "$ref": "AAAAAAFdG6MH7Zmtypw=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6MH7Zmvqpw=", + "_parent": { + "$ref": "AAAAAAFdG6MH7Zmtypw=" + }, + "reference": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "composite", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdG6TzIJwX5cs=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6TzIJwYZJ8=", + "_parent": { + "$ref": "AAAAAAFdG6TzIJwX5cs=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6TzIJwZeVE=", + "_parent": { + "$ref": "AAAAAAFdG6TzIJwX5cs=" + }, + "reference": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + } + ], + "visibility": "public", + "operations": [ + { + "_type": "UMLOperation", + "_id": "AAAAAAFdF9tkT58TEw0=", + "_parent": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "name": "play", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "concurrency": "sequential", + "isQuery": false, + "isAbstract": false + } + ], + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false, + "isActive": false + }, + { + "_type": "UMLClass", + "_id": "AAAAAAFdF9RF6Z25s+k=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "Dice", + "ownedElements": [ + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdG6Mw9ZoppUM=", + "_parent": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6Mw9ZoqSLc=", + "_parent": { + "$ref": "AAAAAAFdG6Mw9ZoppUM=" + }, + "reference": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6Mw9porfGs=", + "_parent": { + "$ref": "AAAAAAFdG6Mw9ZoppUM=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "composite", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdG6S2iZusc0s=", + "_parent": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6S2iZutrMs=", + "_parent": { + "$ref": "AAAAAAFdG6S2iZusc0s=" + }, + "reference": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdG6S2iZuu5hA=", + "_parent": { + "$ref": "AAAAAAFdG6S2iZusc0s=" + }, + "reference": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "shared", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + } + ], + "visibility": "public", + "operations": [ + { + "_type": "UMLOperation", + "_id": "AAAAAAFdF9yOrp8l+p4=", + "_parent": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "name": "roll", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "concurrency": "sequential", + "isQuery": false, + "isAbstract": false + } + ], + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false, + "isActive": false + }, + { + "_type": "UMLActor", + "_id": "AAAAAAFdGAKakKRgInE=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "用户", + "ownedElements": [ + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdGBfGHaYFPwU=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBfGHaYGRkw=", + "_parent": { + "$ref": "AAAAAAFdGBfGHaYFPwU=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBfGHaYHyF4=", + "_parent": { + "$ref": "AAAAAAFdGBfGHaYFPwU=" + }, + "reference": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdGBfedKZIprQ=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBfedaZJO7I=", + "_parent": { + "$ref": "AAAAAAFdGBfedKZIprQ=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBfedaZKKu0=", + "_parent": { + "$ref": "AAAAAAFdGBfedKZIprQ=" + }, + "reference": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdGBf23qaao/Y=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBf23qabaUY=", + "_parent": { + "$ref": "AAAAAAFdGBf23qaao/Y=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBf23qacez0=", + "_parent": { + "$ref": "AAAAAAFdGBf23qaao/Y=" + }, + "reference": { + "$ref": "AAAAAAFdGAVH16S6bA0=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdGBgGqabpFws=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBgGqabqC0k=", + "_parent": { + "$ref": "AAAAAAFdGBgGqabpFws=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdGBgGqabrjBY=", + "_parent": { + "$ref": "AAAAAAFdGBgGqabpFws=" + }, + "reference": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdHQ9cPqL2MKE=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdHQ9cPqL3JSg=", + "_parent": { + "$ref": "AAAAAAFdHQ9cPqL2MKE=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdHQ9cPqL4Obc=", + "_parent": { + "$ref": "AAAAAAFdHQ9cPqL2MKE=" + }, + "reference": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdHQ/nC6SIpV8=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdHQ/nC6SJEfc=", + "_parent": { + "$ref": "AAAAAAFdHQ/nC6SIpV8=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdHQ/nC6SKfbM=", + "_parent": { + "$ref": "AAAAAAFdHQ/nC6SIpV8=" + }, + "reference": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + }, + { + "_type": "UMLAssociation", + "_id": "AAAAAAFdHRA1LqWeYgw=", + "_parent": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "end1": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdHRA1LqWfgCc=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWeYgw=" + }, + "reference": { + "$ref": "AAAAAAFdGAKakKRgInE=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "end2": { + "_type": "UMLAssociationEnd", + "_id": "AAAAAAFdHRA1LqWgex0=", + "_parent": { + "$ref": "AAAAAAFdHRA1LqWeYgw=" + }, + "reference": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "visibility": "public", + "navigable": true, + "aggregation": "none", + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "isID": false + }, + "visibility": "public", + "isDerived": false + } + ], + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdGAO/iaSMYxI=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "搜索产品", + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdGAVH16S6bA0=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "查看产品细节", + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdGAW4LaTq8JA=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "登录", + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdGAXoAqUZa/0=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "加入购物车", + "ownedElements": [ + { + "_type": "UMLExtend", + "_id": "AAAAAAFdHQ7gj6Gn9wA=", + "_parent": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "source": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "target": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visibility": "public" + }, + { + "_type": "UMLExtend", + "_id": "AAAAAAFdHQ8AdqIKyBQ=", + "_parent": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "source": { + "$ref": "AAAAAAFdGAXoAqUZa/0=" + }, + "target": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "visibility": "public" + } + ], + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdGAY0uKVHc28=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "下订单", + "ownedElements": [ + { + "_type": "UMLInclude", + "_id": "AAAAAAFdGBT5vaXucnQ=", + "_parent": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "source": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "target": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visibility": "public" + }, + { + "_type": "UMLExtend", + "_id": "AAAAAAFdHQ+6bqQVrTI=", + "_parent": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "source": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "target": { + "$ref": "AAAAAAFdHQ882KKXixg=" + }, + "visibility": "public" + }, + { + "_type": "UMLInclude", + "_id": "AAAAAAFdHRBbZKYaDv0=", + "_parent": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "source": { + "$ref": "AAAAAAFdGAY0uKVHc28=" + }, + "target": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visibility": "public" + } + ], + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdGAfYTKV2bvY=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "产品", + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCaseSubject", + "_id": "AAAAAAFdGBPCQaWkzJE=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "UseCaseSubject1", + "visibility": "public" + }, + { + "_type": "UMLClass", + "_id": "AAAAAAFdG6RIwpshRVw=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "Display", + "visibility": "public", + "operations": [ + { + "_type": "UMLOperation", + "_id": "AAAAAAFdG6UEzJx4aDY=", + "_parent": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "name": "showResult", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "concurrency": "sequential", + "isQuery": false, + "isAbstract": false + } + ], + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false, + "isActive": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdHQ4fLZ+9HuM=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "查看产品详情", + "ownedElements": [ + { + "_type": "UMLExtend", + "_id": "AAAAAAFdHQ57DaAopRI=", + "_parent": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "source": { + "$ref": "AAAAAAFdHQ4fLZ+9HuM=" + }, + "target": { + "$ref": "AAAAAAFdGAO/iaSMYxI=" + }, + "visibility": "public" + } + ], + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdHQ882KKXixg=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "显示购物车", + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + }, + { + "_type": "UMLUseCase", + "_id": "AAAAAAFdHQ/+ZqTpmg8=", + "_parent": { + "$ref": "AAAAAAFdF8bUGpzmKj4=" + }, + "name": "注册", + "ownedElements": [ + { + "_type": "UMLExtend", + "_id": "AAAAAAFdHRAkKaVg3zE=", + "_parent": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "source": { + "$ref": "AAAAAAFdHQ/+ZqTpmg8=" + }, + "target": { + "$ref": "AAAAAAFdGAW4LaTq8JA=" + }, + "visibility": "public" + } + ], + "visibility": "public", + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + } + ], + "visibility": "public" + }, + { + "_type": "UMLCollaboration", + "_id": "AAAAAAFdF9ENuJ1Khbw=", + "_parent": { + "$ref": "AAAAAAFF+h6SjaM2Hec=" + }, + "name": "Collaboration", + "ownedElements": [ + { + "_type": "UMLInteraction", + "_id": "AAAAAAFdF9ENuJ1LFdg=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1Khbw=" + }, + "name": "Interaction", + "ownedElements": [ + { + "_type": "UMLSequenceDiagram", + "_id": "AAAAAAFdF9ENuJ1MVCI=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "掷骰子顺序图", + "visible": true, + "defaultDiagram": false, + "ownedViews": [ + { + "_type": "UMLFrameView", + "_id": "AAAAAAFdF9ENuJ1NVPk=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF9ENuZ1OWM4=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1NVPk=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 76, + "top": 10, + "width": 79, + "height": 13, + "autoResize": false, + "underline": false, + "text": "掷骰子顺序图", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF9ENuZ1P378=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1NVPk=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 10, + "top": 10, + "width": 61, + "height": 13, + "autoResize": false, + "underline": false, + "text": "interaction", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 5, + "top": 5, + "width": 695, + "height": 595, + "autoResize": false, + "nameLabel": { + "$ref": "AAAAAAFdF9ENuZ1OWM4=" + }, + "frameTypeLabel": { + "$ref": "AAAAAAFdF9ENuZ1P378=" + } + }, + { + "_type": "UMLSeqLifelineView", + "_id": "AAAAAAFdF+OdeqGXCpA=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdF+OdeqGWcbc=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdF+OdeqGYEEU=", + "_parent": { + "$ref": "AAAAAAFdF+OdeqGXCpA=" + }, + "model": { + "$ref": "AAAAAAFdF+OdeqGWcbc=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF+Ode6GZUBc=", + "_parent": { + "$ref": "AAAAAAFdF+OdeqGYEEU=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -160, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+Ode6GavkA=", + "_parent": { + "$ref": "AAAAAAFdF+OdeqGYEEU=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 85, + "top": 47, + "width": 95, + "height": 13, + "autoResize": false, + "underline": false, + "text": "player: Player", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+Ode6Gb7JQ=", + "_parent": { + "$ref": "AAAAAAFdF+OdeqGYEEU=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -160, + "top": 0, + "width": 99, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from Interaction)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+OdfKGc5R8=", + "_parent": { + "$ref": "AAAAAAFdF+OdeqGYEEU=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -160, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 80, + "top": 40, + "width": 105, + "height": 40, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdF+Ode6GZUBc=" + }, + "nameLabel": { + "$ref": "AAAAAAFdF+Ode6GavkA=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdF+Ode6Gb7JQ=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF+OdfKGc5R8=" + } + }, + { + "_type": "UMLLinePartView", + "_id": "AAAAAAFdF+OdfKGdq7U=", + "_parent": { + "$ref": "AAAAAAFdF+OdeqGXCpA=" + }, + "model": { + "$ref": "AAAAAAFdF+OdeqGWcbc=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 133, + "top": 80, + "width": 1, + "height": 271, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 80, + "top": 40, + "width": 105, + "height": 311, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdF+OdeqGYEEU=" + }, + "wordWrap": false, + "linePart": { + "$ref": "AAAAAAFdF+OdfKGdq7U=" + } + }, + { + "_type": "UMLSeqLifelineView", + "_id": "AAAAAAFdF+RP86G5S4s=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdF+RP86G6V2w=", + "_parent": { + "$ref": "AAAAAAFdF+RP86G5S4s=" + }, + "model": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF+RP86G7KPw=", + "_parent": { + "$ref": "AAAAAAFdF+RP86G6V2w=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -80, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+RP9KG8g9w=", + "_parent": { + "$ref": "AAAAAAFdF+RP86G6V2w=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 205, + "top": 47, + "width": 143, + "height": 13, + "autoResize": false, + "underline": false, + "text": "diceGame: DiceGame", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+RP9KG9Bck=", + "_parent": { + "$ref": "AAAAAAFdF+RP86G6V2w=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -80, + "top": 0, + "width": 99, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from Interaction)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+RP9KG+FO0=", + "_parent": { + "$ref": "AAAAAAFdF+RP86G6V2w=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -80, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 200, + "top": 40, + "width": 153, + "height": 40, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdF+RP86G7KPw=" + }, + "nameLabel": { + "$ref": "AAAAAAFdF+RP9KG8g9w=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdF+RP9KG9Bck=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF+RP9KG+FO0=" + } + }, + { + "_type": "UMLLinePartView", + "_id": "AAAAAAFdF+RP9KG/qmo=", + "_parent": { + "$ref": "AAAAAAFdF+RP86G5S4s=" + }, + "model": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 277, + "top": 80, + "width": 1, + "height": 283, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 200, + "top": 40, + "width": 153, + "height": 323, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdF+RP86G6V2w=" + }, + "wordWrap": false, + "linePart": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + } + }, + { + "_type": "UMLSeqLifelineView", + "_id": "AAAAAAFdF+UgqKHvECc=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdF+Ugp6Huy74=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdF+UgqKHwKJY=", + "_parent": { + "$ref": "AAAAAAFdF+UgqKHvECc=" + }, + "model": { + "$ref": "AAAAAAFdF+Ugp6Huy74=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdF+UgqaHx/1c=", + "_parent": { + "$ref": "AAAAAAFdF+UgqKHwKJY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -96, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+UgqaHy7Ec=", + "_parent": { + "$ref": "AAAAAAFdF+UgqKHwKJY=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 373, + "top": 47, + "width": 78, + "height": 13, + "autoResize": false, + "underline": false, + "text": "dice1: Dice", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+UgqaHzfxg=", + "_parent": { + "$ref": "AAAAAAFdF+UgqKHwKJY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -96, + "top": 0, + "width": 99, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from Interaction)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdF+UgqaH0Efk=", + "_parent": { + "$ref": "AAAAAAFdF+UgqKHwKJY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -96, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 368, + "top": 40, + "width": 88, + "height": 40, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdF+UgqaHx/1c=" + }, + "nameLabel": { + "$ref": "AAAAAAFdF+UgqaHy7Ec=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdF+UgqaHzfxg=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF+UgqaH0Efk=" + } + }, + { + "_type": "UMLLinePartView", + "_id": "AAAAAAFdF+UgqaH1Ack=", + "_parent": { + "$ref": "AAAAAAFdF+UgqKHvECc=" + }, + "model": { + "$ref": "AAAAAAFdF+Ugp6Huy74=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 412, + "top": 80, + "width": 1, + "height": 209, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 368, + "top": 40, + "width": 88, + "height": 249, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdF+UgqKHwKJY=" + }, + "wordWrap": false, + "linePart": { + "$ref": "AAAAAAFdF+UgqaH1Ack=" + } + }, + { + "_type": "UMLSeqMessageView", + "_id": "AAAAAAFdF+TkA6HYtTw=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdF+TkA6HXVqw=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdF+TkBKHZZ+Y=", + "_parent": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "model": { + "$ref": "AAAAAAFdF+TkA6HXVqw=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 162, + "top": 167, + "width": 79, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "edgePosition": 1, + "underline": false, + "text": "1 : play", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdF+TkBKHaWq4=", + "_parent": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "model": { + "$ref": "AAAAAAFdF+TkA6HXVqw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 201, + "top": 152, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdF+TkBKHbuuY=", + "_parent": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "model": { + "$ref": "AAAAAAFdF+TkA6HXVqw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 201, + "top": 187, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLActivationView", + "_id": "AAAAAAFdF+TkBKHctG4=", + "_parent": { + "$ref": "AAAAAAFdF+TkA6HYtTw=" + }, + "model": { + "$ref": "AAAAAAFdF+TkA6HXVqw=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 270, + "top": 183, + "width": 14, + "height": 154, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "tail": { + "$ref": "AAAAAAFdF+OdfKGdq7U=" + }, + "lineStyle": 0, + "points": "133:183;270:183", + "nameLabel": { + "$ref": "AAAAAAFdF+TkBKHZZ+Y=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdF+TkBKHaWq4=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF+TkBKHbuuY=" + }, + "activation": { + "$ref": "AAAAAAFdF+TkBKHctG4=" + }, + "showProperty": true, + "showType": true + }, + { + "_type": "UMLSeqMessageView", + "_id": "AAAAAAFdF/sfZqPnl+I=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdF/sfZaPm+zc=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdF/sfZqPogK0=", + "_parent": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "model": { + "$ref": "AAAAAAFdF/sfZaPm+zc=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 305, + "top": 178, + "width": 79, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "edgePosition": 1, + "underline": false, + "text": "2 : roll", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdF/sfZqPp5uY=", + "_parent": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "model": { + "$ref": "AAAAAAFdF/sfZaPm+zc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 344, + "top": 163, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdF/sfZqPqawY=", + "_parent": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "model": { + "$ref": "AAAAAAFdF/sfZaPm+zc=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 344, + "top": 198, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLActivationView", + "_id": "AAAAAAFdF/sfZqPrd6c=", + "_parent": { + "$ref": "AAAAAAFdF/sfZqPnl+I=" + }, + "model": { + "$ref": "AAAAAAFdF/sfZaPm+zc=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 405, + "top": 194, + "width": 14, + "height": 29, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdF+UgqaH1Ack=" + }, + "tail": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "lineStyle": 0, + "points": "283:194;405:194", + "nameLabel": { + "$ref": "AAAAAAFdF/sfZqPogK0=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdF/sfZqPp5uY=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdF/sfZqPqawY=" + }, + "activation": { + "$ref": "AAAAAAFdF/sfZqPrd6c=" + }, + "showProperty": true, + "showType": true + }, + { + "_type": "UMLSeqMessageView", + "_id": "AAAAAAFdHQp4LZ8Q7dM=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdHQp4LZ8P0ZU=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQp4LZ8R3GI=", + "_parent": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "model": { + "$ref": "AAAAAAFdHQp4LZ8P0ZU=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 357, + "top": 232, + "width": 79, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "edgePosition": 1, + "underline": false, + "text": "3 : roll", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQp4LZ8S8XE=", + "_parent": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "model": { + "$ref": "AAAAAAFdHQp4LZ8P0ZU=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 396, + "top": 217, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQp4LZ8TEEM=", + "_parent": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "model": { + "$ref": "AAAAAAFdHQp4LZ8P0ZU=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 396, + "top": 252, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLActivationView", + "_id": "AAAAAAFdHQp4LZ8UAbU=", + "_parent": { + "$ref": "AAAAAAFdHQp4LZ8Q7dM=" + }, + "model": { + "$ref": "AAAAAAFdHQp4LZ8P0ZU=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 509, + "top": 248, + "width": 14, + "height": 29, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdHQn7x57ralA=" + }, + "tail": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "lineStyle": 0, + "points": "283:248;509:248", + "nameLabel": { + "$ref": "AAAAAAFdHQp4LZ8R3GI=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQp4LZ8S8XE=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQp4LZ8TEEM=" + }, + "activation": { + "$ref": "AAAAAAFdHQp4LZ8UAbU=" + }, + "showProperty": true, + "showType": true + }, + { + "_type": "UMLSeqLifelineView", + "_id": "AAAAAAFdHQn7xp7lBR4=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdHQn7xp7kRhc=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdHQn7x57mVek=", + "_parent": { + "$ref": "AAAAAAFdHQn7xp7lBR4=" + }, + "model": { + "$ref": "AAAAAAFdHQn7xp7kRhc=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdHQn7x57nLbY=", + "_parent": { + "$ref": "AAAAAAFdHQn7x57mVek=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -176, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQn7x57o4+o=", + "_parent": { + "$ref": "AAAAAAFdHQn7x57mVek=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 477, + "top": 47, + "width": 78, + "height": 13, + "autoResize": false, + "underline": false, + "text": "dice2: Dice", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQn7x57pTmg=", + "_parent": { + "$ref": "AAAAAAFdHQn7x57mVek=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -176, + "top": 0, + "width": 99, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from Interaction)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQn7x57qzPQ=", + "_parent": { + "$ref": "AAAAAAFdHQn7x57mVek=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -176, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 472, + "top": 40, + "width": 88, + "height": 40, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQn7x57nLbY=" + }, + "nameLabel": { + "$ref": "AAAAAAFdHQn7x57o4+o=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdHQn7x57pTmg=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQn7x57qzPQ=" + } + }, + { + "_type": "UMLLinePartView", + "_id": "AAAAAAFdHQn7x57ralA=", + "_parent": { + "$ref": "AAAAAAFdHQn7xp7lBR4=" + }, + "model": { + "$ref": "AAAAAAFdHQn7xp7kRhc=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 516, + "top": 80, + "width": 1, + "height": 233, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 472, + "top": 40, + "width": 88, + "height": 273, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdHQn7x57mVek=" + }, + "wordWrap": false, + "linePart": { + "$ref": "AAAAAAFdHQn7x57ralA=" + } + }, + { + "_type": "UMLSeqMessageView", + "_id": "AAAAAAFdHQrka58ztv8=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdHQrkap8ywZE=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQrka580RZc=", + "_parent": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "model": { + "$ref": "AAAAAAFdHQrkap8ywZE=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 280, + "top": 259, + "width": 84, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "edgePosition": 1, + "underline": false, + "text": "4 : checkIfWin", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQrka581cj0=", + "_parent": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "model": { + "$ref": "AAAAAAFdHQrkap8ywZE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 337, + "top": 259, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQrka582R4Q=", + "_parent": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "model": { + "$ref": "AAAAAAFdHQrkap8ywZE=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 303, + "top": 260, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLActivationView", + "_id": "AAAAAAFdHQrka5831N4=", + "_parent": { + "$ref": "AAAAAAFdHQrka58ztv8=" + }, + "model": { + "$ref": "AAAAAAFdHQrkap8ywZE=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 277, + "top": 276, + "width": 14, + "height": 29, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "tail": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "lineStyle": 0, + "points": "283:256;313:256;313:276;290:276", + "nameLabel": { + "$ref": "AAAAAAFdHQrka580RZc=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQrka581cj0=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQrka582R4Q=" + }, + "activation": { + "$ref": "AAAAAAFdHQrka5831N4=" + }, + "showProperty": true, + "showType": true + }, + { + "_type": "UMLSeqMessageView", + "_id": "AAAAAAFdHQtT8J9UAqo=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdHQtT8J9TQQw=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQtT8J9VOo0=", + "_parent": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "model": { + "$ref": "AAAAAAFdHQtT8J9TQQw=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 191, + "top": 276, + "width": 19, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "edgePosition": 1, + "underline": false, + "text": "5 : ", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQtT8J9WSys=", + "_parent": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "model": { + "$ref": "AAAAAAFdHQtT8J9TQQw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 200, + "top": 291, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQtT8Z9XeJ4=", + "_parent": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "model": { + "$ref": "AAAAAAFdHQtT8J9TQQw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 201, + "top": 256, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLActivationView", + "_id": "AAAAAAFdHQtT8Z9YmtM=", + "_parent": { + "$ref": "AAAAAAFdHQtT8J9UAqo=" + }, + "model": { + "$ref": "AAAAAAFdHQtT8J9TQQw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 133, + "top": 272, + "width": 14, + "height": 25, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdF+OdfKGdq7U=" + }, + "tail": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "lineStyle": 0, + "points": "270:272;133:272", + "nameLabel": { + "$ref": "AAAAAAFdHQtT8J9VOo0=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQtT8J9WSys=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQtT8Z9XeJ4=" + }, + "activation": { + "$ref": "AAAAAAFdHQtT8Z9YmtM=" + }, + "showProperty": true, + "showType": true + }, + { + "_type": "UMLSeqLifelineView", + "_id": "AAAAAAFdHQt8mJ9qCGY=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdHQt8mJ9p6E8=" + }, + "subViews": [ + { + "_type": "UMLNameCompartmentView", + "_id": "AAAAAAFdHQt8mJ9ruWw=", + "_parent": { + "$ref": "AAAAAAFdHQt8mJ9qCGY=" + }, + "model": { + "$ref": "AAAAAAFdHQt8mJ9p6E8=" + }, + "subViews": [ + { + "_type": "LabelView", + "_id": "AAAAAAFdHQt8mZ9sOEM=", + "_parent": { + "$ref": "AAAAAAFdHQt8mJ9ruWw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -192, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQt8mZ9tGhY=", + "_parent": { + "$ref": "AAAAAAFdHQt8mJ9ruWw=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;1", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 573, + "top": 47, + "width": 109, + "height": 13, + "autoResize": false, + "underline": false, + "text": "display: Display", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQt8mZ9uDAY=", + "_parent": { + "$ref": "AAAAAAFdHQt8mJ9ruWw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -192, + "top": 0, + "width": 99, + "height": 13, + "autoResize": false, + "underline": false, + "text": "(from Interaction)", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "LabelView", + "_id": "AAAAAAFdHQt8mZ9vP4w=", + "_parent": { + "$ref": "AAAAAAFdHQt8mJ9ruWw=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": -192, + "top": 0, + "width": 0, + "height": 13, + "autoResize": false, + "underline": false, + "horizontalAlignment": 1, + "verticalAlignment": 5, + "wordWrap": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 568, + "top": 40, + "width": 119, + "height": 40, + "autoResize": false, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQt8mZ9sOEM=" + }, + "nameLabel": { + "$ref": "AAAAAAFdHQt8mZ9tGhY=" + }, + "namespaceLabel": { + "$ref": "AAAAAAFdHQt8mZ9uDAY=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQt8mZ9vP4w=" + } + }, + { + "_type": "UMLLinePartView", + "_id": "AAAAAAFdHQt8mZ9w62Y=", + "_parent": { + "$ref": "AAAAAAFdHQt8mJ9qCGY=" + }, + "model": { + "$ref": "AAAAAAFdHQt8mJ9p6E8=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 628, + "top": 80, + "width": 1, + "height": 283, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 568, + "top": 40, + "width": 119, + "height": 323, + "autoResize": false, + "stereotypeDisplay": "label", + "showVisibility": true, + "showNamespace": false, + "showProperty": true, + "showType": true, + "nameCompartment": { + "$ref": "AAAAAAFdHQt8mJ9ruWw=" + }, + "wordWrap": false, + "linePart": { + "$ref": "AAAAAAFdHQt8mZ9w62Y=" + } + }, + { + "_type": "UMLSeqMessageView", + "_id": "AAAAAAFdHQxJ4p+Q4MA=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1MVCI=" + }, + "model": { + "$ref": "AAAAAAFdHQxJ4p+P7MY=" + }, + "subViews": [ + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQxJ45+RqsQ=", + "_parent": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "model": { + "$ref": "AAAAAAFdHQxJ4p+P7MY=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 409, + "top": 304, + "width": 86, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "edgePosition": 1, + "underline": false, + "text": "6 : showResult", + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQxJ45+STu4=", + "_parent": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "model": { + "$ref": "AAAAAAFdHQxJ4p+P7MY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 452, + "top": 289, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": 1.5707963267948966, + "distance": 25, + "hostEdge": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "EdgeLabelView", + "_id": "AAAAAAFdHQxJ45+TGcs=", + "_parent": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "model": { + "$ref": "AAAAAAFdHQxJ4p+P7MY=" + }, + "visible": false, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 452, + "top": 324, + "width": 0, + "height": 13, + "autoResize": false, + "alpha": -1.5707963267948966, + "distance": 10, + "hostEdge": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "edgePosition": 1, + "underline": false, + "horizontalAlignment": 2, + "verticalAlignment": 5, + "wordWrap": false + }, + { + "_type": "UMLActivationView", + "_id": "AAAAAAFdHQxJ45+UKO0=", + "_parent": { + "$ref": "AAAAAAFdHQxJ4p+Q4MA=" + }, + "model": { + "$ref": "AAAAAAFdHQxJ4p+P7MY=" + }, + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "left": 621, + "top": 320, + "width": 14, + "height": 29, + "autoResize": false + } + ], + "visible": true, + "enabled": true, + "lineColor": "#000000", + "fillColor": "#ffffff", + "fontColor": "#000000", + "font": "Arial;13;0", + "showShadow": true, + "containerChangeable": false, + "containerExtending": false, + "head": { + "$ref": "AAAAAAFdHQt8mZ9w62Y=" + }, + "tail": { + "$ref": "AAAAAAFdF+RP9KG/qmo=" + }, + "lineStyle": 0, + "points": "283:320;621:320", + "nameLabel": { + "$ref": "AAAAAAFdHQxJ45+RqsQ=" + }, + "stereotypeLabel": { + "$ref": "AAAAAAFdHQxJ45+STu4=" + }, + "propertyLabel": { + "$ref": "AAAAAAFdHQxJ45+TGcs=" + }, + "activation": { + "$ref": "AAAAAAFdHQxJ45+UKO0=" + }, + "showProperty": true, + "showType": true + } + ], + "showSequenceNumber": true, + "showSignature": true, + "showActivation": true + } + ], + "visibility": "public", + "isReentrant": true, + "messages": [ + { + "_type": "UMLMessage", + "_id": "AAAAAAFdF+TkA6HXVqw=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "play", + "source": { + "$ref": "AAAAAAFdF+OdeqGWcbc=" + }, + "target": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "visibility": "public", + "messageSort": "synchCall", + "isConcurrentIteration": false + }, + { + "_type": "UMLMessage", + "_id": "AAAAAAFdF/sfZaPm+zc=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "roll", + "source": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "target": { + "$ref": "AAAAAAFdF+Ugp6Huy74=" + }, + "visibility": "public", + "messageSort": "synchCall", + "isConcurrentIteration": false + }, + { + "_type": "UMLMessage", + "_id": "AAAAAAFdHQp4LZ8P0ZU=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "roll", + "source": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "target": { + "$ref": "AAAAAAFdHQn7xp7kRhc=" + }, + "visibility": "public", + "messageSort": "synchCall", + "isConcurrentIteration": false + }, + { + "_type": "UMLMessage", + "_id": "AAAAAAFdHQrkap8ywZE=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "checkIfWin", + "source": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "target": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "visibility": "public", + "messageSort": "synchCall", + "isConcurrentIteration": false + }, + { + "_type": "UMLMessage", + "_id": "AAAAAAFdHQtT8J9TQQw=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "source": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "target": { + "$ref": "AAAAAAFdF+OdeqGWcbc=" + }, + "visibility": "public", + "messageSort": "reply", + "isConcurrentIteration": false + }, + { + "_type": "UMLMessage", + "_id": "AAAAAAFdHQxJ4p+P7MY=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "showResult", + "source": { + "$ref": "AAAAAAFdF+RP86G4mVc=" + }, + "target": { + "$ref": "AAAAAAFdHQt8mJ9p6E8=" + }, + "visibility": "public", + "messageSort": "synchCall", + "isConcurrentIteration": false + } + ], + "participants": [ + { + "_type": "UMLLifeline", + "_id": "AAAAAAFdF+OdeqGWcbc=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "player", + "visibility": "public", + "represent": { + "$ref": "AAAAAAFdF+OdeaGVt7c=" + }, + "isMultiInstance": false + }, + { + "_type": "UMLLifeline", + "_id": "AAAAAAFdF+RP86G4mVc=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "diceGame", + "visibility": "public", + "represent": { + "$ref": "AAAAAAFdF+RP8qG3O3c=" + }, + "isMultiInstance": false + }, + { + "_type": "UMLLifeline", + "_id": "AAAAAAFdF+Ugp6Huy74=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "dice1", + "visibility": "public", + "represent": { + "$ref": "AAAAAAFdF+Ugp6Htms4=" + }, + "isMultiInstance": false + }, + { + "_type": "UMLLifeline", + "_id": "AAAAAAFdHQn7xp7kRhc=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "dice2", + "visibility": "public", + "represent": { + "$ref": "AAAAAAFdHQn7xZ7jTMM=" + }, + "isMultiInstance": false + }, + { + "_type": "UMLLifeline", + "_id": "AAAAAAFdHQt8mJ9p6E8=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1LFdg=" + }, + "name": "display", + "visibility": "public", + "represent": { + "$ref": "AAAAAAFdHQt8mJ9oW1c=" + }, + "isMultiInstance": false + } + ] + } + ], + "visibility": "public", + "attributes": [ + { + "_type": "UMLAttribute", + "_id": "AAAAAAFdF+OdeaGVt7c=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1Khbw=" + }, + "name": "Role1", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "type": { + "$ref": "AAAAAAFdF9Jh5Z1ciZA=" + }, + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "aggregation": "none", + "isID": false + }, + { + "_type": "UMLAttribute", + "_id": "AAAAAAFdF+RP8qG3O3c=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1Khbw=" + }, + "name": "Role2", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "type": { + "$ref": "AAAAAAFdF9NBMZ2Jv50=" + }, + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "aggregation": "none", + "isID": false + }, + { + "_type": "UMLAttribute", + "_id": "AAAAAAFdF+Ugp6Htms4=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1Khbw=" + }, + "name": "Role3", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "type": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "aggregation": "none", + "isID": false + }, + { + "_type": "UMLAttribute", + "_id": "AAAAAAFdHQn7xZ7jTMM=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1Khbw=" + }, + "name": "Role4", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "type": { + "$ref": "AAAAAAFdF9RF6Z25s+k=" + }, + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "aggregation": "none", + "isID": false + }, + { + "_type": "UMLAttribute", + "_id": "AAAAAAFdHQt8mJ9oW1c=", + "_parent": { + "$ref": "AAAAAAFdF9ENuJ1Khbw=" + }, + "name": "Role5", + "visibility": "public", + "isStatic": false, + "isLeaf": false, + "type": { + "$ref": "AAAAAAFdG6RIwpshRVw=" + }, + "isReadOnly": false, + "isOrdered": false, + "isUnique": false, + "isDerived": false, + "aggregation": "none", + "isID": false + } + ], + "isAbstract": false, + "isFinalSpecialization": false, + "isLeaf": false + } + ] +} \ No newline at end of file From 096522a2ee05c39df8ac2c3414961cb8b863bb3d Mon Sep 17 00:00:00 2001 From: eulerlcs Date: Wed, 12 Jul 2017 01:45:12 +0900 Subject: [PATCH 72/73] =?UTF-8?q?=E6=B7=BB=E5=8A=A0=E6=AD=A3=E5=88=99?= =?UTF-8?q?=E8=A1=A8=E8=BE=BE=E5=BC=8F=E7=94=A8=E4=BE=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../2.code/jmr-02-parent/pom.xml | 15 + .../2.code/jmr-11-challenge/pom.xml | 8 + .../eulerlcs/jmr/challenge/camel/Hello1.java | 12 + .../eulerlcs/jmr/challenge/camel/Hello2.java | 13 + .../jmr/challenge/camel/HelloConv.java | 7 + .../jmr/challenge/camel/HelloProcessor1.java | 13 + .../jmr/challenge/camel/HelloProcessor2.java | 18 + .../jmr/challenge/camel/HelloRoute1.java | 11 + .../jmr/challenge/camel/HelloRoute2.java | 11 + .../jmr/challenge/camel/HelloRoute3.java | 11 + .../jmr/challenge/camel/HelloRoute4.java | 12 + .../jmr/challenge/camel/HelloRoute5.java | 12 + .../jmr/challenge/camel/HelloRoute6.java | 14 + .../regularexpression/ClassLoaderTree.java | 12 - .../ClassLoaderTreeTest.java | 119 ------- .../eulerlcs/regularexpression/UtilsTest.java | 316 ++++++++++++++++++ .../src/test/resources/01.txt | 2 + .../src/test/resources/{01_01.txt => 07.txt} | 0 18 files changed, 475 insertions(+), 131 deletions(-) create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java create mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01.txt rename students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/{01_01.txt => 07.txt} (100%) diff --git a/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml b/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml index 82b785a432..381200eaa0 100644 --- a/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml +++ b/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml @@ -18,6 +18,21 @@ + + org.apache.camel + camel-stream + 2.19.1 + + + org.apache.camel + camel-core + 2.19.1 + + + org.apache.activemq + activemq-core + 5.7.0 + org.apache.commons commons-lang3 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml index 589a5f69ee..3f106b77b5 100644 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml @@ -12,6 +12,14 @@ + + org.apache.camel + camel-stream + + + org.apache.camel + camel-core + commons-digester commons-digester diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java new file mode 100644 index 0000000000..2cbe755db2 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java @@ -0,0 +1,12 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.main.Main; + +public class Hello1 { + public static void main(String[] args) throws Exception { + System.out.println("hello camel"); + + Main main = new Main(); + main.start(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java new file mode 100644 index 0000000000..17ea05f2cb --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java @@ -0,0 +1,13 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.main.Main; + +public class Hello2 { + public static void main(String[] args) throws Exception { + System.out.println("hello camel"); + + Main main = new Main(); + main.addRouteBuilder(new HelloRoute6()); + main.run(); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java new file mode 100644 index 0000000000..9f7f9b1c1c --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java @@ -0,0 +1,7 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +public class HelloConv { + public String addHello(String data) { + return "MyHello " + data; + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java new file mode 100644 index 0000000000..5c5de3e899 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java @@ -0,0 +1,13 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.Exchange; +import org.apache.camel.Processor; + +public class HelloProcessor1 implements Processor { + @Override + public void process(Exchange exchange) throws Exception { + String body = exchange.getIn().getBody(String.class); + body = "Hello " + body; + exchange.getIn().setBody(body); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java new file mode 100644 index 0000000000..0009907c99 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java @@ -0,0 +1,18 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.Exchange; +import org.apache.camel.Processor; + +public class HelloProcessor2 implements Processor { + @Override + public void process(Exchange exchange) throws Exception { + String body = exchange.getIn().getBody(String.class); + + if ("".equals(body)) { + throw new Exception("empty value."); + } + + body = "Hello " + body; + exchange.getIn().setBody(body); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java new file mode 100644 index 0000000000..6a6c01f909 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java @@ -0,0 +1,11 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.builder.RouteBuilder; + +public class HelloRoute1 extends RouteBuilder { + + @Override + public void configure() throws Exception { + from("timer:test-hello").to("log:test-log"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java new file mode 100644 index 0000000000..a83e09d34f --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java @@ -0,0 +1,11 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.builder.RouteBuilder; + +public class HelloRoute2 extends RouteBuilder { + + @Override + public void configure() throws Exception { + from("stream:in?promptMessage=Enter : ").to("stream:out"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java new file mode 100644 index 0000000000..3e11a71181 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java @@ -0,0 +1,11 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.builder.RouteBuilder; + +public class HelloRoute3 extends RouteBuilder { + + @Override + public void configure() throws Exception { + from("stream:in?promptMessage=Enter : ").process(new HelloProcessor1()).to("stream:out"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java new file mode 100644 index 0000000000..315279b213 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java @@ -0,0 +1,12 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.builder.RouteBuilder; + +public class HelloRoute4 extends RouteBuilder { + + @Override + public void configure() throws Exception { + from("stream:in?promptMessage=Enter : ").process(new HelloProcessor1()) + .bean(HelloConv.class, "addHello(${body})").to("stream:out"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java new file mode 100644 index 0000000000..816304c82b --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java @@ -0,0 +1,12 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.builder.RouteBuilder; + +public class HelloRoute5 extends RouteBuilder { + + @Override + public void configure() throws Exception { + from("stream:in?promptMessage=Enter : ").routeId("HelloRoute20170705").process(new HelloProcessor2()) + .to("stream:out"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java new file mode 100644 index 0000000000..dae8d2887a --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java @@ -0,0 +1,14 @@ +package com.github.eulerlcs.jmr.challenge.camel; + +import org.apache.camel.builder.RouteBuilder; + +public class HelloRoute6 extends RouteBuilder { + + @Override + public void configure() throws Exception { + onException(Exception.class).handled(true).setBody().constant("なにかエラーが発生").to("stream:out"); + + from("stream:in?promptMessage=Enter : ").process(new HelloProcessor2()).process(new HelloProcessor2()) + .to("stream:out"); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java deleted file mode 100644 index 2ea7809504..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/ClassLoaderTree.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.github.eulerlcs.regularexpression; - -public class ClassLoaderTree { - - public static void main(String[] args) { - ClassLoader loader = ClassLoaderTree.class.getClassLoader(); - while (loader != null) { - System.out.println(loader.toString()); - loader = loader.getParent(); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java deleted file mode 100644 index 2e0b955bad..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/ClassLoaderTreeTest.java +++ /dev/null @@ -1,119 +0,0 @@ -package com.github.eulerlcs.regularexpression; - -import static org.junit.Assert.assertFalse; -import static org.junit.Assert.assertTrue; - -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -import org.junit.Test; - -public class ClassLoaderTreeTest { - - @Test - public void test01_01() { - String text = Utils.readAllFromResouce("01_01.txt"); - System.out.println("--orignal text start--"); - System.out.print(text); - System.out.println("--orignal text end --"); - - // 统一换行符 - String result = text.replaceAll("(\r\n)|\r", "\n"); - System.out.println("--统一换行符 start--"); - System.out.print(result); - System.out.println("--统一换行符 end --"); - - // 行单位前后trim - result = result.replaceAll("(?m)^\\s*(.*?)\\s*$", "$1"); - System.out.println("--行单位前后trim start--"); - System.out.print(result); - System.out.println("--行单位前后trim end --"); - - assertFalse(result.equals(text)); - } - - @Test - public void test01_02() { - - // ^ $ \A \E (?m) - String text = "123\r\nabc def"; - String regex = "\\Aabc"; - // Pattern p = Pattern.compile(regex); - Pattern p = Pattern.compile(regex, Pattern.MULTILINE); - - Matcher m = p.matcher(text); - - boolean result = m.find(); - if (result) { - System.out.println("found"); - } else { - System.out.println("not found"); - } - assertTrue(result); - } - - @Test - public void test01_03_dotall() { - Pattern p = null; - Matcher m = null; - - String text1 = "width height"; - String text2 = "width\nheight"; - // Pattern p = Pattern.compile("(?s)width.height"); - p = Pattern.compile("width.height", Pattern.DOTALL); - - m = p.matcher(text1); - boolean result1 = m.find(); - - m = p.matcher(text2); - boolean result2 = m.find(); - if (result2) { - System.out.println("found"); - } else { - System.out.println("not found"); - } - - assertTrue(result1); - assertTrue(result2); - } - - @Test - public void test01_04_Zz() { - Pattern p = null; - Matcher m = null; - boolean result1 = false; - boolean result2 = false; - boolean result3 = false; - - String text1 = "abc def"; - String text2 = "def abc"; - String text3 = "def abc\n"; - - p = Pattern.compile("abc\\z"); - - m = p.matcher(text1); - result1 = m.find(); - - m = p.matcher(text2); - result2 = m.find(); - - m = p.matcher(text3); - result3 = m.find(); - - p = Pattern.compile("abc\\Z"); - - m = p.matcher(text1); - result1 = m.find(); - - m = p.matcher(text2); - result2 = m.find(); - - m = p.matcher(text3); - result3 = m.find(); - - assertFalse(result1); - assertTrue(result2); - assertTrue(result3); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java new file mode 100644 index 0000000000..3fa9e25c8d --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java @@ -0,0 +1,316 @@ +package com.github.eulerlcs.regularexpression; + +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertTrue; + +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import org.junit.Test; + +// http://www.cnblogs.com/playing/archive/2011/03/15/1984943.html + +public class UtilsTest { + + /** + * 多行模式-1 + */ + @Test + public void test01_01() { + String t1 = Utils.readAllFromResouce("01.txt"); + + // 默认 单行模式 + Pattern p1 = Pattern.compile("^def$"); + Matcher m1 = p1.matcher(t1); + + if (m1.find()) { + System.out.println("found!"); + } else { + System.out.println("not found!"); + } + } + + /** + *

+	 * 多行模式-2 
+	 *  (?m)		Pattern.MULTILINE
+	 * 
+ */ + @Test + public void test01_02() { + String t1 = Utils.readAllFromResouce("01.txt"); + + // 多行模式 写法一 + // Pattern p1 = Pattern.compile("(?m)^def$"); + // 多行模式 写法二 + Pattern p1 = Pattern.compile("^def$", Pattern.MULTILINE); + + Matcher m1 = p1.matcher(t1); + + if (m1.find()) { + System.out.println("found!"); + } else { + System.out.println("not found!"); + } + } + + /** + * flag设定和(?X)的等价关系 + * + *
+	 *  (?m)		Pattern.MULTILINE
+	 *  (?i)		Pattern.CASE_INSENSITIVE
+	 *  (?u)		Pattern.UNICODE_CASE
+	 *  (?s)		Pattern.DOTALL
+	 *  (?d)		Pattern.UNIX_LINES
+	 *  (?x)		Pattern.COMMENTS
+	 * 
+ */ + + /** + *
+	 * ascii大小写
+	 *  (?i)		Pattern.CASE_INSENSITIVE
+	 * 
+ */ + @Test + public void test02_01() { + String t1 = "abc AbC aCd abc ABc 2343"; + String r1 = "abc"; + + // 默认 区分大小写 + // Pattern p1 = Pattern.compile(r1); + + // 忽略ascii大小,写法一 + Pattern p1 = Pattern.compile("(?i)abc"); + + // 忽略ascii大小,写法而 + // Pattern p1 = Pattern.compile(r1, Pattern.CASE_INSENSITIVE ); + + Matcher m1 = p1.matcher(t1); + + while (m1.find()) { + System.out.println(m1.group()); + } + } + + /** + *
+	 * unicode大小写
+	 *  (?u)		Pattern.UNICODE_CASE
+	 * 
+ */ + @Test + public void test03_01() { + String t1 = "abc AbC aCd abc ABc 2343"; + String r1 = "abc";// 日文输入法下,全角abc,也就是宽字体 + + // 默认 区分大小写只适用于ascii + // Pattern p1 = Pattern.compile((?i)abc); + + // 忽略ascii大小,写法一 + Pattern p1 = Pattern.compile("(?iu)abc"); + + // 忽略ascii大小,写法而 + // Pattern p1 = Pattern.compile(r1, Pattern.UNICODE_CASE); + + Matcher m1 = p1.matcher(t1); + + while (m1.find()) { + System.out.println(m1.group()); + } + } + + /** 通过设定标志位忽略大小写 */ + @Test + public void test03_02() { + String t1 = "abc AbC aCd\nABCD 2343"; + String r1 = "(?i)(?m)abc"; + Pattern p1 = Pattern.compile(r1); + Matcher m1 = p1.matcher(t1); + + while (m1.find()) { + System.out.println(m1.group()); + } + } + + @Test + public void test04_01_dotall() { + Pattern p = null; + Matcher m = null; + + String text1 = "width height"; + String text2 = "width\nheight"; + // Pattern p = Pattern.compile("(?s)width.height"); + p = Pattern.compile("width.height", Pattern.DOTALL); + + m = p.matcher(text1); + boolean result1 = m.find(); + if (result1) { + System.out.println("text1 found"); + } else { + System.out.println("text1 not found"); + } + + m = p.matcher(text2); + boolean result2 = m.find(); + if (result2) { + System.out.println("text2 found"); + } else { + System.out.println("text2 not found"); + } + } + + /** + * group + * + *
+	 * group(0):正则表达式的匹配值 
+	 * group(1):第一个子串
+	 * 
+ */ + @Test + public void test05_01() { + Pattern p = Pattern.compile("([a-z]+)-(\\d+)"); + Matcher m = p.matcher("type x-235, type y-3, type zw-465"); + + while (m.find()) { + for (int i = 0; i < m.groupCount() + 1; i++) { + System.out.println("group(" + i + ")=" + m.group(i)); + } + System.out.println("---------------------"); + } + } + + /** + * 字符串分割的例子 + */ + @Test + public void test05_02() { + String abc = "a///b/c"; + + // 分割后的数组中包含空字符 + String[] array1 = abc.split("/"); + for (String str : array1) { + System.out.println(str); + } + + System.out.println("---------------------"); + + // 分割后的数组中取出了空字符 + String[] array2 = abc.split("/+"); + for (String str : array2) { + System.out.println(str); + } + } + + /** + * 替换 + */ + @Test + public void test06_01() { + String str = "Orange is 100yuan, Banana is 180 yuan."; + String regex = "\\d+\\s*yuan"; + Pattern p = Pattern.compile(regex); + + Matcher m = p.matcher(str); + System.out.println(m.find()); + String result = m.replaceFirst("_$0_"); + + System.out.println(result); + } + + /** + * 替换 + */ + @Test + public void test06_02() { + String str = "Orange is 100yuan, Banana is 180 yuan."; + String regex = "(\\d)\\s*(yuan)"; + + Pattern p = Pattern.compile(regex); + Matcher m = p.matcher(str); + + String result = m.replaceAll("$2_$1"); + + System.out.println(result); + } + + /** + * 命名分组,替换 + */ + @Test + public void test06_03() { + String pathfFilename = "aa/notepad.exe"; + + String regex = "^.+/(?.+)$"; + String replacement = "${filename}"; + + String filename = pathfFilename.replaceFirst(regex, replacement); + System.out.println(filename); + } + + /** + * 从文本中读取多行数据后,建议先把回车符删掉 + */ + @Test + public void test07_01() { + String t1 = Utils.readAllFromResouce("07.txt"); + System.out.println("--orignal text start--"); + System.out.print(t1); + System.out.println("--orignal text end --"); + + // 统一换行符 + String ret1 = t1.replaceAll("(\r\n)|\r", "\n"); + System.out.println("--统一换行符 start--"); + System.out.print(ret1); + System.out.println("--统一换行符 end --"); + + // 行单位前后trim + String ret2 = ret1.replaceAll("(?m)^\\s*(.*?)\\s*$", "$1"); + System.out.println("--行单位前后trim start--"); + System.out.println(ret2); + System.out.println("--行单位前后trim end --"); + + assertFalse(ret2.equals(t1)); + } + + @Test + public void test01_04_Zz() { + Pattern p = null; + Matcher m = null; + boolean result1 = false; + boolean result2 = false; + boolean result3 = false; + + String text1 = "abc def"; + String text2 = "def abc"; + String text3 = "def abc\n"; + + p = Pattern.compile("abc\\z"); + + m = p.matcher(text1); + result1 = m.find(); + + m = p.matcher(text2); + result2 = m.find(); + + m = p.matcher(text3); + result3 = m.find(); + + p = Pattern.compile("abc\\Z"); + + m = p.matcher(text1); + result1 = m.find(); + + m = p.matcher(text2); + result2 = m.find(); + + m = p.matcher(text3); + result3 = m.find(); + + assertFalse(result1); + assertTrue(result2); + assertTrue(result3); + } +} diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01.txt b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01.txt new file mode 100644 index 0000000000..5f5521fae2 --- /dev/null +++ b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01.txt @@ -0,0 +1,2 @@ +abc +def diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01_01.txt b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/07.txt similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01_01.txt rename to students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/07.txt From 5c16127a38c12d79db8b84c1cbfad0477e88c322 Mon Sep 17 00:00:00 2001 From: eulerlcs Date: Wed, 12 Jul 2017 23:59:11 +0900 Subject: [PATCH 73/73] add regexp project --- students/41689722.eulerlcs/2.code/.gitignore | 6 - .../2.code/jmr-01-aggregator/pom.xml | 18 - .../2.code/jmr-02-parent/pom.xml | 163 ------- .../data/shoppingcart/shoppingcart.data | Bin 131 -> 0 bytes .../data/xmlparser/app-config.xml | 12 - .../jmr-11-challenge/data/xmlparser/hello.xml | 5 - .../2.code/jmr-11-challenge/pom.xml | 56 --- .../eulerlcs/jmr/challenge/camel/Hello1.java | 12 - .../eulerlcs/jmr/challenge/camel/Hello2.java | 13 - .../jmr/challenge/camel/HelloConv.java | 7 - .../jmr/challenge/camel/HelloProcessor1.java | 13 - .../jmr/challenge/camel/HelloProcessor2.java | 18 - .../jmr/challenge/camel/HelloRoute1.java | 11 - .../jmr/challenge/camel/HelloRoute2.java | 11 - .../jmr/challenge/camel/HelloRoute3.java | 11 - .../jmr/challenge/camel/HelloRoute4.java | 12 - .../jmr/challenge/camel/HelloRoute5.java | 12 - .../jmr/challenge/camel/HelloRoute6.java | 14 - .../core/FileSystemClassLoader.java | 58 --- .../classloader/core/ICalculator.java | 5 - .../classloader/core/NetworkClassLoader.java | 46 -- .../challenge/classloader/core/Versioned.java | 5 - .../classloader/driver/CalculatorTest.java | 24 - .../classloader/driver/ClassIdentity.java | 36 -- .../classloader/driver/ClassLoaderTree.java | 12 - .../challenge/classloader/package-info.java | 7 - .../sampleRename/CalculatorAdvanced.java | 15 - .../sampleRename/CalculatorBasic.java | 15 - .../classloader/sampleRename/Sample.java | 10 - .../challenge/systemrules/AppWithExit.java | 13 - .../challenge/systemrules/package-info.java | 5 - .../digester/core/HelloDigester.java | 17 - .../digester/core/HelloFileRulerSet.java | 28 -- .../xmlparser/digester/driver/Driver.java | 28 -- .../xmlparser/digester/entity/Hello.java | 19 - .../xmlparser/digester/entity/HelloFile.java | 11 - .../challenge/xmlparser/jaxb/AppConfig.java | 29 -- .../jmr/challenge/xmlparser/jaxb/Driver.java | 20 - .../jmr/challenge/xmlparser/jaxb/Hello.java | 22 - .../challenge/xmlparser/jaxb/HelloFile.java | 14 - .../challenge/xmlparser/jaxb/JaxbParser.java | 22 - .../jmr/challenge/xmlparser/package-info.java | 13 - .../jmr/challenge/xmlparser/sax/Driver.java | 19 - .../xmlparser/sax/HelloSaxParser.java | 42 -- .../challenge/zzz/master170219/Try170205.java | 132 ------ .../challenge/zzz/master170219/Try170212.java | 34 -- .../challenge/zzz/master170219/Try170219.java | 47 -- .../com/hoo/download/BatchDownloadFile.java | 227 --------- .../java/com/hoo/download/DownloadFile.java | 176 ------- .../java/com/hoo/download/SaveItemFile.java | 68 --- .../java/com/hoo/entity/DownloadInfo.java | 125 ----- .../main/java/com/hoo/util/DownloadUtils.java | 40 -- .../java/com/hoo/util/DownloadUtilsTest.java | 39 -- .../src/main/java/com/hoo/util/LogUtils.java | 40 -- .../src/main/resources/.gitkeep | 0 .../jmr-11-challenge/src/test/java/.gitkeep | 0 .../systemrules/AppWithExitTest.java | 51 -- .../src/test/resources/.gitkeep | 0 .../2.code/jmr-61-collection/pom.xml | 27 -- .../eulerlcs/jmr/algorithm/ArrayList.java | 438 ------------------ .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 - .../eulerlcs/jmr/algorithm/TestArrayList.java | 44 -- .../src/test/resources/.gitkeep | 0 .../2.code/jmr-62-litestruts/data/struts.xml | 11 - .../2.code/jmr-62-litestruts/pom.xml | 39 -- .../jmr-62-litestruts/src/main/java/.gitkeep | 0 .../eulerlcs/jmr/algorithm/ArrayUtil.java | 279 ----------- .../jmr/litestruts/action/LoginAction.java | 30 -- .../jmr/litestruts/action/LogoutAction.java | 30 -- .../eulerlcs/jmr/litestruts/core/Struts.java | 200 -------- .../eulerlcs/jmr/litestruts/core/View.java | 26 -- .../jmr/litestruts/degister/StrutsAction.java | 22 - .../degister/StrutsActionResult.java | 13 - .../degister/StrutsActionRulerSet.java | 30 -- .../jmr/litestruts/degister/StrutsConfig.java | 15 - .../litestruts/degister/StrutsDigester.java | 13 - .../src/main/resources/log4j.xml | 16 - .../jmr-62-litestruts/src/test/java/.gitkeep | 0 .../eulerlcs/jmr/algorithm/ArrayUtilTest.java | 266 ----------- .../jmr/litestruts/core/StrutsTest.java | 38 -- .../src/test/resources/.gitkeep | 0 .../2.code/jmr-63-download/data/.gitkeep | 0 .../2.code/jmr-63-download/pom.xml | 39 -- .../eulerlcs/jmr/algorithm/Iterator.java | 8 - .../eulerlcs/jmr/algorithm/LinkedList.java | 126 ----- .../github/eulerlcs/jmr/algorithm/List.java | 13 - .../eulerlcs/jmr/download/api/Connection.java | 28 -- .../jmr/download/api/ConnectionException.java | 5 - .../jmr/download/api/ConnectionManager.java | 11 - .../jmr/download/api/DownloadListener.java | 5 - .../jmr/download/core/DownloadThread.java | 20 - .../jmr/download/core/FileDownloader.java | 64 --- .../jmr/download/impl/ConnectionImpl.java | 25 - .../download/impl/ConnectionManagerImpl.java | 14 - .../src/main/resources/log4j.xml | 16 - .../jmr/download/core/FileDownloaderTest.java | 53 --- .../src/test/resources/.gitkeep | 0 .../2.code/jmr-64-minijvm/data/.gitkeep | 0 .../2.code/jmr-64-minijvm/pom.xml | 43 -- .../eulerlcs/jmr/algorithm/LRUPageFrame.java | 110 ----- .../github/eulerlcs/jmr/algorithm/Stack.java | 24 - .../eulerlcs/jmr/algorithm/StackUtil.java | 43 -- .../eulerlcs/jmr/jvm/attr/AttributeInfo.java | 19 - .../eulerlcs/jmr/jvm/attr/CodeAttr.java | 52 --- .../jmr/jvm/attr/LineNumberTable.java | 46 -- .../jmr/jvm/attr/LocalVariableItem.java | 49 -- .../jmr/jvm/attr/LocalVariableTable.java | 25 - .../eulerlcs/jmr/jvm/attr/StackMapTable.java | 29 -- .../eulerlcs/jmr/jvm/clz/AccessFlag.java | 26 -- .../eulerlcs/jmr/jvm/clz/ClassFile.java | 100 ---- .../eulerlcs/jmr/jvm/clz/ClassIndex.java | 22 - .../eulerlcs/jmr/jvm/constant/ClassInfo.java | 29 -- .../jmr/jvm/constant/ConstantInfo.java | 29 -- .../jmr/jvm/constant/ConstantPool.java | 28 -- .../jmr/jvm/constant/FieldRefInfo.java | 54 --- .../jmr/jvm/constant/MethodRefInfo.java | 56 --- .../jmr/jvm/constant/NameAndTypeInfo.java | 50 -- .../jmr/jvm/constant/NullConstantInfo.java | 11 - .../eulerlcs/jmr/jvm/constant/StringInfo.java | 28 -- .../eulerlcs/jmr/jvm/constant/UTF8Info.java | 37 -- .../github/eulerlcs/jmr/jvm/field/Field.java | 26 -- .../jmr/jvm/loader/ByteCodeIterator.java | 55 --- .../jmr/jvm/loader/ClassFileLoader.java | 74 --- .../jmr/jvm/loader/ClassFileParser.java | 146 ------ .../eulerlcs/jmr/jvm/method/Method.java | 48 -- .../github/eulerlcs/jmr/jvm/util/Util.java | 22 - .../src/main/resources/log4j.xml | 16 - .../jmr/algorithm/LRUPageFrameTest.java | 27 -- .../jmr/jvm/loader/ClassFileloaderTest.java | 220 --------- .../eulerlcs/jmr/jvm/loader/EmployeeV1.java | 28 -- .../src/test/resources/.gitkeep | 0 .../src/main/resources/.gitkeep | 0 .../src/main/resources/log4j.xml | 16 - .../src/test/java/.gitkeep | 0 .../src/test/resources/.gitkeep | 0 .../5.settingfile/eclipsev45.epf | 186 -------- .../5.settingfile/git cmd help.txt | 43 -- .../tool.161118.git-source-copy.bat | 37 -- .../tool.170330.java-maven-source-cleaner.bat | 37 -- .../pom.xml | 0 .../eulerlcs/regularexpression/Utils.java | 0 .../src/main/resources}/.gitkeep | 0 .../src/main/resources/log4j.xml | 0 .../src/test/java}/.gitkeep | 0 .../eulerlcs/regularexpression/UtilsTest.java | 0 .../src/test/resources}/.gitkeep | 0 .../src/test/resources/01.txt | 0 .../src/test/resources/07.txt | 0 149 files changed, 5779 deletions(-) delete mode 100644 students/41689722.eulerlcs/2.code/.gitignore delete mode 100644 students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/data/shoppingcart/shoppingcart.data delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/data/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-63-download/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/data/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java delete mode 100644 students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml delete mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/.gitkeep delete mode 100644 students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/.gitkeep delete mode 100644 students/41689722.eulerlcs/5.settingfile/eclipsev45.epf delete mode 100644 students/41689722.eulerlcs/5.settingfile/git cmd help.txt delete mode 100644 students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat delete mode 100644 students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat rename students/41689722.eulerlcs/{2.code/jmr-71-regularexpression => regularexpression}/pom.xml (100%) rename students/41689722.eulerlcs/{2.code/jmr-71-regularexpression => regularexpression}/src/main/java/com/github/eulerlcs/regularexpression/Utils.java (100%) rename students/41689722.eulerlcs/{1.article => regularexpression/src/main/resources}/.gitkeep (100%) rename students/41689722.eulerlcs/{2.code/jmr-11-challenge => regularexpression}/src/main/resources/log4j.xml (100%) rename students/41689722.eulerlcs/{2.code/jmr-01-aggregator/src/site => regularexpression/src/test/java}/.gitkeep (100%) rename students/41689722.eulerlcs/{2.code/jmr-71-regularexpression => regularexpression}/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java (100%) rename students/41689722.eulerlcs/{2.code/jmr-02-parent/src/site => regularexpression/src/test/resources}/.gitkeep (100%) rename students/41689722.eulerlcs/{2.code/jmr-71-regularexpression => regularexpression}/src/test/resources/01.txt (100%) rename students/41689722.eulerlcs/{2.code/jmr-71-regularexpression => regularexpression}/src/test/resources/07.txt (100%) diff --git a/students/41689722.eulerlcs/2.code/.gitignore b/students/41689722.eulerlcs/2.code/.gitignore deleted file mode 100644 index c2be49c379..0000000000 --- a/students/41689722.eulerlcs/2.code/.gitignore +++ /dev/null @@ -1,6 +0,0 @@ -.metadata/ -.recommenders/ -**/.settings/ -**/target/ -**/.classpath -**/.project diff --git a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml b/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml deleted file mode 100644 index 78a5afbac0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/pom.xml +++ /dev/null @@ -1,18 +0,0 @@ - - 4.0.0 - com.github.eulerlcs - jmr-01-aggregator - 0.0.1-SNAPSHOT - pom - eulerlcs master java road aggregator - - - ../jmr-02-parent - ../jmr-11-challenge - ../jmr-61-collection - ../jmr-62-litestruts - ../jmr-63-download - ../jmr-64-minijvm - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml b/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml deleted file mode 100644 index 381200eaa0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-02-parent/pom.xml +++ /dev/null @@ -1,163 +0,0 @@ - - 4.0.0 - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - pom - eulerlcs master java road parent - - - - 1.7.24 - 4.12 - 2.17 - 1.8 - 1.8 - - - - - - org.apache.camel - camel-stream - 2.19.1 - - - org.apache.camel - camel-core - 2.19.1 - - - org.apache.activemq - activemq-core - 5.7.0 - - - org.apache.commons - commons-lang3 - 3.5 - - - org.apache.commons - commons-io - 1.3.2 - - - com.github.eulerlcs - jmr-61-collection - ${project.version} - - - commons-digester - commons-digester - 2.1 - - - org.jdom - jdom2 - 2.0.6 - - - dom4j - dom4j - 1.6.1 - - - org.projectlombok - lombok - 1.16.14 - provided - - - org.slf4j - slf4j-api - ${slf4j.version} - - - org.slf4j - slf4j-log4j12 - ${slf4j.version} - - - junit - junit - ${junit.version} - test - - - com.github.stefanbirkner - system-rules - 1.16.1 - test - - - - - - - - - org.apache.maven.plugins - maven-source-plugin - 3.0.1 - - - attach-source - - jar-no-fork - - - - - - org.apache.maven.plugins - maven-compiler-plugin - 3.6.1 - - ${maven.compiler.source} - ${maven.compiler.target} - - - - org.apache.maven.plugins - maven-jar-plugin - 3.0.2 - - - org.apache.maven.plugins - maven-javadoc-plugin - 2.10.4 - - true - 1.8 - protected - UTF-8 - UTF-8 - UTF-8 - - - - org.apache.maven.plugins - maven-surefire-plugin - 2.19.1 - - - org.apache.maven.plugins - maven-surefire-report-plugin - 2.19.1 - - true - - - - - - - - org.apache.maven.plugins - maven-source-plugin - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/shoppingcart/shoppingcart.data b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/shoppingcart/shoppingcart.data deleted file mode 100644 index 336fd732b4dcf94a212cb3a8f2718aca7a10584b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 131 zcmZ=T{#&s4I+ra20|O5Ok5^(@qC$vnaYklQiG%X5hwke{s(~^b3>;t?-_mpkeYhwu zgRo0!cB+C`X?l82W?s62OMXsHu>=3>R=FL4Z-Cllq1pm6^Bjb~9_o+L_y!a;V&DTC O=ABxp;GB_|nFj!(-zjkb diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml deleted file mode 100644 index e989327e9d..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/app-config.xml +++ /dev/null @@ -1,12 +0,0 @@ - - - a - b - c - d - e - f - g - h - i - diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml deleted file mode 100644 index 748019e106..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/data/xmlparser/hello.xml +++ /dev/null @@ -1,5 +0,0 @@ - - - a.txt - b.txt - diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml b/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml deleted file mode 100644 index 3f106b77b5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/pom.xml +++ /dev/null @@ -1,56 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-11-challenge - eulerlcs master java road challenge - - - - - org.apache.camel - camel-stream - - - org.apache.camel - camel-core - - - commons-digester - commons-digester - - - org.jdom - jdom2 - - - dom4j - dom4j - - - org.projectlombok - lombok - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - com.github.stefanbirkner - system-rules - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java deleted file mode 100644 index 2cbe755db2..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello1.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.main.Main; - -public class Hello1 { - public static void main(String[] args) throws Exception { - System.out.println("hello camel"); - - Main main = new Main(); - main.start(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java deleted file mode 100644 index 17ea05f2cb..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/Hello2.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.main.Main; - -public class Hello2 { - public static void main(String[] args) throws Exception { - System.out.println("hello camel"); - - Main main = new Main(); - main.addRouteBuilder(new HelloRoute6()); - main.run(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java deleted file mode 100644 index 9f7f9b1c1c..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloConv.java +++ /dev/null @@ -1,7 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -public class HelloConv { - public String addHello(String data) { - return "MyHello " + data; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java deleted file mode 100644 index 5c5de3e899..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor1.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.Exchange; -import org.apache.camel.Processor; - -public class HelloProcessor1 implements Processor { - @Override - public void process(Exchange exchange) throws Exception { - String body = exchange.getIn().getBody(String.class); - body = "Hello " + body; - exchange.getIn().setBody(body); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java deleted file mode 100644 index 0009907c99..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloProcessor2.java +++ /dev/null @@ -1,18 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.Exchange; -import org.apache.camel.Processor; - -public class HelloProcessor2 implements Processor { - @Override - public void process(Exchange exchange) throws Exception { - String body = exchange.getIn().getBody(String.class); - - if ("".equals(body)) { - throw new Exception("empty value."); - } - - body = "Hello " + body; - exchange.getIn().setBody(body); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java deleted file mode 100644 index 6a6c01f909..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute1.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.builder.RouteBuilder; - -public class HelloRoute1 extends RouteBuilder { - - @Override - public void configure() throws Exception { - from("timer:test-hello").to("log:test-log"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java deleted file mode 100644 index a83e09d34f..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute2.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.builder.RouteBuilder; - -public class HelloRoute2 extends RouteBuilder { - - @Override - public void configure() throws Exception { - from("stream:in?promptMessage=Enter : ").to("stream:out"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java deleted file mode 100644 index 3e11a71181..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute3.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.builder.RouteBuilder; - -public class HelloRoute3 extends RouteBuilder { - - @Override - public void configure() throws Exception { - from("stream:in?promptMessage=Enter : ").process(new HelloProcessor1()).to("stream:out"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java deleted file mode 100644 index 315279b213..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute4.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.builder.RouteBuilder; - -public class HelloRoute4 extends RouteBuilder { - - @Override - public void configure() throws Exception { - from("stream:in?promptMessage=Enter : ").process(new HelloProcessor1()) - .bean(HelloConv.class, "addHello(${body})").to("stream:out"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java deleted file mode 100644 index 816304c82b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute5.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.builder.RouteBuilder; - -public class HelloRoute5 extends RouteBuilder { - - @Override - public void configure() throws Exception { - from("stream:in?promptMessage=Enter : ").routeId("HelloRoute20170705").process(new HelloProcessor2()) - .to("stream:out"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java deleted file mode 100644 index dae8d2887a..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/camel/HelloRoute6.java +++ /dev/null @@ -1,14 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.camel; - -import org.apache.camel.builder.RouteBuilder; - -public class HelloRoute6 extends RouteBuilder { - - @Override - public void configure() throws Exception { - onException(Exception.class).handled(true).setBody().constant("なにかエラーが発生").to("stream:out"); - - from("stream:in?promptMessage=Enter : ").process(new HelloProcessor2()).process(new HelloProcessor2()) - .to("stream:out"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java deleted file mode 100644 index 82c8b60d56..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/FileSystemClassLoader.java +++ /dev/null @@ -1,58 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.core; - -import java.io.ByteArrayOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; - -public class FileSystemClassLoader extends ClassLoader { - - private String rootDir; - - public FileSystemClassLoader(String rootDir) { - this.rootDir = rootDir; - } - - @Override - protected Class findClass(String name) throws ClassNotFoundException { - byte[] classData = getClassData(name); - if (classData == null) { - throw new ClassNotFoundException(); - } else { - return defineClass(name, classData, 0, classData.length); - } - } - - private byte[] getClassData(String className) { - String path = classNameToPath(className); - InputStream ins = null; - try { - ins = new FileInputStream(path); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - int bufferSize = 4096; - byte[] buffer = new byte[bufferSize]; - int bytesNumRead = 0; - while ((bytesNumRead = ins.read(buffer)) != -1) { - baos.write(buffer, 0, bytesNumRead); - } - return baos.toByteArray(); - } catch (IOException e) { - e.printStackTrace(); - } finally { - if (ins != null) { - try { - ins.close(); - } catch (IOException e) { - e.printStackTrace(); - } - } - } - - return null; - } - - private String classNameToPath(String className) { - return rootDir + File.separatorChar + className.replace('.', File.separatorChar) + ".class"; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java deleted file mode 100644 index 697bf8065f..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/ICalculator.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.core; - -public interface ICalculator extends Versioned { - String calculate(String expression); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java deleted file mode 100644 index c0f524a1b4..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/NetworkClassLoader.java +++ /dev/null @@ -1,46 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.core; - -import java.io.ByteArrayOutputStream; -import java.io.InputStream; -import java.net.URL; - -public class NetworkClassLoader extends ClassLoader { - - private String rootUrl; - - public NetworkClassLoader(String rootUrl) { - this.rootUrl = rootUrl; - } - - protected Class findClass(String name) throws ClassNotFoundException { - byte[] classData = getClassData(name); - if (classData == null) { - throw new ClassNotFoundException(); - } else { - return defineClass(name, classData, 0, classData.length); - } - } - - private byte[] getClassData(String className) { - String path = classNameToPath(className); - try { - URL url = new URL(path); - InputStream ins = url.openStream(); - ByteArrayOutputStream baos = new ByteArrayOutputStream(); - int bufferSize = 4096; - byte[] buffer = new byte[bufferSize]; - int bytesNumRead = 0; - while ((bytesNumRead = ins.read(buffer)) != -1) { - baos.write(buffer, 0, bytesNumRead); - } - return baos.toByteArray(); - } catch (Exception e) { - e.printStackTrace(); - } - return null; - } - - private String classNameToPath(String className) { - return rootUrl + "/" + className.replace('.', '/') + ".class"; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java deleted file mode 100644 index 34dfacbbd1..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/core/Versioned.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.core; - -public interface Versioned { - String getVersion(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java deleted file mode 100644 index d19ee1dbe0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/CalculatorTest.java +++ /dev/null @@ -1,24 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.driver; - -import com.github.eulerlcs.jmr.challenge.classloader.core.ICalculator; -import com.github.eulerlcs.jmr.challenge.classloader.core.NetworkClassLoader; - -public class CalculatorTest { - - public static void main(String[] args) { - String url = "http://localhost:8080/ClassloaderTest/classes"; - NetworkClassLoader ncl = new NetworkClassLoader(url); - String basicClassName = "com.example.CalculatorBasic"; - String advancedClassName = "com.example.CalculatorAdvanced"; - try { - Class clazz = ncl.loadClass(basicClassName); - ICalculator calculator = (ICalculator) clazz.newInstance(); - System.out.println(calculator.getVersion()); - clazz = ncl.loadClass(advancedClassName); - calculator = (ICalculator) clazz.newInstance(); - System.out.println(calculator.getVersion()); - } catch (Exception e) { - e.printStackTrace(); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java deleted file mode 100644 index 3a9226b8ca..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassIdentity.java +++ /dev/null @@ -1,36 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.driver; - -import java.io.File; -import java.lang.reflect.Method; - -import com.github.eulerlcs.jmr.challenge.classloader.core.FileSystemClassLoader; - -public class ClassIdentity { - - public static void main(String[] args) { - new ClassIdentity().testClassIdentity(); - } - - public void testClassIdentity() { - String userDir = System.getProperty("user.dir"); - String classDataRootPath = userDir + File.separator + "data" + File.separator + "classloader"; - - FileSystemClassLoader fscl1 = new FileSystemClassLoader(classDataRootPath); - FileSystemClassLoader fscl2 = new FileSystemClassLoader(classDataRootPath); - String className = "com.github.eulerlcs.jmr.challenge.classloader.sample.Sample"; - - try { - Class class1 = fscl1.loadClass(className); - Object obj1 = class1.newInstance(); - - Class class2 = fscl2.loadClass(className); - Object obj2 = class2.newInstance(); - - Method setSampleMethod = class1.getMethod("setSample", java.lang.Object.class); - - setSampleMethod.invoke(obj1, obj2); - } catch (Exception e) { - e.printStackTrace(); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java deleted file mode 100644 index 38916b6db5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/driver/ClassLoaderTree.java +++ /dev/null @@ -1,12 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.driver; - -public class ClassLoaderTree { - - public static void main(String[] args) { - ClassLoader loader = ClassLoaderTree.class.getClassLoader(); - while (loader != null) { - System.out.println(loader.toString()); - loader = loader.getParent(); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java deleted file mode 100644 index d35a4ee992..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/package-info.java +++ /dev/null @@ -1,7 +0,0 @@ -/** - * download from ibm developerworks - * - * @see
https://www.ibm.com/developerworks/cn/java/j-lo-classloader/ - */ -package com.github.eulerlcs.jmr.challenge.classloader; \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java deleted file mode 100644 index 9076a4f4c8..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorAdvanced.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.sampleRename; - -import com.github.eulerlcs.jmr.challenge.classloader.core.ICalculator; - -public class CalculatorAdvanced implements ICalculator { - - public String calculate(String expression) { - return "Result is " + expression; - } - - public String getVersion() { - return "2.0"; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java deleted file mode 100644 index d5f7b054dd..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/CalculatorBasic.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.sampleRename; - -import com.github.eulerlcs.jmr.challenge.classloader.core.ICalculator; - -public class CalculatorBasic implements ICalculator { - - public String calculate(String expression) { - return expression; - } - - public String getVersion() { - return "1.0"; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java deleted file mode 100644 index c67a7278e8..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/classloader/sampleRename/Sample.java +++ /dev/null @@ -1,10 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.classloader.sampleRename; - -public class Sample { - @SuppressWarnings("unused") - private Sample instance; - - public void setSample(Object instance) { - this.instance = (Sample) instance; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java deleted file mode 100644 index 2afd5b2074..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExit.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.systemrules; - -public class AppWithExit { - public static String message; - - public static void doSomethingAndExit() { - message = "exit ..."; - System.exit(1); - } - - public static void doNothing() { - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java deleted file mode 100644 index 1710e69d47..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/systemrules/package-info.java +++ /dev/null @@ -1,5 +0,0 @@ -/** - * copy from http://stefanbirkner.github.io/system-rules/index.html - */ - -package com.github.eulerlcs.jmr.challenge.systemrules; \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java deleted file mode 100644 index 3f58d74c7f..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloDigester.java +++ /dev/null @@ -1,17 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.digester.core; - -import org.apache.commons.digester.Digester; - -import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.Hello; - -public class HelloDigester { - public static Digester newInstance() { - Digester d = new Digester(); - - d.addObjectCreate("files", Hello.class); - d.addSetProperties("files"); - d.addRuleSet(new HelloFileRulerSet("files/")); - - return d; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java deleted file mode 100644 index 3d62c8c93e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/core/HelloFileRulerSet.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.digester.core; - -import org.apache.commons.digester.Digester; -import org.apache.commons.digester.RuleSetBase; - -import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.HelloFile; - -final class HelloFileRulerSet extends RuleSetBase { - protected String prefix = null; - - public HelloFileRulerSet() { - this(""); - } - - public HelloFileRulerSet(String prefix) { - super(); - this.namespaceURI = null; - this.prefix = prefix; - } - - @Override - public void addRuleInstances(Digester digester) { - digester.addObjectCreate(prefix + "file", HelloFile.class); - digester.addSetProperties(prefix + "file", "dir", "path"); - digester.addBeanPropertySetter(prefix + "file", "name"); - digester.addSetNext(prefix + "file", "addFile"); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java deleted file mode 100644 index 59a2987909..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/driver/Driver.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.digester.driver; - -import java.io.File; -import java.io.IOException; - -import org.apache.commons.digester.Digester; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.xml.sax.SAXException; - -import com.github.eulerlcs.jmr.challenge.xmlparser.digester.core.HelloDigester; -import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.Hello; - -public class Driver { - private final static Logger log = LoggerFactory.getLogger(Driver.class); - - public static void main(String[] args) { - Digester d = HelloDigester.newInstance(); - - try { - File file = new File("data//xmlparser", "hello.xml"); - Hello helloEntity = (Hello) d.parse(file); - log.debug("hello.value=[{}]", helloEntity.getValue()); - } catch (IOException | SAXException e) { - e.printStackTrace(); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java deleted file mode 100644 index 415dbef23a..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/Hello.java +++ /dev/null @@ -1,19 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity; - -import java.util.ArrayList; -import java.util.List; - -import lombok.Getter; -import lombok.Setter; - -@Getter -@Setter -public class Hello { - private String project; - private String value; - private List files = new ArrayList<>(); - - public void addFile(HelloFile file) { - files.add(file); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java deleted file mode 100644 index 2892a3058e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/digester/entity/HelloFile.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity; - -import lombok.Getter; -import lombok.Setter; - -@Getter -@Setter -public class HelloFile { - private String path; - private String name; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java deleted file mode 100644 index c50bce4a15..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/AppConfig.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; - -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; - -import lombok.Getter; - -@Getter -@XmlRootElement(name = "app-config") -public class AppConfig { - @XmlElement(name = "input-path") - private String inputPath; - @XmlElement(name = "input-look-subfolder") - private boolean inputLookSubfolder; - @XmlElement(name = "input-encode") - private String inputEncode; - @XmlElement(name = "output-path") - private String outputPath; - @XmlElement(name = "output-by-package-tree") - private boolean outputByPackageTree; - @XmlElement(name = "output-prefix") - private String outputPrefix; - @XmlElement(name = "output-subfix") - private String outputSubfix; - @XmlElement(name = "output-encode") - private String outputEncode; - @XmlElement(name = "output-package-name") - private String outputPackageName; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java deleted file mode 100644 index 15c5686e2e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Driver.java +++ /dev/null @@ -1,20 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; - -import java.io.File; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -public class Driver { - private final static Logger log = LoggerFactory.getLogger(Driver.class); - - public static void main(String[] args) { - File xml = new File("data//xmlparser", "hello.xml"); - Hello hello = JaxbParser.loadAppConfig(xml, Hello.class); - log.debug("hello.value=[{}]", hello.getValue()); - - xml = new File("data//xmlparser", "app-config.xml"); - AppConfig appConfig = JaxbParser.loadAppConfig(xml, AppConfig.class); - log.debug("process-args.InputPath=[{}] ", appConfig.getInputPath()); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java deleted file mode 100644 index 5bad90241e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/Hello.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; - -import java.util.List; - -import javax.xml.bind.annotation.XmlAttribute; -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; - -import com.github.eulerlcs.jmr.challenge.xmlparser.digester.entity.HelloFile; - -import lombok.Getter; - -@Getter -@XmlRootElement(name = "files") -public class Hello { - @XmlAttribute - private String project; - @XmlAttribute - private String value; - @XmlElement(name = "file") - private List files; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java deleted file mode 100644 index c5bdd127f1..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/HelloFile.java +++ /dev/null @@ -1,14 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; - -import javax.xml.bind.annotation.XmlAttribute; -import javax.xml.bind.annotation.XmlValue; - -import lombok.Getter; - -@Getter -public class HelloFile { - @XmlAttribute(name = "dir") - private String path; - @XmlValue - private String name; -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java deleted file mode 100644 index 720f524426..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/jaxb/JaxbParser.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.jaxb; - -import java.io.File; - -import javax.xml.bind.JAXBContext; -import javax.xml.bind.Unmarshaller; - -/* jaxb: Java Architecture for XML Binding */ -public class JaxbParser { - @SuppressWarnings("unchecked") - public static E loadAppConfig(File xml, Class clazz) { - E entity = null; - try { - JAXBContext jc = JAXBContext.newInstance(clazz); - Unmarshaller u = jc.createUnmarshaller(); - entity = (E) u.unmarshal(xml); - } catch (Exception e) { - e.printStackTrace(); - } - return entity; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java deleted file mode 100644 index 4f7a71c4bc..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/package-info.java +++ /dev/null @@ -1,13 +0,0 @@ -/** - * 各种xml库 - *
    - *
  • apache digester - *
  • dom - *
  • dom4j - *
  • ldom - *
  • jaxb - *
  • sax - *
- */ - -package com.github.eulerlcs.jmr.challenge.xmlparser; \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java deleted file mode 100644 index d15739c5c9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/Driver.java +++ /dev/null @@ -1,19 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.sax; - -import java.io.File; - -import javax.xml.parsers.SAXParser; -import javax.xml.parsers.SAXParserFactory; - -public class Driver { - public static void main(String[] args) { - SAXParserFactory factory = SAXParserFactory.newInstance(); - File xml = new File("data//xmlparser", "hello.xml"); - try { - SAXParser parser = factory.newSAXParser(); - parser.parse(xml, new HelloSaxParser()); - } catch (Exception e) { - e.printStackTrace(); - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java deleted file mode 100644 index 26cc926b11..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/xmlparser/sax/HelloSaxParser.java +++ /dev/null @@ -1,42 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.xmlparser.sax; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.xml.sax.Attributes; -import org.xml.sax.SAXException; -import org.xml.sax.helpers.DefaultHandler; - -/* sax: simple api for xml */ -public class HelloSaxParser extends DefaultHandler { - protected static Logger log = LoggerFactory.getLogger(HelloSaxParser.class); - - @Override - public void startDocument() throws SAXException { - super.startDocument(); - log.debug("sax startDocument"); - } - - @Override - public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { - super.startElement(uri, localName, qName, attributes); - log.debug("sax startElement qName: [{}]", qName); - } - - @Override - public void characters(char[] ch, int start, int length) throws SAXException { - super.characters(ch, start, length); - log.debug("sax characters: [{}]", new String(ch, start, length)); - } - - @Override - public void endElement(String uri, String localName, String qName) throws SAXException { - super.endElement(uri, localName, qName); - log.debug("sax endElement qName: [{}]", qName); - } - - @Override - public void endDocument() throws SAXException { - super.endDocument(); - log.debug("sax endDocument"); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java deleted file mode 100644 index b18db9d387..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170205.java +++ /dev/null @@ -1,132 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.zzz.master170219; - -import java.io.DataInputStream; -import java.io.FileInputStream; -import java.io.IOException; -import java.lang.reflect.Constructor; -import java.lang.reflect.Field; -import java.lang.reflect.Method; -import java.util.ArrayList; - -public class Try170205 { - public static void main(String[] args) throws Exception { - task94(); - task93(); - task84(); - task83(); - task65(); - task64(); - - ArrayList list = new ArrayList(); - show(list); - } - - public static void show(ArrayList list) { - // .... - } - - public static void task64() { - DataInputStream dis = null; - double price = 0; - int count = 0; - double sum = 0; - String disp = ""; - - try { - dis = new DataInputStream(new FileInputStream("data/shoppingcart.data")); - while (dis.available() > 0) { - price = dis.readDouble(); - count = dis.readInt(); - disp = dis.readUTF(); - System.out.println(disp); - sum += price * count; - } - - System.out.println("sum=" + sum); - } catch (IOException e) { - e.printStackTrace(); - } finally { - try { - dis.close(); - } catch (IOException e) { - e.printStackTrace(); - } - } - - } - - public static void task65() { - DataInputStream dis = null; - byte[] magic = { (byte) 0xca, (byte) 0xfe, (byte) 0xba, (byte) 0xbe }; - boolean ret = true; - - try { - dis = new DataInputStream(new FileInputStream("data/sc.class")); - for (int i = 0; i < 4; i++) { - if (magic[i] != dis.readByte()) { - ret = false; - break; - } - } - } catch (IOException e) { - e.printStackTrace(); - } finally { - try { - dis.close(); - } catch (IOException e) { - e.printStackTrace(); - } - } - - if (ret) { - System.out.println("it is cafebabe"); - } else { - System.out.println("it is not cafebabe"); - } - } - - public static void task83() throws Exception { - Class clazz = Class.forName("shoppingcart.Employee"); - Constructor ct = clazz.getConstructor(String.class, int.class); - Object obj = ct.newInstance("ref", 22); - - Method sayHello = clazz.getDeclaredMethod("sayHello"); - sayHello.invoke(obj); - - Method getID = clazz.getDeclaredMethod("getID"); - getID.setAccessible(true); - String ids = (String) getID.invoke(obj); - System.out.println("getID=" + ids); - - Field[] flds = clazz.getDeclaredFields(); - for (Field fld : flds) { - System.out.println(fld); - } - } - - public static void task84() throws Exception { - ArrayList list = new ArrayList<>(); - list.add(3232); - - Class clazz = ArrayList.class; - - Field elementDataField = clazz.getDeclaredField("elementData"); - elementDataField.setAccessible(true); - Object[] elementData = (Object[]) elementDataField.get(list); - if (elementData.length > 1) { - elementData[1] = "added by reflection"; - } - } - - public static void task93() { - ArrayList list1 = new ArrayList(); - ArrayList list2 = new ArrayList(); - System.out.println(list1.getClass().equals(list2.getClass())); - } - - public static void task94() { - ArrayList numbers = new ArrayList(); - numbers.add(new Integer(10)); - numbers.add(new Double(10.0d)); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java deleted file mode 100644 index 5492441572..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170212.java +++ /dev/null @@ -1,34 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.zzz.master170219; - -public class Try170212 { - - public static void main(String[] args) { - t28(); - } - - public static void changeStr(String str) { - str = "welcome"; - } - - public static void t28() { - String str = "1234"; - changeStr(str); - System.out.println(str); - } - - public static void t34() { - Try170212 x = new Try170212(); - Try170212.Hello obj = x.new Hello(""); - obj.msg += ",World!"; - System.out.println(obj.msg); - } - - class Hello { - public String msg = "Hello"; - - public Hello(String msg) { - this.msg = msg; - } - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java deleted file mode 100644 index 559dc44a7c..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/github/eulerlcs/jmr/challenge/zzz/master170219/Try170219.java +++ /dev/null @@ -1,47 +0,0 @@ -package com.github.eulerlcs.jmr.challenge.zzz.master170219; - -import java.util.ArrayList; -import java.util.Date; - -public class Try170219 { - public static void main(String[] args) { - Integer[] a = new Integer[10]; - case003(a); - } - - public static void case001() { - Fruit f = new Apple(); - f.setDate(new Date()); - } - - public static void case002() { - ArrayList list1 = new ArrayList(); - ArrayList list2 = new ArrayList(); - System.out.println(list1.getClass().equals(list2.getClass())); - } - - public static void case003(Number[] n) { - // nop - } - -} - -class Fruit { - public void setDate(Object d) { - System.out.println("Fruit.setDate(Object d)"); - } - - // public void setDate2(Object d) { - // System.out.println("Fruit.setDate(Object d)"); - // } -} - -class Apple extends Fruit { - public void setDate(Date d) { - System.out.println("Apple.setDate(Date d)"); - } - - public void setDate2(Date d) { - System.out.println("Apple.setDate(Date d)"); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java deleted file mode 100644 index 48b4f67670..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/BatchDownloadFile.java +++ /dev/null @@ -1,227 +0,0 @@ -package com.hoo.download; - -import java.io.DataInputStream; -import java.io.DataOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileOutputStream; -import java.io.IOException; -import java.net.HttpURLConnection; -import java.net.MalformedURLException; -import java.net.URL; - -import com.hoo.entity.DownloadInfo; -import com.hoo.util.LogUtils; - -/** - * function: 分批量下载文件 - * - * @author hoojo - * @createDate 2011-9-22 下午05:51:54 - * @file BatchDownloadFile.java - * @package com.hoo.download - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public class BatchDownloadFile implements Runnable { - // 下载文件信息 - private DownloadInfo downloadInfo; - // 一组开始下载位置 - private long[] startPos; - // 一组结束下载位置 - private long[] endPos; - // 休眠时间 - private static final int SLEEP_SECONDS = 500; - // 子线程下载 - private DownloadFile[] fileItem; - // 文件长度 - private int length; - // 是否第一个文件 - private boolean first = true; - // 是否停止下载 - private boolean stop = false; - // 临时文件信息 - private File tempFile; - - public BatchDownloadFile(DownloadInfo downloadInfo) { - this.downloadInfo = downloadInfo; - String tempPath = this.downloadInfo.getFilePath() + File.separator + downloadInfo.getFileName() + ".position"; - tempFile = new File(tempPath); - // 如果存在读入点位置的文件 - if (tempFile.exists()) { - first = false; - // 就直接读取内容 - try { - readPosInfo(); - } catch (IOException e) { - e.printStackTrace(); - } - } else { - // 数组的长度就要分成多少段的数量 - startPos = new long[downloadInfo.getSplitter()]; - endPos = new long[downloadInfo.getSplitter()]; - } - } - - @Override - public void run() { - // 首次下载,获取下载文件长度 - if (first) { - length = this.getFileSize();// 获取文件长度 - if (length == -1) { - LogUtils.log("file length is know!"); - stop = true; - } else if (length == -2) { - LogUtils.log("read file length is error!"); - stop = true; - } else if (length > 0) { - /** - * eg start: 1, 3, 5, 7, 9 end: 3, 5, 7, 9, length - */ - for (int i = 0, len = startPos.length; i < len; i++) { - int size = i * (length / len); - startPos[i] = size; - - // 设置最后一个结束点的位置 - if (i == len - 1) { - endPos[i] = length; - } else { - size = (i + 1) * (length / len); - endPos[i] = size; - } - LogUtils.log("start-end Position[" + i + "]: " + startPos[i] + "-" + endPos[i]); - } - } else { - LogUtils.log("get file length is error, download is stop!"); - stop = true; - } - } - - // 子线程开始下载 - if (!stop) { - // 创建单线程下载对象数组 - fileItem = new DownloadFile[startPos.length];// startPos.length = - // downloadInfo.getSplitter() - for (int i = 0; i < startPos.length; i++) { - try { - // 创建指定个数单线程下载对象,每个线程独立完成指定块内容的下载 - fileItem[i] = new DownloadFile(downloadInfo.getUrl(), - this.downloadInfo.getFilePath() + File.separator + downloadInfo.getFileName(), startPos[i], - endPos[i], i); - fileItem[i].start();// 启动线程,开始下载 - LogUtils.log("Thread: " + i + ", startPos: " + startPos[i] + ", endPos: " + endPos[i]); - } catch (IOException e) { - e.printStackTrace(); - } - } - - // 循环写入下载文件长度信息 - while (!stop) { - try { - writePosInfo(); - LogUtils.log("downloading……"); - Thread.sleep(SLEEP_SECONDS); - stop = true; - } catch (IOException e) { - e.printStackTrace(); - } catch (InterruptedException e) { - e.printStackTrace(); - } - for (int i = 0; i < startPos.length; i++) { - if (!fileItem[i].isDownloadOver()) { - stop = false; - break; - } - } - } - LogUtils.info("Download task is finished!"); - } - } - - /** - * 将写入点数据保存在临时文件中 - * - * @author hoojo - * @createDate 2011-9-23 下午05:25:37 - * @throws IOException - */ - private void writePosInfo() throws IOException { - DataOutputStream dos = new DataOutputStream(new FileOutputStream(tempFile)); - dos.writeInt(startPos.length); - for (int i = 0; i < startPos.length; i++) { - dos.writeLong(fileItem[i].getStartPos()); - dos.writeLong(fileItem[i].getEndPos()); - // LogUtils.info("[" + fileItem[i].getStartPos() + "#" + - // fileItem[i].getEndPos() + "]"); - } - dos.close(); - } - - /** - * function:读取写入点的位置信息 - * - * @author hoojo - * @createDate 2011-9-23 下午05:30:29 - * @throws IOException - */ - private void readPosInfo() throws IOException { - DataInputStream dis = new DataInputStream(new FileInputStream(tempFile)); - int startPosLength = dis.readInt(); - startPos = new long[startPosLength]; - endPos = new long[startPosLength]; - for (int i = 0; i < startPosLength; i++) { - startPos[i] = dis.readLong(); - endPos[i] = dis.readLong(); - } - dis.close(); - } - - /** - * function: 获取下载文件的长度 - * - * @author hoojo - * @createDate 2011-9-26 下午12:15:08 - * @return - */ - private int getFileSize() { - int fileLength = -1; - try { - URL url = new URL(this.downloadInfo.getUrl()); - HttpURLConnection conn = (HttpURLConnection) url.openConnection(); - - DownloadFile.setHeader(conn); - - int stateCode = conn.getResponseCode(); - // 判断http status是否为HTTP/1.1 206 Partial Content或者200 OK - if (stateCode != HttpURLConnection.HTTP_OK && stateCode != HttpURLConnection.HTTP_PARTIAL) { - LogUtils.log("Error Code: " + stateCode); - return -2; - } else if (stateCode >= 400) { - LogUtils.log("Error Code: " + stateCode); - return -2; - } else { - // 获取长度 - fileLength = conn.getContentLength(); - LogUtils.log("FileLength: " + fileLength); - } - - // 读取文件长度 - /* - * for (int i = 1; ; i++) { String header = - * conn.getHeaderFieldKey(i); if (header != null) { if - * ("Content-Length".equals(header)) { fileLength = - * Integer.parseInt(conn.getHeaderField(i)); break; } } else { - * break; } } - */ - - DownloadFile.printHeader(conn); - } catch (MalformedURLException e) { - e.printStackTrace(); - } catch (IOException e) { - e.printStackTrace(); - } - return fileLength; - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java deleted file mode 100644 index 784efa1d88..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/DownloadFile.java +++ /dev/null @@ -1,176 +0,0 @@ -package com.hoo.download; - -import java.io.IOException; -import java.io.InputStream; -import java.net.HttpURLConnection; -import java.net.MalformedURLException; -import java.net.URL; -import java.net.URLConnection; - -import com.hoo.util.LogUtils; - -/** - * function: 单线程下载文件 - * - * @author hoojo - * @createDate 2011-9-22 下午02:55:10 - * @file DownloadFile.java - * @package com.hoo.download - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public class DownloadFile extends Thread { - - // 下载文件url - private String url; - // 下载文件起始位置 - private long startPos; - // 下载文件结束位置 - private long endPos; - // 线程id - private int threadId; - - // 下载是否完成 - private boolean isDownloadOver = false; - - private SaveItemFile itemFile; - - private static final int BUFF_LENGTH = 1024 * 8; - - /** - * @param url - * 下载文件url - * @param name - * 文件名称 - * @param startPos - * 下载文件起点 - * @param endPos - * 下载文件结束点 - * @param threadId - * 线程id - * @throws IOException - */ - public DownloadFile(String url, String name, long startPos, long endPos, int threadId) throws IOException { - super(); - this.url = url; - this.startPos = startPos; - this.endPos = endPos; - this.threadId = threadId; - // 分块下载写入文件内容 - this.itemFile = new SaveItemFile(name, startPos); - } - - @Override - public void run() { - while (endPos > startPos && !isDownloadOver) { - try { - URL url = new URL(this.url); - HttpURLConnection conn = (HttpURLConnection) url.openConnection(); - - // 设置连接超时时间为10000ms - conn.setConnectTimeout(10000); - // 设置读取数据超时时间为10000ms - conn.setReadTimeout(10000); - - setHeader(conn); - - String property = "bytes=" + startPos + "-"; - conn.setRequestProperty("RANGE", property); - - // 输出log信息 - LogUtils.log("开始 " + threadId + ":" + property + endPos); - // printHeader(conn); - - // 获取文件输入流,读取文件内容 - InputStream is = conn.getInputStream(); - - byte[] buff = new byte[BUFF_LENGTH]; - int length = -1; - LogUtils.log("#start#Thread: " + threadId + ", startPos: " + startPos + ", endPos: " + endPos); - while ((length = is.read(buff)) > 0 && startPos < endPos && !isDownloadOver) { - // 写入文件内容,返回最后写入的长度 - startPos += itemFile.write(buff, 0, length); - } - LogUtils.log("#over#Thread: " + threadId + ", startPos: " + startPos + ", endPos: " + endPos); - LogUtils.log("Thread " + threadId + " is execute over!"); - this.isDownloadOver = true; - } catch (MalformedURLException e) { - e.printStackTrace(); - } catch (IOException e) { - e.printStackTrace(); - } finally { - try { - if (itemFile != null) { - itemFile.close(); - } - } catch (IOException e) { - e.printStackTrace(); - } - } - } - if (endPos < startPos && !isDownloadOver) { - LogUtils.log("Thread " + threadId + " startPos > endPos, not need download file !"); - this.isDownloadOver = true; - } - if (endPos == startPos && !isDownloadOver) { - LogUtils.log("Thread " + threadId + " startPos = endPos, not need download file !"); - this.isDownloadOver = true; - } - } - - /** - * function: 打印下载文件头部信息 - * - * @author hoojo - * @createDate 2011-9-22 下午05:44:35 - * @param conn - * HttpURLConnection - */ - public static void printHeader(URLConnection conn) { - int i = 1; - while (true) { - String header = conn.getHeaderFieldKey(i); - i++; - if (header != null) { - LogUtils.info(header + ":" + conn.getHeaderField(i)); - } else { - break; - } - } - } - - /** - * function: 设置URLConnection的头部信息,伪装请求信息 - * - * @author hoojo - * @createDate 2011-9-28 下午05:29:43 - * @param con - */ - public static void setHeader(URLConnection conn) { - conn.setRequestProperty("User-Agent", - "Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.0.3) Gecko/2008092510 Ubuntu/8.04 (hardy) Firefox/3.0.3"); - conn.setRequestProperty("Accept-Language", "en-us,en;q=0.7,zh-cn;q=0.3"); - conn.setRequestProperty("Accept-Encoding", "utf-8"); - conn.setRequestProperty("Accept-Charset", "ISO-8859-1,utf-8;q=0.7,*;q=0.7"); - conn.setRequestProperty("Keep-Alive", "300"); - conn.setRequestProperty("connnection", "keep-alive"); - conn.setRequestProperty("If-Modified-Since", "Fri, 02 Jan 2009 17:00:05 GMT"); - conn.setRequestProperty("If-None-Match", "\"1261d8-4290-df64d224\""); - conn.setRequestProperty("Cache-conntrol", "max-age=0"); - conn.setRequestProperty("Referer", "https://www.github.com"); - } - - public boolean isDownloadOver() { - return isDownloadOver; - } - - public long getStartPos() { - return startPos; - } - - public long getEndPos() { - return endPos; - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java deleted file mode 100644 index c0dcb62ac3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/download/SaveItemFile.java +++ /dev/null @@ -1,68 +0,0 @@ -package com.hoo.download; - -import java.io.IOException; -import java.io.RandomAccessFile; - -/** - * function: 写入文件、保存文件 - * - * @author hoojo - * @createDate 2011-9-21 下午05:44:02 - * @file SaveItemFile.java - * @package com.hoo.download - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public class SaveItemFile { - // 存储文件 - private RandomAccessFile itemFile; - - public SaveItemFile() throws IOException { - this("", 0); - } - - /** - * @param name - * 文件路径、名称 - * @param pos - * 写入点位置 position - * @throws IOException - */ - public SaveItemFile(String name, long pos) throws IOException { - itemFile = new RandomAccessFile(name, "rw"); - // 在指定的pos位置开始写入数据 - itemFile.seek(pos); - } - - /** - * function: 同步方法写入文件 - * - * @author hoojo - * @createDate 2011-9-26 下午12:21:22 - * @param buff - * 缓冲数组 - * @param start - * 起始位置 - * @param length - * 长度 - * @return - */ - public synchronized int write(byte[] buff, int start, int length) { - int i = -1; - try { - itemFile.write(buff, start, length); - i = length; - } catch (IOException e) { - e.printStackTrace(); - } - return i; - } - - public void close() throws IOException { - if (itemFile != null) { - itemFile.close(); - } - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java deleted file mode 100644 index 7ef4ba5477..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/entity/DownloadInfo.java +++ /dev/null @@ -1,125 +0,0 @@ - -package com.hoo.entity; - -/** - * function: 下载文件信息类 - * - * @author hoojo - * @createDate 2011-9-21 下午05:14:58 - * @file DownloadInfo.java - * @package com.hoo.entity - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public class DownloadInfo { - // 下载文件url - private String url; - // 下载文件名称 - private String fileName; - // 下载文件路径 - private String filePath; - // 分成多少段下载, 每一段用一个线程完成下载 - private int splitter; - - // 下载文件默认保存路径 - private final static String FILE_PATH = "C:/temp"; - // 默认分块数、线程数 - private final static int SPLITTER_NUM = 5; - - public DownloadInfo() { - super(); - } - - /** - * @param url - * 下载地址 - */ - public DownloadInfo(String url) { - this(url, null, null, SPLITTER_NUM); - } - - /** - * @param url - * 下载地址url - * @param splitter - * 分成多少段或是多少个线程下载 - */ - public DownloadInfo(String url, int splitter) { - this(url, null, null, splitter); - } - - /*** - * @param url - * 下载地址 - * @param fileName - * 文件名称 - * @param filePath - * 文件保存路径 - * @param splitter - * 分成多少段或是多少个线程下载 - */ - public DownloadInfo(String url, String fileName, String filePath, int splitter) { - super(); - if (url == null || "".equals(url)) { - throw new RuntimeException("url is not null!"); - } - this.url = url; - this.fileName = (fileName == null || "".equals(fileName)) ? getFileName(url) : fileName; - this.filePath = (filePath == null || "".equals(filePath)) ? FILE_PATH : filePath; - this.splitter = (splitter < 1) ? SPLITTER_NUM : splitter; - } - - /** - * function: 通过url获得文件名称 - * - * @author hoojo - * @createDate 2011-9-30 下午05:00:00 - * @param url - * @return - */ - private String getFileName(String url) { - return url.substring(url.lastIndexOf("/") + 1, url.length()); - } - - public String getUrl() { - return url; - } - - public void setUrl(String url) { - if (url == null || "".equals(url)) { - throw new RuntimeException("url is not null!"); - } - this.url = url; - } - - public String getFileName() { - return fileName; - } - - public void setFileName(String fileName) { - this.fileName = (fileName == null || "".equals(fileName)) ? getFileName(url) : fileName; - } - - public String getFilePath() { - return filePath; - } - - public void setFilePath(String filePath) { - this.filePath = (filePath == null || "".equals(filePath)) ? FILE_PATH : filePath; - } - - public int getSplitter() { - return splitter; - } - - public void setSplitter(int splitter) { - this.splitter = (splitter < 1) ? SPLITTER_NUM : splitter; - } - - @Override - public String toString() { - return this.url + "#" + this.fileName + "#" + this.filePath + "#" + this.splitter; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java deleted file mode 100644 index 3ca0384319..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtils.java +++ /dev/null @@ -1,40 +0,0 @@ -package com.hoo.util; - -import com.hoo.download.BatchDownloadFile; -import com.hoo.entity.DownloadInfo; - -/** - * function: 分块多线程下载工具类 - * - * @author hoojo - * @createDate 2011-9-28 下午05:22:18 - * @file DownloadUtils.java - * @package com.hoo.util - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public abstract class DownloadUtils { - - public static void download(String url) { - DownloadInfo bean = new DownloadInfo(url); - LogUtils.info(bean); - BatchDownloadFile down = new BatchDownloadFile(bean); - new Thread(down).start(); - } - - public static void download(String url, int threadNum) { - DownloadInfo bean = new DownloadInfo(url, threadNum); - LogUtils.info(bean); - BatchDownloadFile down = new BatchDownloadFile(bean); - new Thread(down).start(); - } - - public static void download(String url, String fileName, String filePath, int threadNum) { - DownloadInfo bean = new DownloadInfo(url, fileName, filePath, threadNum); - LogUtils.info(bean); - BatchDownloadFile down = new BatchDownloadFile(bean); - new Thread(down).start(); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java deleted file mode 100644 index 562a0ec047..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/DownloadUtilsTest.java +++ /dev/null @@ -1,39 +0,0 @@ -/** - * copy from http://blog.csdn.net/ibm_hoojo/article/details/6838222 - */ -package com.hoo.util; - -/** - * function: 下载测试 - * - * @author hoojo - * @createDate 2011-9-23 下午05:49:46 - * @file TestDownloadMain.java - * @package com.hoo.download - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public class DownloadUtilsTest { - public static void main(String[] args) { - /* - * DownloadInfo bean = new DownloadInfo( - * "http://i7.meishichina.com/Health/UploadFiles/201109/2011092116224363.jpg" - * ); System.out.println(bean); BatchDownloadFile down = new - * BatchDownloadFile(bean); new Thread(down).start(); - */ - - // DownloadUtils.download("http://i7.meishichina.com/Health/UploadFiles/201109/2011092116224363.jpg"); - DownloadUtils.download("https://github.com/dracome/coding2017/archive/master.zip", 5); - - try { - Thread.sleep(30 * 1000); - } catch (InterruptedException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } - int i = 3; - System.out.println(i); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java deleted file mode 100644 index 62d48bd0f9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/java/com/hoo/util/LogUtils.java +++ /dev/null @@ -1,40 +0,0 @@ -package com.hoo.util; - -/** - * function: 日志工具类 - * - * @author hoojo - * @createDate 2011-9-21 下午05:21:27 - * @file LogUtils.java - * @package com.hoo.util - * @project MultiThreadDownLoad - * @blog http://blog.csdn.net/IBM_hoojo - * @email hoojo_@126.com - * @version 1.0 - */ -public abstract class LogUtils { - - public static void log(Object message) { - System.err.println(message); - } - - public static void log(String message) { - System.err.println(message); - } - - public static void log(int message) { - System.err.println(message); - } - - public static void info(Object message) { - System.out.println(message); - } - - public static void info(String message) { - System.out.println(message); - } - - public static void info(int message) { - System.out.println(message); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java deleted file mode 100644 index c849302200..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/java/com/github/eulerlcs/jmr/challenge/systemrules/AppWithExitTest.java +++ /dev/null @@ -1,51 +0,0 @@ -/* copy from http://stefanbirkner.github.io/system-rules/index.html */ - -package com.github.eulerlcs.jmr.challenge.systemrules; - -import static org.junit.Assert.assertEquals; - -import org.junit.Rule; -import org.junit.Test; -import org.junit.contrib.java.lang.system.Assertion; -import org.junit.contrib.java.lang.system.ExpectedSystemExit; - -public class AppWithExitTest { - @Rule - public final ExpectedSystemExit exit = ExpectedSystemExit.none(); - - @Test - public void exits() { - exit.expectSystemExit(); - AppWithExit.doSomethingAndExit(); - } - - @Test - public void exitsWithStatusCode1() { - exit.expectSystemExitWithStatus(1); - AppWithExit.doSomethingAndExit(); - } - - @Test - public void writesMessage() { - exit.expectSystemExitWithStatus(1); - exit.checkAssertionAfterwards(new Assertion() { - @Override - public void checkAssertion() { - assertEquals("exit ...", AppWithExit.message); - } - }); - AppWithExit.doSomethingAndExit(); - } - - @Test - public void systemExitWithStatusCode1() { - exit.expectSystemExitWithStatus(1); - AppWithExit.doSomethingAndExit(); - } - - @Test - public void noSystemExit() { - AppWithExit.doNothing(); - // passes - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml b/students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml deleted file mode 100644 index 1da435d5b6..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-61-collection/pom.xml +++ /dev/null @@ -1,27 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-61-collection - eulerlcs master java road collection - - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java deleted file mode 100644 index 555f5ea954..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayList.java +++ /dev/null @@ -1,438 +0,0 @@ -/** - * 90% or more copy from jdk - */ -package com.github.eulerlcs.jmr.algorithm; - -import java.util.Arrays; -import java.util.Collection; -import java.util.ConcurrentModificationException; -import java.util.Iterator; -import java.util.List; -import java.util.ListIterator; -import java.util.NoSuchElementException; -import java.util.Objects; -import java.util.RandomAccess; -import java.util.function.Consumer; - -public class ArrayList implements List, RandomAccess { - private static final int MAX_ARRAY_SIZE = 1 << 10; - private transient Object[] elementData = new Object[0]; - private int size; - private transient int modCount = 0; - - @Override - public int size() { - return size; - } - - @Override - public boolean isEmpty() { - return size == 0; - } - - @Override - public boolean contains(Object o) { - if (o == null) { - for (Object obi : elementData) { - if (obi == null) { - return true; - } - } - } else { - for (Object obj : elementData) { - if (o.equals(obj)) { - return true; - } - } - } - return false; - } - - @Override - public boolean containsAll(Collection c) { - for (Object e : c) - if (!contains(e)) - return false; - return true; - } - - @Override - public Object[] toArray() { - return Arrays.copyOf(elementData, size, elementData.getClass()); - } - - @SuppressWarnings("unchecked") - @Override - public T[] toArray(T[] a) { - if (a.length < size) { - return (T[]) Arrays.copyOf(elementData, size, a.getClass()); - } else { - System.arraycopy(elementData, 0, a, 0, size); - if (a.length > size) - a[size] = null; - return a; - } - } - - @Override - public boolean add(E e) { - ensureExplicitCapacity(size + 1); // Increments modCount!! - elementData[size] = e; - size++; - return true; - } - - @Override - public void add(int index, E element) { - if (index >= size) - throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); - ensureExplicitCapacity(size + 1); // Increments modCount!! - System.arraycopy(elementData, index, elementData, index + 1, size - index); - elementData[index] = element; - size++; - } - - @Override - public E remove(int index) { - if (index >= size) - throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); - - modCount++; - @SuppressWarnings("unchecked") - E oldValue = (E) elementData[index]; - int numMoved = size - index - 1; - if (numMoved > 0) - System.arraycopy(elementData, index + 1, elementData, index, numMoved); - elementData[--size] = null;// clear to let GC do its work - - return oldValue; - } - - @Override - public boolean remove(Object o) { - int index = -1; - - if (o == null) { - for (int i = 0; i < size; i++) - if (elementData[i] == null) { - index = i; - break; - } - } else { - for (int i = 0; i < size; i++) - if (o.equals(elementData[i])) { - index = i; - break; - } - } - - if (index > 0) { - modCount++; - int numMoved = size - index - 1; - if (numMoved > 0) - System.arraycopy(elementData, index + 1, elementData, index, numMoved); - elementData[--size] = null;// clear to let GC do its work - - return true; - } - - return false; - } - - @Override - public boolean removeAll(Collection c) { - boolean modified = false; - for (Object obj : c) { - modified |= remove(obj); - } - - return modified; - } - - @Override - public boolean addAll(Collection c) { - Object[] a = c.toArray(); - int numNew = a.length; - ensureExplicitCapacity(size + numNew);// Increments modCount - System.arraycopy(a, 0, elementData, size, numNew); - size += numNew; - return numNew != 0; - } - - @Override - public boolean addAll(int index, Collection c) { - if (index >= size) - throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); - - Object[] a = c.toArray(); - int numNew = a.length; - ensureExplicitCapacity(size + numNew);// Increments modCount - - int numMoved = size - index; - if (numMoved > 0) - System.arraycopy(elementData, index, elementData, index + numNew, numMoved); - - System.arraycopy(a, 0, elementData, index, numNew); - size += numNew; - return numNew != 0; - } - - @Override - public boolean retainAll(Collection c) { - final Object[] elementData = this.elementData; - int r = 0, w = 0; - boolean modified = false; - for (; r < size; r++) - if (c.contains(elementData[r])) - elementData[w++] = elementData[r]; - - if (w != size) { - // clear to let GC do its work - for (int i = w; i < size; i++) - elementData[i] = null; - modCount += size - w; - size = w; - modified = true; - } - - return modified; - } - - @Override - public void clear() { - modCount++; - for (int i = 0; i < size; i++) - elementData[i] = null; - - size = 0; - } - - @Override - public List subList(int fromIndex, int toIndex) { - throw new UnsupportedOperationException(); - } - - @SuppressWarnings("unchecked") - @Override - public E get(int index) { - if (index >= size) - throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); - - return (E) elementData[index]; - } - - @SuppressWarnings("unchecked") - @Override - public E set(int index, E element) { - if (index >= size) - throw new IndexOutOfBoundsException("Index: " + index + ", Size:" + size); - - E oldValue = (E) elementData[index]; - elementData[index] = element; - return oldValue; - } - - @Override - public int indexOf(Object o) { - if (o == null) { - for (int i = 0; i < size; i++) - if (elementData[i] == null) - return i; - } else { - for (int i = 0; i < size; i++) - if (o.equals(elementData[i])) - return i; - } - - return -1; - } - - @Override - public int lastIndexOf(Object o) { - if (o == null) { - for (int i = size - 1; i >= 0; i--) - if (elementData[i] == null) - return i; - } else { - for (int i = size - 1; i >= 0; i--) - if (o.equals(elementData[i])) - return i; - } - - return -1; - } - - private void ensureExplicitCapacity(int minCapacity) { - modCount++; - - if (elementData.length > minCapacity) { - return; - } else if (minCapacity > MAX_ARRAY_SIZE) { - throw new OutOfMemoryError(); - } - - int oldCapacity = elementData.length; - - int newCapacity = oldCapacity == 0 ? 10 : (oldCapacity + (oldCapacity >> 1)); - if (newCapacity > MAX_ARRAY_SIZE) { - newCapacity = MAX_ARRAY_SIZE; - } - - elementData = Arrays.copyOf(elementData, newCapacity); - } - - @Override - public Iterator iterator() { - return new Itr(); - } - - @Override - public ListIterator listIterator() { - return new ListItr(0); - } - - @Override - public ListIterator listIterator(int index) { - if (index < 0 || index > size) - throw new IndexOutOfBoundsException("Index: " + index); - return new ListItr(index); - } - - /** - * fully copy from jdk ArrayList.Itr - */ - private class Itr implements Iterator { - int cursor; // index of next element to return - int lastRet = -1; // index of last element returned; -1 if no such - int expectedModCount = modCount; - - @Override - public boolean hasNext() { - return cursor != size; - } - - @Override - @SuppressWarnings("unchecked") - public E next() { - checkForComodification(); - int i = cursor; - if (i >= size) - throw new NoSuchElementException(); - Object[] elementData = ArrayList.this.elementData; - if (i >= elementData.length) - throw new ConcurrentModificationException(); - cursor = i + 1; - return (E) elementData[lastRet = i]; - } - - @Override - public void remove() { - if (lastRet < 0) - throw new IllegalStateException(); - checkForComodification(); - - try { - ArrayList.this.remove(lastRet); - cursor = lastRet; - lastRet = -1; - expectedModCount = modCount; - } catch (IndexOutOfBoundsException ex) { - throw new ConcurrentModificationException(); - } - } - - @Override - @SuppressWarnings("unchecked") - public void forEachRemaining(Consumer consumer) { - Objects.requireNonNull(consumer); - final int size = ArrayList.this.size; - int i = cursor; - if (i >= size) { - return; - } - final Object[] elementData = ArrayList.this.elementData; - if (i >= elementData.length) { - throw new ConcurrentModificationException(); - } - while (i != size && modCount == expectedModCount) { - consumer.accept((E) elementData[i++]); - } - // update once at end of iteration to reduce heap write traffic - cursor = i; - lastRet = i - 1; - checkForComodification(); - } - - final void checkForComodification() { - if (modCount != expectedModCount) - throw new ConcurrentModificationException(); - } - } - - /** - * fully copy from jdk ArrayList.ListItr - */ - private class ListItr extends Itr implements ListIterator { - ListItr(int index) { - super(); - cursor = index; - } - - @Override - public boolean hasPrevious() { - return cursor != 0; - } - - @Override - public int nextIndex() { - return cursor; - } - - @Override - public int previousIndex() { - return cursor - 1; - } - - @Override - @SuppressWarnings("unchecked") - public E previous() { - checkForComodification(); - int i = cursor - 1; - if (i < 0) - throw new NoSuchElementException(); - Object[] elementData = ArrayList.this.elementData; - if (i >= elementData.length) - throw new ConcurrentModificationException(); - cursor = i; - return (E) elementData[lastRet = i]; - } - - @Override - public void set(E e) { - if (lastRet < 0) - throw new IllegalStateException(); - checkForComodification(); - - try { - ArrayList.this.set(lastRet, e); - } catch (IndexOutOfBoundsException ex) { - throw new ConcurrentModificationException(); - } - } - - @Override - public void add(E e) { - checkForComodification(); - - try { - int i = cursor; - ArrayList.this.add(i, e); - cursor = i + 1; - lastRet = -1; - expectedModCount = modCount; - } catch (IndexOutOfBoundsException ex) { - throw new ConcurrentModificationException(); - } - } - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java deleted file mode 100644 index 47ed2e0bef..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/java/com/github/eulerlcs/jmr/algorithm/TestArrayList.java +++ /dev/null @@ -1,44 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -import java.util.List; - -import org.junit.After; -import org.junit.AfterClass; -import org.junit.Assert; -import org.junit.Before; -import org.junit.BeforeClass; -import org.junit.Test; - -public class TestArrayList { - - @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 test_foreach() { - List list = new ArrayList<>(); - list.add(1); - list.add(2); - list.add(3); - - int sum = 0; - for (Integer item : list) { - sum += item; - } - - Assert.assertEquals(sum, 6); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-61-collection/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml deleted file mode 100644 index a7a77b73df..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/data/struts.xml +++ /dev/null @@ -1,11 +0,0 @@ - - - - /jsp/homepage.jsp - /jsp/showLogin.jsp - - - /jsp/welcome.jsp - /jsp/error.jsp - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml deleted file mode 100644 index 353155e346..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/pom.xml +++ /dev/null @@ -1,39 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-62-litestruts - eulerlcs master java road lite struts - - - - commons-digester - commons-digester - - - org.projectlombok - lombok - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - com.github.stefanbirkner - system-rules - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java deleted file mode 100644 index c9cc7522b5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/algorithm/ArrayUtil.java +++ /dev/null @@ -1,279 +0,0 @@ -/** - * 问题点: 没写注释,代码比较难读。尤其 merge方法。 - */ -package com.github.eulerlcs.jmr.algorithm; - -import java.util.Arrays; - -public class ArrayUtil { - - /** - * 给定一个整形数组a , 对该数组的值进行置换 例如: a = [7, 9 , 30, 3] , 置换后为 [3, 30, 9,7] 如果 a = - * [7, 9, 30, 3, 4] , 置换后为 [4,3, 30 , 9,7] - * - * @param origin - * @return - */ - public static void reverseArray(int[] origin) { - if (origin == null || origin.length < 2) { - return; - } - - for (int head = 0, tail = origin.length - 1; head < tail; head++, tail--) { - origin[head] = origin[head] ^ origin[tail]; - origin[tail] = origin[head] ^ origin[tail]; - origin[head] = origin[head] ^ origin[tail]; - } - } - - /** - * 现在有如下的一个数组: int oldArr[]={1,3,4,5,0,0,6,6,0,5,4,7,6,7,0,5} - * 要求将以上数组中值为0的项去掉,将不为0的值存入一个新的数组,生成的新数组为: {1,3,4,5,6,6,5,4,7,6,7,5} - * - * @param oldArray - * @return - */ - - public static int[] removeZero(int[] oldArray) { - if (oldArray == null) { - return new int[0]; - } - - int count = 0; - for (int i = 0; i < oldArray.length; i++) { - if (oldArray[i] != 0) - count++; - } - - int[] newArray = new int[count]; - int newIndex = 0; - for (int i = 0; i < oldArray.length; i++) { - if (oldArray[i] != 0) { - newArray[newIndex] = oldArray[i]; - newIndex++; - } - } - - return newArray; - } - - /** - * 给定两个已经排序好的整形数组, a1和a2 , 创建一个新的数组a3, 使得a3 包含a1和a2 的所有元素, 并且仍然是有序的 例如 a1 = - * [3, 5, 7,8] a2 = [4, 5, 6,7] 则 a3 为[3,4,5,6,7,8] , 注意: 已经消除了重复 - * - * @param array1 - * @param array2 - * @return - */ - - public static int[] merge(int[] array1, int[] array2) { - if (array1 == null || array1.length == 0) { - if (array2 == null || array2.length == 0) { - return new int[0]; - } else { - return Arrays.copyOf(array2, array2.length); - } - } else if (array2 == null || array2.length == 0) { - return Arrays.copyOf(array1, array1.length); - } - - int[] result = new int[array1.length + array2.length]; - int idxResult = 0; - int idx1 = 0; - int idx2 = 0; - - for (; idx1 < array1.length; idx1++) { - if (array1[idx1] < array2[idx2]) { - result[idxResult] = array1[idx1]; - idxResult++; - } else if (array1[idx1] == array2[idx2]) { - result[idxResult] = array1[idx1]; - idxResult++; - idx2++; - } else { - for (; idx2 < array2.length; idx2++) { - if (array2[idx2] < array1[idx1]) { - result[idxResult] = array2[idx2]; - idxResult++; - } else { - if (array2[idx2] == array1[idx1]) { - idx2++; - } - - break; - } - } - - if (idx2 == array2.length) { - break; - } else { - idx1--; - } - } - } - - if (idx1 < array1.length) { - System.arraycopy(array1, idx1, result, idxResult, array1.length - idx1); - idxResult += array1.length - idx1; - } - - if (idx2 < array2.length) { - System.arraycopy(array2, idx2, result, idxResult, array2.length - idx2); - idxResult += array2.length - idx2; - } - - result = removeZero(result); - return result; - } - - /** - * 把一个已经存满数据的数组 oldArray的容量进行扩展, 扩展后的新数据大小为oldArray.length + size - * 注意,老数组的元素在新数组中需要保持 例如 oldArray = [2,3,6] , size = 3,则返回的新数组为 - * [2,3,6,0,0,0] - * - * @param oldArray - * @param increaseCapacity - * @return - */ - public static int[] grow(int[] oldArray, int increaseCapacity) { - if (oldArray == null || increaseCapacity < 0) { - return new int[0]; - } - - int newCapacity = oldArray.length + increaseCapacity; - - int[] newArray = Arrays.copyOf(oldArray, newCapacity); - - return newArray; - } - - /** - * 斐波那契数列为:1,1,2,3,5,8,13,21...... ,给定一个最大值, 返回小于该值的数列 例如, max = 15 , - * 则返回的数组应该为 [1,1,2,3,5,8,13] max = 1, 则返回空数组 [] - * - * @param max - * @return - */ - public static int[] fibonacci(int max) { - if (max <= 1) { - return new int[0]; - } - - int[] result = new int[10]; - result[0] = 1; - result[1] = 1; - int idx = 2; - int sum = 2; - while (sum < max) { - if (idx >= result.length) { - grow(result, result.length * 2); - } - - result[idx] = sum; - sum = result[idx - 1] + result[idx]; - idx++; - } - - result = removeZero(result); - return result; - } - - /** - * 返回小于给定最大值max的所有素数数组 例如max = 23, 返回的数组为[2,3,5,7,11,13,17,19] - * - * @param max - * @return - */ - public static int[] getPrimes(int max) { - if (max < 2) { - return new int[0]; - } - - int[] all = new int[max]; - int index = 0; - int temp = 0; - - for (int i = 0; i < max; i++) { - all[i] = i; - } - - all[0] = 0; - all[1] = 0; - index = 2; - - // 筛法 - loops: for (; index < max;) { - for (int i = 2;; i++) { - temp = index * i; - if (temp >= max) { - break; - } - all[temp] = 0; - } - - for (int i = index + 1; i < max; i++) { - if (all[i] != 0) { - index = i; - continue loops; - } - } - - break; - } - - int[] result = removeZero(all); - return result; - } - - /** - * 所谓“完数”, 是指这个数恰好等于它的因子之和,例如6=1+2+3 给定一个最大值max, 返回一个数组, 数组中是小于max 的所有完数 - * - * @param max - * @return - */ - public static long[] getPerfectNumbers(long max) { - long[] perfect = new long[49];// 到2016年1月为止,共发现了49个完全数 - int idx = 0; - long sum = 1; - long sqrt = 0; - - for (long n = 2; n < max; n++) { - sum = 1; - sqrt = (long) Math.sqrt(n); - for (long i = 2; i <= sqrt; i++) { - if (n % i == 0) - sum += i + n / i; - } - - if (sum == n) { - perfect[idx] = n; - idx++; - } - } - - // return removeZero(perfect); - return perfect; - } - - /** - * 用separator 把数组 array给连接起来 例如array= [3,8,9], separator = "-" 则返回值为"3-8-9" - * - * @param array - * @param separator - * @return - */ - public static String join(int[] array, String separator) { - if (array == null || array.length == 0) { - return ""; - } - - StringBuilder sb = new StringBuilder(); - - for (int i = 0; i < array.length - 1; i++) { - sb.append(array[i] + separator); - } - sb.append(String.valueOf(array[array.length - 1])); - - return sb.toString(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java deleted file mode 100644 index 4d9af132ac..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LoginAction.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.action; - -import lombok.Getter; -import lombok.Setter; - -/** - * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 - * - * @author liuxin - * - */ -public class LoginAction { - @Setter - @Getter - private String name; - @Setter - @Getter - private String password; - @Getter - private String message; - - public String execute() { - if ("test".equals(name) && "1234".equals(password)) { - this.message = "login successful"; - return "success"; - } - this.message = "login failed,please check your user/pwd"; - return "fail"; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java deleted file mode 100644 index 119e74e3e9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/action/LogoutAction.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.action; - -import lombok.Getter; -import lombok.Setter; - -/** - * 这是一个用来展示登录的业务类, 其中的用户名和密码都是硬编码的。 - * - * @author liuxin - * - */ -public class LogoutAction { - @Setter - @Getter - private String name; - @Setter - @Getter - private String password; - @Getter - private String message; - - public String execute() { - if ("test".equals(name) && "1234".equals(password)) { - this.message = "login successful"; - return "success"; - } - this.message = "login failed,please check your user/pwd"; - return "error"; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java deleted file mode 100644 index 459abaae99..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/Struts.java +++ /dev/null @@ -1,200 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.core; - -import java.io.File; -import java.io.IOException; -import java.lang.reflect.InvocationTargetException; -import java.lang.reflect.Method; -import java.util.HashMap; -import java.util.Map; - -import org.apache.commons.digester.Digester; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; -import org.xml.sax.SAXException; - -import com.github.eulerlcs.jmr.litestruts.degister.StrutsConfig; -import com.github.eulerlcs.jmr.litestruts.degister.StrutsDigester; - -/** - *
    - *
  • 读取配置文件struts.xml
  • - *
  • 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) - * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , - * "password"="1234") , 那就应该调用 setName和setPassword方法
  • - *
  • 通过反射调用对象的exectue 方法, 并获得返回值,例如"success"
  • - *
  • 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 - * {"message": "登录成功"} , 放到View对象的parameters
  • - *
  • 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, 放到View对象的jsp字段中。
  • - *
- */ -public class Struts { - private final static Logger log = LoggerFactory.getLogger(Struts.class); - private static StrutsConfig config = null; - - public static View runAction(String actionName, Map parameters) { - /* - * 0. 读取配置文件struts.xml - * - * 1. 根据actionName找到相对应的class , 例如LoginAction, 通过反射实例化(创建对象) - * 据parameters中的数据,调用对象的setter方法, 例如parameters中的数据是 ("name"="test" , - * "password"="1234") , 那就应该调用 setName和setPassword方法 - * - * 2. 通过反射调用对象的exectue 方法, 并获得返回值,例如"success" - * - * 3. 通过反射找到对象的所有getter方法(例如 getMessage), 通过反射来调用, 把值和属性形成一个HashMap , 例如 - * {"message": "登录成功"} , 放到View对象的parameters - * - * 4. 根据struts.xml中的 配置,以及execute的返回值, 确定哪一个jsp, - * 放到View对象的jsp字段中。 - * - */ - - // 0. - getConfig(); - - // 1.1. - Object object = createInstance(actionName); - if (object == null) { - return null; - } - // 1.2. - if (!prepareParameters(object, parameters)) { - return null; - } - // 2. - String viewId = execute(object); - if (viewId == null) { - return null; - } - // 3. - View view = biuldView(object); - if (view == null) { - return null; - } - - // 4. - String uri = config.getActionMap().get(actionName).getResults().get(viewId).getUrl(); - view.setJsp(uri); - - return view; - } - - private static StrutsConfig getConfig() { - if (config != null) { - return config; - } - - Digester d = StrutsDigester.newInstance(); - try { - File file = new File("data", "struts.xml"); - config = (StrutsConfig) d.parse(file); - } catch (IOException | SAXException e) { - log.error("getConfig", e); - System.exit(1); - } - - return config; - } - - private static Object createInstance(String actionName) { - if (actionName == null) { - return null; - } - - String className = config.getActionMap().get(actionName).getClazz(); - Object object = null; - try { - Class clazz = Class.forName(className); - object = clazz.newInstance(); - } catch (ClassNotFoundException | InstantiationException | IllegalAccessException e) { - log.error("createInstance", e); - } - - return object; - } - - private static boolean prepareParameters(Object object, Map parameters) { - if (parameters == null || parameters.size() == 0) { - return true; - } - - Class clazz = object.getClass(); - Method setter = null; - - try { - for (String key : parameters.keySet()) { - setter = clazz.getMethod(biuldSetterName(key), String.class); - setter.setAccessible(true); - setter.invoke(object, parameters.get(key)); - } - } catch (NoSuchMethodException | SecurityException | IllegalAccessException | IllegalArgumentException - | InvocationTargetException e) { - log.error("prepareParameters", e); - return false; - } - - return true; - } - - private static String biuldSetterName(String name) { - String setterName = "set"; - setterName += name.substring(0, 1).toUpperCase() + name.substring(1); - return setterName; - - } - - private static String debiuldGetterName(String getterName) { - if (getterName == null || getterName.length() <= 3) { - return null; - } - if (!getterName.substring(0, 3).equals("get")) { - return null; - } - - String name = getterName.substring(3, 4).toLowerCase() + getterName.substring(4); - return name; - } - - private static String execute(Object object) { - final String METHOD_EXECUTE = "execute"; - String viewId = null; - - Class clazz = object.getClass(); - try { - Method method = clazz.getMethod(METHOD_EXECUTE); - viewId = (String) method.invoke(object); - } catch (NoSuchMethodException | SecurityException | IllegalAccessException | IllegalArgumentException - | InvocationTargetException e) { - log.error("execute", e); - return viewId; - } - - return viewId; - } - - private static View biuldView(Object object) { - View view = new View(); - Map parameters = new HashMap<>(); - - Class clazz = object.getClass(); - Method[] methods; - try { - methods = clazz.getMethods(); - for (Method method : methods) { - String name = debiuldGetterName(method.getName()); - if (name == null) { - continue; - } - Object value = method.invoke(object); - parameters.put(name, value); - } - - view.setParameters(parameters); - } catch (SecurityException | IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { - log.error("biuldResult", e); - return null; - } - - return view; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java deleted file mode 100644 index 0aa18d5f54..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/core/View.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.core; - -import java.util.Map; - -public class View { - private String jsp; - private Map parameters; - - public String getJsp() { - return jsp; - } - - public View setJsp(String jsp) { - this.jsp = jsp; - return this; - } - - public Map getParameters() { - return parameters; - } - - public View setParameters(Map parameters) { - this.parameters = parameters; - return this; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java deleted file mode 100644 index 336f594241..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsAction.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.degister; - -import java.util.HashMap; -import java.util.Map; - -import lombok.Getter; -import lombok.Setter; - -public class StrutsAction { - @Getter - @Setter - private String name; - @Getter - @Setter - private String clazz; - @Getter - private Map results = new HashMap<>(); - - public void addResult(StrutsActionResult result) { - results.put(result.getName(), result); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java deleted file mode 100644 index 64247d4aba..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionResult.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.degister; - -import lombok.Getter; -import lombok.Setter; - -public class StrutsActionResult { - @Getter - @Setter - private String name; - @Getter - @Setter - private String url; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java deleted file mode 100644 index 567f4c7ef1..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsActionRulerSet.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.degister; - -import org.apache.commons.digester.Digester; -import org.apache.commons.digester.RuleSetBase; - -final class StrutsActionRulerSet extends RuleSetBase { - protected String prefix = null; - - public StrutsActionRulerSet() { - this(""); - } - - public StrutsActionRulerSet(String prefix) { - super(); - this.namespaceURI = null; - this.prefix = prefix; - } - - @Override - public void addRuleInstances(Digester digester) { - digester.addObjectCreate(prefix + "action", StrutsAction.class); - digester.addSetProperties(prefix + "action"); - digester.addSetProperties(prefix + "action", "class", "clazz"); - digester.addSetNext(prefix + "action", "addAction"); - digester.addObjectCreate(prefix + "action/result", StrutsActionResult.class); - digester.addSetProperties(prefix + "action/result"); - digester.addBeanPropertySetter(prefix + "action/result", "url"); - digester.addSetNext(prefix + "action/result", "addResult"); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java deleted file mode 100644 index b2005c9700..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsConfig.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.degister; - -import java.util.HashMap; -import java.util.Map; - -import lombok.Getter; - -public class StrutsConfig { - @Getter - private Map actionMap = new HashMap<>(); - - public void addAction(StrutsAction action) { - actionMap.put(action.getName(), action); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java deleted file mode 100644 index f466c8cb10..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/java/com/github/eulerlcs/jmr/litestruts/degister/StrutsDigester.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.degister; - -import org.apache.commons.digester.Digester; - -public class StrutsDigester { - public static Digester newInstance() { - Digester d = new Digester(); - d.addObjectCreate("struts", StrutsConfig.class); - d.addSetProperties("struts"); - d.addRuleSet(new StrutsActionRulerSet("struts/")); - return d; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java deleted file mode 100644 index 7242407f74..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/algorithm/ArrayUtilTest.java +++ /dev/null @@ -1,266 +0,0 @@ -/** - * 问题点: 没有全分支覆盖。只简单的测了关键或者关心的case - */ -package com.github.eulerlcs.jmr.algorithm; - -import static org.junit.Assert.assertArrayEquals; -import static org.junit.Assert.assertEquals; - -import org.junit.Test; - -public class ArrayUtilTest { - - @Test - public void reverseArray_null() { - int[] actuals = null; - int[] expecteds = null; - - ArrayUtil.reverseArray(actuals); - - assertArrayEquals(actuals, expecteds); - } - - @Test - public void reverseArray_0() { - int[] actuals = {}; - int[] expecteds = {}; - - ArrayUtil.reverseArray(actuals); - - assertArrayEquals(actuals, expecteds); - } - - @Test - public void reverseArray_1() { - int[] actuals = { 2 }; - int[] expecteds = { 2 }; - - ArrayUtil.reverseArray(actuals); - - assertArrayEquals(actuals, expecteds); - } - - @Test - public void reverseArray_2() { - int[] actuals = { 7, 9 }; - int[] expecteds = { 9, 7 }; - - ArrayUtil.reverseArray(actuals); - - assertArrayEquals(actuals, expecteds); - } - - @Test - public void reverseArray_4() { - int[] actuals = { 7, 9, 30, 3 }; - int[] expecteds = { 3, 30, 9, 7 }; - - ArrayUtil.reverseArray(actuals); - - assertArrayEquals(actuals, expecteds); - } - - @Test - public void reverseArray_5() { - int[] actuals = { 7, 9, 30, 3, 4 }; - int[] expecteds = { 4, 3, 30, 9, 7 }; - - ArrayUtil.reverseArray(actuals); - - assertArrayEquals(actuals, expecteds); - } - - @Test - public void removeZero_null() { - int oldArr[] = null; - int[] expecteds = {}; - - int[] newArr = ArrayUtil.removeZero(oldArr); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void removeZero_0() { - int oldArr[] = {}; - int[] expecteds = {}; - - int[] newArr = ArrayUtil.removeZero(oldArr); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void removeZero_1() { - int oldArr[] = { 0 }; - int[] expecteds = {}; - - int[] newArr = ArrayUtil.removeZero(oldArr); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void removeZero_2() { - int oldArr[] = { 3, 5 }; - int[] expecteds = { 3, 5 }; - - int[] newArr = ArrayUtil.removeZero(oldArr); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void removeZero_3() { - int oldArr[] = { 1, 3, 4, 5, 0, 0, 6, 6, 0, 5, 4, 7, 6, 7, 0, 5 }; - int[] expecteds = { 1, 3, 4, 5, 6, 6, 5, 4, 7, 6, 7, 5 }; - - int[] newArr = ArrayUtil.removeZero(oldArr); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void merge_1() { - int[] a1 = { 3, 5, 7, 8 }; - int[] a2 = { 4, 5, 6, 7 }; - int[] expecteds = { 3, 4, 5, 6, 7, 8 }; - - int[] newArr = ArrayUtil.merge(a1, a2); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void merge_2() { - int[] a1 = { 4, 5, 6, 7 }; - int[] a2 = { 3, 5, 7, 8 }; - int[] expecteds = { 3, 4, 5, 6, 7, 8 }; - - int[] newArr = ArrayUtil.merge(a1, a2); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void grow_1() { - int[] oldArray = { 2, 3, 6 }; - int increaseCapacity = 3; - int[] expecteds = { 2, 3, 6, 0, 0, 0 }; - - int[] newArr = ArrayUtil.grow(oldArray, increaseCapacity); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void fibonacci_1() { - int max = 1; - int[] expecteds = {}; - - int[] newArr = ArrayUtil.fibonacci(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void fibonacci_2() { - int max = 2; - int[] expecteds = { 1, 1 }; - - int[] newArr = ArrayUtil.fibonacci(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void fibonacci_15() { - int max = 15; - int[] expecteds = { 1, 1, 2, 3, 5, 8, 13 }; - - int[] newArr = ArrayUtil.fibonacci(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPrimes_1() { - int max = 1; - int[] expecteds = {}; - - int[] newArr = ArrayUtil.getPrimes(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPrimes_2() { - int max = 2; - int[] expecteds = {}; - - int[] newArr = ArrayUtil.getPrimes(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPrimes_3() { - int max = 3; - int[] expecteds = { 2 }; - - int[] newArr = ArrayUtil.getPrimes(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPrimes_4() { - int max = 4; - int[] expecteds = { 2, 3 }; - - int[] newArr = ArrayUtil.getPrimes(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPrimes_23() { - int max = 23; - int[] expecteds = { 2, 3, 5, 7, 11, 13, 17, 19 }; - - int[] newArr = ArrayUtil.getPrimes(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPrimes_24() { - int max = 24; - int[] expecteds = { 2, 3, 5, 7, 11, 13, 17, 19, 23 }; - - int[] newArr = ArrayUtil.getPrimes(max); - - assertArrayEquals(newArr, expecteds); - } - - @Test - public void getPerfectNumbers_max() { - long max = Long.MAX_VALUE; - max = 10000; - long[] expecteds = { 6, 28, 496, 8128, 33550336, 8589869056L, 137438691328L, 2305843008139952128L }; - - long[] newArr = ArrayUtil.getPerfectNumbers(max); - - assertEquals(newArr[3], expecteds[3]); - } - - @Test - public void join_0() { - int[] array = { 3, 8, 9 }; - String separator = "-"; - String expected = "3-8-9"; - - String actual = ArrayUtil.join(array, separator); - assertEquals(expected, actual); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java deleted file mode 100644 index b2fa989915..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/java/com/github/eulerlcs/jmr/litestruts/core/StrutsTest.java +++ /dev/null @@ -1,38 +0,0 @@ -package com.github.eulerlcs.jmr.litestruts.core; - -import java.util.HashMap; -import java.util.Map; - -import org.junit.Assert; -import org.junit.Test; - -public class StrutsTest { - - @Test - public void testLoginActionSuccess() { - - String actionName = "login"; - - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "1234"); - - View view = Struts.runAction(actionName, params); - - Assert.assertEquals("/jsp/homepage.jsp", view.getJsp()); - Assert.assertEquals("login successful", view.getParameters().get("message")); - } - - @Test - public void testLoginActionFailed() { - String actionName = "login"; - Map params = new HashMap(); - params.put("name", "test"); - params.put("password", "123456"); // 密码和预设的不一致 - - View view = Struts.runAction(actionName, params); - - Assert.assertEquals("/jsp/showLogin.jsp", view.getJsp()); - Assert.assertEquals("login failed,please check your user/pwd", view.getParameters().get("message")); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-62-litestruts/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/data/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-63-download/data/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml b/students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml deleted file mode 100644 index 8656e91371..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/pom.xml +++ /dev/null @@ -1,39 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-63-download - eulerlcs master java road - download file by multiple thread - - - - commons-digester - commons-digester - - - org.projectlombok - lombok - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - com.github.stefanbirkner - system-rules - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java deleted file mode 100644 index 78d537e842..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/Iterator.java +++ /dev/null @@ -1,8 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -public interface Iterator { - public boolean hasNext(); - - public Object next(); - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java deleted file mode 100644 index 7f42cc502b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/LinkedList.java +++ /dev/null @@ -1,126 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -public class LinkedList implements List { - - private Node head; - - public void add(Object o) { - - } - - public void add(int index, Object o) { - - } - - public Object get(int index) { - return null; - } - - public Object remove(int index) { - return null; - } - - public int size() { - return -1; - } - - public void addFirst(Object o) { - - } - - public void addLast(Object o) { - - } - - public Object removeFirst() { - return null; - } - - public Object removeLast() { - return null; - } - - public Iterator iterator() { - return null; - } - - private static class Node { - Object data; - Node next; - - } - - /** - * 把该链表逆置 例如链表为 3->7->10 , 逆置后变为 10->7->3 - */ - public void reverse() { - - } - - /** - * 删除一个单链表的前半部分 例如:list = 2->5->7->8 , 删除以后的值为 7->8 如果list = 2->5->7->8->10 - * ,删除以后的值为7,8,10 - * - */ - public void removeFirstHalf() { - - } - - /** - * 从第i个元素开始, 删除length 个元素 , 注意i从0开始 - * - * @param i - * @param length - */ - public void remove(int i, int length) { - - } - - /** - * 假定当前链表和list均包含已升序排列的整数 从当前链表中取出那些list所指定的元素 例如当前链表 = - * 11->101->201->301->401->501->601->701 listB = 1->3->4->6 - * 返回的结果应该是[101,301,401,601] - * - * @param list - */ - public static int[] getElements(LinkedList list) { - return null; - } - - /** - * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 从当前链表中中删除在list中出现的元素 - * - * @param list - */ - - public void subtract(LinkedList list) { - - } - - /** - * 已知当前链表中的元素以值递增有序排列,并以单链表作存储结构。 删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同) - */ - public void removeDuplicateValues() { - - } - - /** - * 已知链表中的元素以值递增有序排列,并以单链表作存储结构。 试写一高效的算法,删除表中所有值大于min且小于max的元素(若表中存在这样的元素) - * - * @param min - * @param max - */ - public void removeRange(int min, int max) { - - } - - /** - * 假设当前链表和参数list指定的链表均以元素依值递增有序排列(同一表中的元素值各不相同) - * 现要求生成新链表C,其元素为当前链表和list中元素的交集,且表C中的元素有依值递增有序排列 - * - * @param list - */ - public LinkedList intersection(LinkedList list) { - return null; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java deleted file mode 100644 index d693a0895d..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/algorithm/List.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -public interface List { - public void add(Object o); - - public void add(int index, Object o); - - public Object get(int index); - - public Object remove(int index); - - public int size(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java deleted file mode 100644 index 30042c8db0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/Connection.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.github.eulerlcs.jmr.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/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java deleted file mode 100644 index 2ba4d3978c..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionException.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.github.eulerlcs.jmr.download.api; - -public class ConnectionException extends Exception { - private static final long serialVersionUID = 1L; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java deleted file mode 100644 index e2faed7df6..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/ConnectionManager.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.github.eulerlcs.jmr.download.api; - -public interface ConnectionManager { - /** - * 给定一个url , 打开一个连接 - * - * @param url - * @return - */ - public Connection open(String url) throws ConnectionException; -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java deleted file mode 100644 index 80400ab21b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/api/DownloadListener.java +++ /dev/null @@ -1,5 +0,0 @@ -package com.github.eulerlcs.jmr.download.api; - -public interface DownloadListener { - public void notifyFinished(); -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java deleted file mode 100644 index 179a037a92..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/DownloadThread.java +++ /dev/null @@ -1,20 +0,0 @@ -package com.github.eulerlcs.jmr.download.core; - -import com.github.eulerlcs.jmr.download.api.Connection; - -public class DownloadThread extends Thread { - Connection conn; - int startPos; - int endPos; - - public DownloadThread(Connection conn, int startPos, int endPos) { - this.conn = conn; - this.startPos = startPos; - this.endPos = endPos; - } - - @Override - public void run() { - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java deleted file mode 100644 index fa3c193960..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/core/FileDownloader.java +++ /dev/null @@ -1,64 +0,0 @@ -package com.github.eulerlcs.jmr.download.core; - -import com.github.eulerlcs.jmr.download.api.Connection; -import com.github.eulerlcs.jmr.download.api.ConnectionException; -import com.github.eulerlcs.jmr.download.api.ConnectionManager; -import com.github.eulerlcs.jmr.download.api.DownloadListener; - -public class FileDownloader { - - String url; - - DownloadListener listener; - - ConnectionManager cm; - - 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 { - conn = cm.open(this.url); - - int length = conn.getContentLength(); - - new DownloadThread(conn, 0, length - 1).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/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java deleted file mode 100644 index 72b679702b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionImpl.java +++ /dev/null @@ -1,25 +0,0 @@ -package com.github.eulerlcs.jmr.download.impl; - -import java.io.IOException; - -import com.github.eulerlcs.jmr.download.api.Connection; - -public class ConnectionImpl implements Connection { - - @Override - public byte[] read(int startPos, int endPos) throws IOException { - - return null; - } - - @Override - public int getContentLength() { - - return 0; - } - - @Override - public void close() { - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java deleted file mode 100644 index b24ae09984..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/java/com/github/eulerlcs/jmr/download/impl/ConnectionManagerImpl.java +++ /dev/null @@ -1,14 +0,0 @@ -package com.github.eulerlcs.jmr.download.impl; - -import com.github.eulerlcs.jmr.download.api.Connection; -import com.github.eulerlcs.jmr.download.api.ConnectionException; -import com.github.eulerlcs.jmr.download.api.ConnectionManager; - -public class ConnectionManagerImpl implements ConnectionManager { - - @Override - public Connection open(String url) throws ConnectionException { - - return null; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java deleted file mode 100644 index 531601606e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/java/com/github/eulerlcs/jmr/download/core/FileDownloaderTest.java +++ /dev/null @@ -1,53 +0,0 @@ -package com.github.eulerlcs.jmr.download.core; - -import org.junit.After; -import org.junit.Before; -import org.junit.Test; - -import com.github.eulerlcs.jmr.download.api.ConnectionManager; -import com.github.eulerlcs.jmr.download.api.DownloadListener; -import com.github.eulerlcs.jmr.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://localhost:8080/test.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/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-63-download/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/data/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/data/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml deleted file mode 100644 index 76b2d2e4be..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/pom.xml +++ /dev/null @@ -1,43 +0,0 @@ - - 4.0.0 - - com.github.eulerlcs - jmr-02-parent - 0.0.1-SNAPSHOT - ../jmr-02-parent/pom.xml - - jmr-64-minijvm - eulerlcs master java road - mini jvm - - - - com.github.eulerlcs - jmr-61-collection - - - commons-digester - commons-digester - - - org.projectlombok - lombok - - - org.slf4j - slf4j-api - - - org.slf4j - slf4j-log4j12 - - - junit - junit - - - com.github.stefanbirkner - system-rules - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java deleted file mode 100644 index 25268be2dc..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrame.java +++ /dev/null @@ -1,110 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -/** - * 用双向链表实现LRU算法 - * - * @author liuxin, eulerlcs - */ -public class LRUPageFrame { - private static class Node { - Node prev; - Node next; - int pageNum; - } - - private int capacity; - private int length = 0; - private Node first;// 链表头 - private Node last;// 链表尾 - - public LRUPageFrame(int capacity) { - this.capacity = capacity; - } - - /** - * 获取缓存中对象 - * - * @param pageNum - */ - public void access(int pageNum) { - Node node = findNode(pageNum); - - if (node != null) { - moveToFirst(node); - } else { - node = new Node(); - node.pageNum = pageNum; - addToFirst(node); - } - } - - private Node findNode(int pageNum) { - Node node = first; - - while (node != null) { - if (node.pageNum == pageNum) { - return node; - } else { - node = node.next; - } - } - - return null; - } - - private void moveToFirst(Node node) { - if (node == first) { - return; - } else if (node == last) { - last = node.prev; - } - - if (node.prev != null) { - node.prev.next = node.next; - } - if (node.next != null) { - node.next.prev = node.prev; - } - - first.prev = node; - node.prev = null; - node.next = first; - - first = node; - } - - private void addToFirst(Node node) { - if (first == null) { - first = node; - last = first; - } else { - first.prev = node; - node.next = first; - first = node; - } - - length++; - if (length > capacity) { - last.prev.next = null; - last = last.prev; - - length = capacity; - } - } - - @Override - public String toString() { - StringBuilder buffer = new StringBuilder(); - Node node = first; - while (node != null) { - buffer.append(node.pageNum); - - node = node.next; - if (node != null) { - buffer.append(","); - } - } - - return buffer.toString(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java deleted file mode 100644 index 6f2c895554..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/Stack.java +++ /dev/null @@ -1,24 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -public class Stack { - private ArrayList elementData = new ArrayList(); - - public void push(Object o) { - } - - public Object pop() { - return null; - } - - public Object peek() { - return null; - } - - public boolean isEmpty() { - return false; - } - - public int size() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java deleted file mode 100644 index 1c0a56be56..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/algorithm/StackUtil.java +++ /dev/null @@ -1,43 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -public class StackUtil { - /** - * 假设栈中的元素是Integer, 从栈顶到栈底是 : 5,4,3,2,1 调用该方法后, 元素次序变为: 1,2,3,4,5 - * 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 - */ - public static void reverse(Stack s) { - - } - - /** - * 删除栈中的某个元素 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, 可以使用另外一个栈来辅助 - * - * @param o - */ - public static void remove(Stack s, Object o) { - - } - - /** - * 从栈顶取得len个元素, 原来的栈中元素保持不变 注意:只能使用Stack的基本操作,即push,pop,peek,isEmpty, - * 可以使用另外一个栈来辅助 - * - * @param len - * @return - */ - public static Object[] getTop(Stack s, int len) { - return null; - } - - /** - * 字符串s 可能包含这些字符: ( ) [ ] { }, a,b,c... x,yz 使用堆栈检查字符串s中的括号是不是成对出现的。 例如s = - * "([e{d}f])" , 则该字符串中的括号是成对出现, 该方法返回true 如果 s = "([b{x]y})", - * 则该字符串中的括号不是成对出现的, 该方法返回false; - * - * @param s - * @return - */ - public static boolean isValidPairs(String s) { - return false; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java deleted file mode 100644 index a74ee2eaaf..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/AttributeInfo.java +++ /dev/null @@ -1,19 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.attr; - -public abstract class AttributeInfo { - public static final String CODE = "Code"; - public static final String CONST_VALUE = "ConstantValue"; - public static final String EXCEPTIONS = "Exceptions"; - public static final String LINE_NUM_TABLE = "LineNumberTable"; - public static final String LOCAL_VAR_TABLE = "LocalVariableTable"; - public static final String STACK_MAP_TABLE = "StackMapTable"; - int attrNameIndex; - int attrLen; - - public AttributeInfo(int attrNameIndex, int attrLen) { - - this.attrNameIndex = attrNameIndex; - this.attrLen = attrLen; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java deleted file mode 100644 index ee99466cad..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/CodeAttr.java +++ /dev/null @@ -1,52 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.attr; - -import com.github.eulerlcs.jmr.jvm.clz.ClassFile; -import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; - -public class CodeAttr extends AttributeInfo { - private int maxStack; - private int maxLocals; - private int codeLen; - private String code; - - public String getCode() { - return code; - } - - // private ByteCodeCommand[] cmds ; - // public ByteCodeCommand[] getCmds() { - // return cmds; - // } - private LineNumberTable lineNumTable; - private LocalVariableTable localVarTable; - private StackMapTable stackMapTable; - - public CodeAttr(int attrNameIndex, int attrLen, int maxStack, int maxLocals, int codeLen, - String code /* ByteCodeCommand[] cmds */) { - super(attrNameIndex, attrLen); - this.maxStack = maxStack; - this.maxLocals = maxLocals; - this.codeLen = codeLen; - this.code = code; - // this.cmds = cmds; - } - - public void setLineNumberTable(LineNumberTable t) { - this.lineNumTable = t; - } - - public void setLocalVariableTable(LocalVariableTable t) { - this.localVarTable = t; - } - - public static CodeAttr parse(ClassFile clzFile, ByteCodeIterator iter) { - - return null; - } - - private void setStackMapTable(StackMapTable t) { - this.stackMapTable = t; - - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java deleted file mode 100644 index 3c3ee7e256..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LineNumberTable.java +++ /dev/null @@ -1,46 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.attr; - -import java.util.ArrayList; -import java.util.List; - -import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; - -public class LineNumberTable extends AttributeInfo { - List items = new ArrayList(); - - private static class LineNumberItem { - int startPC; - int lineNum; - - public int getStartPC() { - return startPC; - } - - public void setStartPC(int startPC) { - this.startPC = startPC; - } - - public int getLineNum() { - return lineNum; - } - - public void setLineNum(int lineNum) { - this.lineNum = lineNum; - } - } - - public void addLineNumberItem(LineNumberItem item) { - this.items.add(item); - } - - public LineNumberTable(int attrNameIndex, int attrLen) { - super(attrNameIndex, attrLen); - - } - - public static LineNumberTable parse(ByteCodeIterator iter) { - - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java deleted file mode 100644 index 19483e48d5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableItem.java +++ /dev/null @@ -1,49 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.attr; - -public class LocalVariableItem { - private int startPC; - private int length; - private int nameIndex; - private int descIndex; - private int index; - - public int getStartPC() { - return startPC; - } - - public void setStartPC(int startPC) { - this.startPC = startPC; - } - - public int getLength() { - return length; - } - - public void setLength(int length) { - this.length = length; - } - - public int getNameIndex() { - return nameIndex; - } - - public void setNameIndex(int nameIndex) { - this.nameIndex = nameIndex; - } - - public int getDescIndex() { - return descIndex; - } - - public void setDescIndex(int descIndex) { - this.descIndex = descIndex; - } - - public int getIndex() { - return index; - } - - public void setIndex(int index) { - this.index = index; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java deleted file mode 100644 index a847d9222e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/LocalVariableTable.java +++ /dev/null @@ -1,25 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.attr; - -import java.util.ArrayList; -import java.util.List; - -import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; - -public class LocalVariableTable extends AttributeInfo { - - List items = new ArrayList(); - - public LocalVariableTable(int attrNameIndex, int attrLen) { - super(attrNameIndex, attrLen); - } - - public static LocalVariableTable parse(ByteCodeIterator iter) { - - return null; - } - - private void addLocalVariableItem(LocalVariableItem item) { - this.items.add(item); - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java deleted file mode 100644 index e281ce8616..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/attr/StackMapTable.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.attr; - -import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; - -public class StackMapTable extends AttributeInfo { - - private String originalCode; - - public StackMapTable(int attrNameIndex, int attrLen) { - super(attrNameIndex, attrLen); - } - - public static StackMapTable parse(ByteCodeIterator iter) { - int index = iter.nextU2ToInt(); - int len = iter.nextU4ToInt(); - StackMapTable t = new StackMapTable(index, len); - - // 后面的StackMapTable太过复杂, 不再处理, 只把原始的代码读进来保存 - String code = iter.nextUxToHexString(len); - t.setOriginalCode(code); - - return t; - } - - private void setOriginalCode(String code) { - this.originalCode = code; - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java deleted file mode 100644 index 2e912067fd..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/AccessFlag.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.clz; - -public class AccessFlag { - private int flagValue; - - public AccessFlag(int value) { - this.flagValue = value; - } - - public int getFlagValue() { - return flagValue; - } - - public void setFlagValue(int flag) { - this.flagValue = flag; - } - - public boolean isPublicClass() { - return (this.flagValue & 0x0001) != 0; - } - - public boolean isFinalClass() { - return (this.flagValue & 0x0010) != 0; - } - -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java deleted file mode 100644 index 7b84ca588e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassFile.java +++ /dev/null @@ -1,100 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.clz; - -import java.util.ArrayList; -import java.util.List; - -import com.github.eulerlcs.jmr.jvm.constant.ClassInfo; -import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; -import com.github.eulerlcs.jmr.jvm.field.Field; -import com.github.eulerlcs.jmr.jvm.method.Method; - -public class ClassFile { - - private int minorVersion; - private int majorVersion; - - private AccessFlag accessFlag; - private ClassIndex clzIndex; - private ConstantPool pool; - private List fields = new ArrayList(); - private List methods = new ArrayList(); - - public ClassIndex getClzIndex() { - return clzIndex; - } - - public AccessFlag getAccessFlag() { - return accessFlag; - } - - public void setAccessFlag(AccessFlag accessFlag) { - this.accessFlag = accessFlag; - } - - public ConstantPool getConstantPool() { - return pool; - } - - public int getMinorVersion() { - return minorVersion; - } - - public void setMinorVersion(int minorVersion) { - this.minorVersion = minorVersion; - } - - public int getMajorVersion() { - return majorVersion; - } - - public void setMajorVersion(int majorVersion) { - this.majorVersion = majorVersion; - } - - public void setConstPool(ConstantPool pool) { - this.pool = pool; - - } - - public void setClassIndex(ClassIndex clzIndex) { - this.clzIndex = clzIndex; - } - - public void addField(Field f) { - this.fields.add(f); - } - - public List getFields() { - return this.fields; - } - - public void addMethod(Method m) { - this.methods.add(m); - } - - public List getMethods() { - return methods; - } - - public void print() { - - if (this.accessFlag.isPublicClass()) { - System.out.println("Access flag : public "); - } - System.out.println("Class Name:" + getClassName()); - - System.out.println("Super Class Name:" + getSuperClassName()); - - } - - private String getClassName() { - int thisClassIndex = this.clzIndex.getThisClassIndex(); - ClassInfo thisClass = (ClassInfo) this.getConstantPool().getConstantInfo(thisClassIndex); - return thisClass.getClassName(); - } - - private String getSuperClassName() { - ClassInfo superClass = (ClassInfo) this.getConstantPool().getConstantInfo(this.clzIndex.getSuperClassIndex()); - return superClass.getClassName(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java deleted file mode 100644 index 819b538406..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/clz/ClassIndex.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.clz; - -public class ClassIndex { - private int thisClassIndex; - private int superClassIndex; - - public int getThisClassIndex() { - return thisClassIndex; - } - - public void setThisClassIndex(int thisClassIndex) { - this.thisClassIndex = thisClassIndex; - } - - public int getSuperClassIndex() { - return superClassIndex; - } - - public void setSuperClassIndex(int superClassIndex) { - this.superClassIndex = superClassIndex; - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java deleted file mode 100644 index d2bc776faf..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ClassInfo.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class ClassInfo extends ConstantInfo { - private int type = ConstantInfo.CLASS_INFO; - private int utf8Index; - - public ClassInfo(ConstantPool pool) { - super(pool); - } - - public int getUtf8Index() { - return utf8Index; - } - - public void setUtf8Index(int utf8Index) { - this.utf8Index = utf8Index; - } - - @Override - public int getType() { - return type; - } - - public String getClassName() { - int index = getUtf8Index(); - UTF8Info utf8Info = (UTF8Info) constantPool.getConstantInfo(index); - return utf8Info.getValue(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java deleted file mode 100644 index c283fb56a5..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantInfo.java +++ /dev/null @@ -1,29 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public abstract class ConstantInfo { - public static final int UTF8_INFO = 1; - public static final int FLOAT_INFO = 4; - public static final int CLASS_INFO = 7; - public static final int STRING_INFO = 8; - public static final int FIELD_INFO = 9; - public static final int METHOD_INFO = 10; - public static final int NAME_AND_TYPE_INFO = 12; - protected ConstantPool constantPool; - - public ConstantInfo() { - } - - public ConstantInfo(ConstantPool pool) { - this.constantPool = pool; - } - - public abstract int getType(); - - public ConstantPool getConstantPool() { - return constantPool; - } - - public ConstantInfo getConstantInfo(int index) { - return this.constantPool.getConstantInfo(index); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java deleted file mode 100644 index ff1af9d094..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/ConstantPool.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -import java.util.ArrayList; -import java.util.List; - -public class ConstantPool { - - private List constantInfos = new ArrayList(); - - public ConstantPool() { - } - - public void addConstantInfo(ConstantInfo info) { - this.constantInfos.add(info); - } - - public ConstantInfo getConstantInfo(int index) { - return this.constantInfos.get(index); - } - - public String getUTF8String(int index) { - return ((UTF8Info) this.constantInfos.get(index)).getValue(); - } - - public Object getSize() { - return this.constantInfos.size() - 1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java deleted file mode 100644 index e5220ac5c4..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/FieldRefInfo.java +++ /dev/null @@ -1,54 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class FieldRefInfo extends ConstantInfo { - private int type = ConstantInfo.FIELD_INFO; - private int classInfoIndex; - private int nameAndTypeIndex; - - public FieldRefInfo(ConstantPool pool) { - super(pool); - } - - @Override - public int getType() { - return type; - } - - public int getClassInfoIndex() { - return classInfoIndex; - } - - public void setClassInfoIndex(int classInfoIndex) { - this.classInfoIndex = classInfoIndex; - } - - public int getNameAndTypeIndex() { - return nameAndTypeIndex; - } - - public void setNameAndTypeIndex(int nameAndTypeIndex) { - this.nameAndTypeIndex = nameAndTypeIndex; - } - - @Override - public String toString() { - NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); - return getClassName() + " : " + typeInfo.getName() + ":" + typeInfo.getTypeInfo() + "]"; - } - - public String getClassName() { - ClassInfo classInfo = (ClassInfo) this.getConstantInfo(this.getClassInfoIndex()); - UTF8Info utf8Info = (UTF8Info) this.getConstantInfo(classInfo.getUtf8Index()); - return utf8Info.getValue(); - } - - public String getFieldName() { - NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getName(); - } - - public String getFieldType() { - NameAndTypeInfo typeInfo = (NameAndTypeInfo) this.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getTypeInfo(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java deleted file mode 100644 index 4dc4ae3d1b..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/MethodRefInfo.java +++ /dev/null @@ -1,56 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class MethodRefInfo extends ConstantInfo { - private int type = ConstantInfo.METHOD_INFO; - - private int classInfoIndex; - private int nameAndTypeIndex; - - public MethodRefInfo(ConstantPool pool) { - super(pool); - } - - @Override - public int getType() { - return type; - } - - public int getClassInfoIndex() { - return classInfoIndex; - } - - public void setClassInfoIndex(int classInfoIndex) { - this.classInfoIndex = classInfoIndex; - } - - public int getNameAndTypeIndex() { - return nameAndTypeIndex; - } - - public void setNameAndTypeIndex(int nameAndTypeIndex) { - this.nameAndTypeIndex = nameAndTypeIndex; - } - - @Override - public String toString() { - return getClassName() + " : " + this.getMethodName() + " : " + this.getParamAndReturnType(); - } - - public String getClassName() { - ConstantPool pool = this.getConstantPool(); - ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(this.getClassInfoIndex()); - return clzInfo.getClassName(); - } - - public String getMethodName() { - ConstantPool pool = this.getConstantPool(); - NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getName(); - } - - public String getParamAndReturnType() { - ConstantPool pool = this.getConstantPool(); - NameAndTypeInfo typeInfo = (NameAndTypeInfo) pool.getConstantInfo(this.getNameAndTypeIndex()); - return typeInfo.getTypeInfo(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java deleted file mode 100644 index 6674006efd..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NameAndTypeInfo.java +++ /dev/null @@ -1,50 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class NameAndTypeInfo extends ConstantInfo { - public int type = ConstantInfo.NAME_AND_TYPE_INFO; - - private int index1; - private int index2; - - public NameAndTypeInfo(ConstantPool pool) { - super(pool); - } - - public int getIndex1() { - return index1; - } - - public void setIndex1(int index1) { - this.index1 = index1; - } - - public int getIndex2() { - return index2; - } - - public void setIndex2(int index2) { - this.index2 = index2; - } - - @Override - public int getType() { - return type; - } - - public String getName() { - ConstantPool pool = this.getConstantPool(); - UTF8Info utf8Info1 = (UTF8Info) pool.getConstantInfo(index1); - return utf8Info1.getValue(); - } - - public String getTypeInfo() { - ConstantPool pool = this.getConstantPool(); - UTF8Info utf8Info2 = (UTF8Info) pool.getConstantInfo(index2); - return utf8Info2.getValue(); - } - - @Override - public String toString() { - return "(" + getName() + "," + getTypeInfo() + ")"; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java deleted file mode 100644 index c4267ca5fc..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/NullConstantInfo.java +++ /dev/null @@ -1,11 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class NullConstantInfo extends ConstantInfo { - public NullConstantInfo() { - } - - @Override - public int getType() { - return -1; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java deleted file mode 100644 index 6f3575a5e0..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/StringInfo.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class StringInfo extends ConstantInfo { - private int type = ConstantInfo.STRING_INFO; - private int index; - - public StringInfo(ConstantPool pool) { - super(pool); - } - - @Override - public int getType() { - return type; - } - - public int getIndex() { - return index; - } - - public void setIndex(int index) { - this.index = index; - } - - @Override - public String toString() { - return this.getConstantPool().getUTF8String(index); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java deleted file mode 100644 index 2435cc554e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/constant/UTF8Info.java +++ /dev/null @@ -1,37 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.constant; - -public class UTF8Info extends ConstantInfo { - private int type = ConstantInfo.UTF8_INFO; - private int length; - private String value; - - public UTF8Info(ConstantPool pool) { - super(pool); - } - - public int getLength() { - return length; - } - - public void setLength(int length) { - this.length = length; - } - - @Override - public int getType() { - return type; - } - - @Override - public String toString() { - return "UTF8Info [type=" + type + ", length=" + length + ", value=" + value + ")]"; - } - - public String getValue() { - return value; - } - - public void setValue(String value) { - this.value = value; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java deleted file mode 100644 index d0f54964ac..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/field/Field.java +++ /dev/null @@ -1,26 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.field; - -import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; -import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; - -public class Field { - private int accessFlag; - private int nameIndex; - private int descriptorIndex; - - private ConstantPool pool; - - public Field(int accessFlag, int nameIndex, int descriptorIndex, ConstantPool pool) { - - this.accessFlag = accessFlag; - this.nameIndex = nameIndex; - this.descriptorIndex = descriptorIndex; - this.pool = pool; - } - - public static Field parse(ConstantPool pool, ByteCodeIterator iter) { - - return null; - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java deleted file mode 100644 index 095a81dece..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ByteCodeIterator.java +++ /dev/null @@ -1,55 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.loader; - -import java.util.Arrays; - -import com.github.eulerlcs.jmr.jvm.util.Util; - -public class ByteCodeIterator { - byte[] codes; - int pos = 0; - - ByteCodeIterator(byte[] codes) { - this.codes = codes; - } - - public byte[] getBytes(int len) { - if (pos + len >= codes.length) { - throw new ArrayIndexOutOfBoundsException(); - } - - byte[] data = Arrays.copyOfRange(codes, pos, pos + len); - pos += len; - return data; - } - - public int nextU1toInt() { - - return Util.byteToInt(new byte[] { codes[pos++] }); - } - - public int nextU2ToInt() { - return Util.byteToInt(new byte[] { codes[pos++], codes[pos++] }); - } - - public int nextU4ToInt() { - return Util.byteToInt(new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] }); - } - - public String nextU4ToHexString() { - return Util.byteToHexString((new byte[] { codes[pos++], codes[pos++], codes[pos++], codes[pos++] })); - } - - public String nextUxToHexString(int len) { - byte[] tmp = new byte[len]; - - for (int i = 0; i < len; i++) { - tmp[i] = codes[pos++]; - } - return Util.byteToHexString(tmp).toLowerCase(); - - } - - public void back(int n) { - this.pos -= n; - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java deleted file mode 100644 index 49018cb0a7..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileLoader.java +++ /dev/null @@ -1,74 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.loader; - -import java.io.DataInputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.util.ArrayList; -import java.util.List; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import com.github.eulerlcs.jmr.jvm.clz.ClassFile; - -public class ClassFileLoader { - private final static Logger log = LoggerFactory.getLogger(ClassFileLoader.class); - - private List clzPaths = new ArrayList(); - - public byte[] readBinaryCode(String className) { - File file = findClassFile(className); - if (file == null) { - return new byte[0]; - } - - byte[] ret = null; - byte[] bytes = new byte[(int) file.length()]; - try (DataInputStream dis = new DataInputStream(new FileInputStream(file))) { - dis.readFully(bytes); - ret = bytes; - } catch (IOException e) { - log.error("ClassFileLoader read error!", e); - } - - return ret; - } - - private File findClassFile(String className) { - String sub = className.replace(".", File.separator) + ".class"; - for (String clzPath : clzPaths) { - File file = new File(clzPath, sub); - if (file.exists()) { - return file; - } - } - - return null; - } - - public void addClassPath(String path) { - clzPaths.add(path); - } - - public String getClassPath() { - if (clzPaths.size() == 0) { - return ""; - } - - StringBuilder sb = new StringBuilder(); - for (String clzPath : clzPaths) { - sb.append(";"); - sb.append(clzPath); - } - - String cat = sb.toString(); - return cat.length() > 0 ? cat.substring(1) : ""; - } - - public ClassFile loadClass(String className) { - byte[] codes = this.readBinaryCode(className); - ClassFileParser parser = new ClassFileParser(); - return parser.parse(codes); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java deleted file mode 100644 index 394c35beb9..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileParser.java +++ /dev/null @@ -1,146 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.loader; - -import java.io.UnsupportedEncodingException; - -import com.github.eulerlcs.jmr.jvm.clz.AccessFlag; -import com.github.eulerlcs.jmr.jvm.clz.ClassFile; -import com.github.eulerlcs.jmr.jvm.clz.ClassIndex; -import com.github.eulerlcs.jmr.jvm.constant.ClassInfo; -import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; -import com.github.eulerlcs.jmr.jvm.constant.FieldRefInfo; -import com.github.eulerlcs.jmr.jvm.constant.MethodRefInfo; -import com.github.eulerlcs.jmr.jvm.constant.NameAndTypeInfo; -import com.github.eulerlcs.jmr.jvm.constant.NullConstantInfo; -import com.github.eulerlcs.jmr.jvm.constant.StringInfo; -import com.github.eulerlcs.jmr.jvm.constant.UTF8Info; - -public class ClassFileParser { - - public ClassFile parse(byte[] codes) { - - ClassFile clzFile = new ClassFile(); - - ByteCodeIterator iter = new ByteCodeIterator(codes); - - String magicNumber = iter.nextU4ToHexString(); - - if (!"cafebabe".equals(magicNumber)) { - return null; - } - - clzFile.setMinorVersion(iter.nextU2ToInt()); - clzFile.setMajorVersion(iter.nextU2ToInt()); - - ConstantPool pool = parseConstantPool(iter); - clzFile.setConstPool(pool); - - AccessFlag flag = parseAccessFlag(iter); - clzFile.setAccessFlag(flag); - - ClassIndex clzIndex = parseClassInfex(iter); - clzFile.setClassIndex(clzIndex); - - parseInterfaces(iter); - - return clzFile; - } - - private AccessFlag parseAccessFlag(ByteCodeIterator iter) { - - AccessFlag flag = new AccessFlag(iter.nextU2ToInt()); - // System.out.println("Is public class: " + flag.isPublicClass()); - // System.out.println("Is final class : " + flag.isFinalClass()); - - return flag; - } - - private ClassIndex parseClassInfex(ByteCodeIterator iter) { - - int thisClassIndex = iter.nextU2ToInt(); - int superClassIndex = iter.nextU2ToInt(); - - ClassIndex clzIndex = new ClassIndex(); - - clzIndex.setThisClassIndex(thisClassIndex); - clzIndex.setSuperClassIndex(superClassIndex); - - return clzIndex; - - } - - private ConstantPool parseConstantPool(ByteCodeIterator iter) { - - int constPoolCount = iter.nextU2ToInt(); - - System.out.println("Constant Pool Count :" + constPoolCount); - - ConstantPool pool = new ConstantPool(); - - pool.addConstantInfo(new NullConstantInfo()); - - for (int i = 1; i <= constPoolCount - 1; i++) { - - int tag = iter.nextU1toInt(); - - if (tag == 7) { - // Class Info - int utf8Index = iter.nextU2ToInt(); - ClassInfo clzInfo = new ClassInfo(pool); - clzInfo.setUtf8Index(utf8Index); - - pool.addConstantInfo(clzInfo); - } else if (tag == 1) { - // UTF-8 String - int len = iter.nextU2ToInt(); - byte[] data = iter.getBytes(len); - String value = null; - try { - value = new String(data, "UTF-8"); - } catch (UnsupportedEncodingException e) { - e.printStackTrace(); - } - - UTF8Info utf8Str = new UTF8Info(pool); - utf8Str.setLength(len); - utf8Str.setValue(value); - pool.addConstantInfo(utf8Str); - } else if (tag == 8) { - StringInfo info = new StringInfo(pool); - info.setIndex(iter.nextU2ToInt()); - pool.addConstantInfo(info); - } else if (tag == 9) { - FieldRefInfo field = new FieldRefInfo(pool); - field.setClassInfoIndex(iter.nextU2ToInt()); - field.setNameAndTypeIndex(iter.nextU2ToInt()); - pool.addConstantInfo(field); - } else if (tag == 10) { - // MethodRef - MethodRefInfo method = new MethodRefInfo(pool); - method.setClassInfoIndex(iter.nextU2ToInt()); - method.setNameAndTypeIndex(iter.nextU2ToInt()); - pool.addConstantInfo(method); - } else if (tag == 12) { - // Name and Type Info - NameAndTypeInfo nameType = new NameAndTypeInfo(pool); - nameType.setIndex1(iter.nextU2ToInt()); - nameType.setIndex2(iter.nextU2ToInt()); - pool.addConstantInfo(nameType); - } else { - throw new RuntimeException("the constant pool tag " + tag + " has not been implemented yet."); - } - } - - System.out.println("Finished reading Constant pool "); - - return pool; - } - - private void parseInterfaces(ByteCodeIterator iter) { - int interfaceCount = iter.nextU2ToInt(); - - System.out.println("interfaceCount:" + interfaceCount); - - // TODO : 如果实现了interface, 这里需要解析 - } - -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java deleted file mode 100644 index 2f043bc42e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/method/Method.java +++ /dev/null @@ -1,48 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.method; - -import com.github.eulerlcs.jmr.jvm.attr.CodeAttr; -import com.github.eulerlcs.jmr.jvm.clz.ClassFile; -import com.github.eulerlcs.jmr.jvm.loader.ByteCodeIterator; - -public class Method { - - private int accessFlag; - private int nameIndex; - private int descriptorIndex; - - private com.github.eulerlcs.jmr.jvm.attr.CodeAttr codeAttr; - - private ClassFile clzFile; - - public ClassFile getClzFile() { - return clzFile; - } - - public int getNameIndex() { - return nameIndex; - } - - public int getDescriptorIndex() { - return descriptorIndex; - } - - public CodeAttr getCodeAttr() { - return codeAttr; - } - - public void setCodeAttr(CodeAttr code) { - this.codeAttr = code; - } - - public Method(ClassFile clzFile, int accessFlag, int nameIndex, int descriptorIndex) { - this.clzFile = clzFile; - this.accessFlag = accessFlag; - this.nameIndex = nameIndex; - this.descriptorIndex = descriptorIndex; - } - - public static Method parse(ClassFile clzFile, ByteCodeIterator iter) { - return null; - - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java deleted file mode 100644 index 7cc99ed27e..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/java/com/github/eulerlcs/jmr/jvm/util/Util.java +++ /dev/null @@ -1,22 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.util; - -public class Util { - public static int byteToInt(byte[] codes) { - String s1 = byteToHexString(codes); - return Integer.valueOf(s1, 16).intValue(); - } - - public static String byteToHexString(byte[] codes) { - StringBuffer buffer = new StringBuffer(); - for (int i = 0; i < codes.length; i++) { - byte b = codes[i]; - int value = b & 0xFF; - String strHex = Integer.toHexString(value); - if (strHex.length() < 2) { - strHex = "0" + strHex; - } - buffer.append(strHex); - } - return buffer.toString(); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java deleted file mode 100644 index debc4d7eb6..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/algorithm/LRUPageFrameTest.java +++ /dev/null @@ -1,27 +0,0 @@ -package com.github.eulerlcs.jmr.algorithm; - -import org.junit.Assert; -import org.junit.Test; - -public class LRUPageFrameTest { - @Test - public void testAccess() { - LRUPageFrame frame = new LRUPageFrame(3); - frame.access(7); - frame.access(0); - frame.access(1); - Assert.assertEquals("1,0,7", frame.toString()); - frame.access(2); - Assert.assertEquals("2,1,0", frame.toString()); - frame.access(0); - Assert.assertEquals("0,2,1", frame.toString()); - frame.access(0); - Assert.assertEquals("0,2,1", frame.toString()); - frame.access(3); - Assert.assertEquals("3,0,2", frame.toString()); - frame.access(0); - Assert.assertEquals("0,3,2", frame.toString()); - frame.access(4); - Assert.assertEquals("4,0,3", frame.toString()); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java deleted file mode 100644 index 1e18416b61..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/ClassFileloaderTest.java +++ /dev/null @@ -1,220 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.loader; - -import java.io.File; -import java.util.List; - -import javax.xml.bind.DatatypeConverter; - -import org.junit.After; -import org.junit.Assert; -import org.junit.Before; -import org.junit.Test; - -import com.github.eulerlcs.jmr.jvm.clz.ClassFile; -import com.github.eulerlcs.jmr.jvm.clz.ClassIndex; -import com.github.eulerlcs.jmr.jvm.constant.ClassInfo; -import com.github.eulerlcs.jmr.jvm.constant.ConstantPool; -import com.github.eulerlcs.jmr.jvm.constant.MethodRefInfo; -import com.github.eulerlcs.jmr.jvm.constant.NameAndTypeInfo; -import com.github.eulerlcs.jmr.jvm.constant.UTF8Info; -import com.github.eulerlcs.jmr.jvm.field.Field; -import com.github.eulerlcs.jmr.jvm.method.Method; - -public class ClassFileloaderTest { - private static final String FULL_QUALIFIED_CLASS_NAME = "com/coderising/jvm/test/EmployeeV1"; - private static String userDir = System.getProperty("user.dir"); - private static String path1 = "C:\temp"; - private static String path2 = userDir + File.separator + "target" + File.separator + "test-classes"; - private static String className = EmployeeV1.class.getName(); - static ClassFileLoader loader = null; - static ClassFile clzFile = null; - static { - loader = new ClassFileLoader(); - loader.addClassPath(path1); - loader.addClassPath(path2); - clzFile = loader.loadClass(className); - clzFile.print(); - } - - @Before - public void setUp() throws Exception { - } - - @After - public void tearDown() throws Exception { - loader = null; - } - - @Test - public void testClassPath() { - String clzPath = loader.getClassPath(); - Assert.assertEquals(path1 + ";" + path2, clzPath); - } - - @Test - public void testClassFileLength() { - byte[] byteCodes = loader.readBinaryCode(className); - // 注意:这个字节数可能和你的JVM版本有关系, 你可以看看编译好的类到底有多大 - Assert.assertEquals(1078, byteCodes.length); - - } - - @Test - public void testMagicNumber() { - byte[] byteCodes = loader.readBinaryCode(className); - byte[] codes = new byte[] { byteCodes[0], byteCodes[1], byteCodes[2], byteCodes[3] }; - String acctualValue = DatatypeConverter.printHexBinary(codes); - - Assert.assertEquals("CAFEBABE", acctualValue); - } - - /** - * ---------------------------------------------------------------------- - */ - - @Test - public void testVersion() { - - Assert.assertEquals(0, clzFile.getMinorVersion()); - Assert.assertEquals(52, clzFile.getMajorVersion()); - - } - - @Test - public void testConstantPool() { - - ConstantPool pool = clzFile.getConstantPool(); - - Assert.assertEquals(53, pool.getSize()); - - { - ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(1); - Assert.assertEquals(2, clzInfo.getUtf8Index()); - - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(2); - Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, utf8Info.getValue()); - } - { - ClassInfo clzInfo = (ClassInfo) pool.getConstantInfo(3); - Assert.assertEquals(4, clzInfo.getUtf8Index()); - - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(4); - Assert.assertEquals("java/lang/Object", utf8Info.getValue()); - } - { - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(5); - Assert.assertEquals("name", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(6); - Assert.assertEquals("Ljava/lang/String;", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(7); - Assert.assertEquals("age", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(8); - Assert.assertEquals("I", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(9); - Assert.assertEquals("", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(10); - Assert.assertEquals("(Ljava/lang/String;I)V", utf8Info.getValue()); - - utf8Info = (UTF8Info) pool.getConstantInfo(11); - Assert.assertEquals("Code", utf8Info.getValue()); - } - - { - MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(12); - Assert.assertEquals(3, methodRef.getClassInfoIndex()); - Assert.assertEquals(13, methodRef.getNameAndTypeIndex()); - } - - { - NameAndTypeInfo nameAndType = (NameAndTypeInfo) pool.getConstantInfo(13); - Assert.assertEquals(9, nameAndType.getIndex1()); - Assert.assertEquals(14, nameAndType.getIndex2()); - } - // 抽查几个吧 - { - MethodRefInfo methodRef = (MethodRefInfo) pool.getConstantInfo(45); - Assert.assertEquals(1, methodRef.getClassInfoIndex()); - Assert.assertEquals(46, methodRef.getNameAndTypeIndex()); - } - - { - UTF8Info utf8Info = (UTF8Info) pool.getConstantInfo(53); - Assert.assertEquals("EmployeeV1.java", utf8Info.getValue()); - } - } - - @Test - public void testClassIndex() { - - ClassIndex clzIndex = clzFile.getClzIndex(); - ClassInfo thisClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getThisClassIndex()); - ClassInfo superClassInfo = (ClassInfo) clzFile.getConstantPool().getConstantInfo(clzIndex.getSuperClassIndex()); - - Assert.assertEquals(FULL_QUALIFIED_CLASS_NAME, thisClassInfo.getClassName()); - Assert.assertEquals("java/lang/Object", superClassInfo.getClassName()); - } - - /** - * 下面是第三次JVM课应实现的测试用例 - */ - @Test - public void testReadFields() { - - List fields = clzFile.getFields(); - Assert.assertEquals(2, fields.size()); - { - Field f = fields.get(0); - Assert.assertEquals("name:Ljava/lang/String;", f.toString()); - } - { - Field f = fields.get(1); - Assert.assertEquals("age:I", f.toString()); - } - } - - @Test - public void testMethods() { - - List methods = clzFile.getMethods(); - ConstantPool pool = clzFile.getConstantPool(); - - { - Method m = methods.get(0); - assertMethodEquals(pool, m, "", "(Ljava/lang/String;I)V", "2ab7000c2a2bb5000f2a1cb50011b1"); - - } - { - Method m = methods.get(1); - assertMethodEquals(pool, m, "setName", "(Ljava/lang/String;)V", "2a2bb5000fb1"); - - } - { - Method m = methods.get(2); - assertMethodEquals(pool, m, "setAge", "(I)V", "2a1bb50011b1"); - } - { - Method m = methods.get(3); - assertMethodEquals(pool, m, "sayHello", "()V", "b2001c1222b60024b1"); - - } - { - Method m = methods.get(4); - assertMethodEquals(pool, m, "main", "([Ljava/lang/String;)V", "bb000159122b101db7002d4c2bb6002fb1"); - } - } - - private void assertMethodEquals(ConstantPool pool, Method m, String expectedName, String expectedDesc, - String expectedCode) { - String methodName = pool.getUTF8String(m.getNameIndex()); - String methodDesc = pool.getUTF8String(m.getDescriptorIndex()); - String code = m.getCodeAttr().getCode(); - Assert.assertEquals(expectedName, methodName); - Assert.assertEquals(expectedDesc, methodDesc); - Assert.assertEquals(expectedCode, code); - } -} diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java deleted file mode 100644 index 070ad19083..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/java/com/github/eulerlcs/jmr/jvm/loader/EmployeeV1.java +++ /dev/null @@ -1,28 +0,0 @@ -package com.github.eulerlcs.jmr.jvm.loader; - -public class EmployeeV1 { - private String name; - private int age; - - public EmployeeV1(String name, int age) { - this.name = name; - this.age = age; - } - - public void setName(String name) { - this.name = name; - } - - public void setAge(int age) { - this.age = age; - } - - public void sayHello() { - System.out.println("Hello , this is class Employee "); - } - - public static void main(String[] args) { - EmployeeV1 p = new EmployeeV1("Andy", 29); - p.sayHello(); - } -} \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-64-minijvm/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml deleted file mode 100644 index 831b8d9ce3..0000000000 --- a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/resources/log4j.xml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/.gitkeep b/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/.gitkeep deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/students/41689722.eulerlcs/5.settingfile/eclipsev45.epf b/students/41689722.eulerlcs/5.settingfile/eclipsev45.epf deleted file mode 100644 index ca88d61e06..0000000000 --- a/students/41689722.eulerlcs/5.settingfile/eclipsev45.epf +++ /dev/null @@ -1,186 +0,0 @@ -#Sat Mar 11 11:44:44 JST 2017 -\!/= -/configuration/org.eclipse.core.net/org.eclipse.core.net.hasMigrated=true -/configuration/org.eclipse.ui.ide/MAX_RECENT_WORKSPACES=10 -/configuration/org.eclipse.ui.ide/RECENT_WORKSPACES=E\:\\10.github.repo\\coding2017.eulerlcs\\group09\\41689722.eulerlcs\\2.code -/configuration/org.eclipse.ui.ide/RECENT_WORKSPACES_PROTOCOL=3 -/configuration/org.eclipse.ui.ide/SHOW_RECENT_WORKSPACES=false -/configuration/org.eclipse.ui.ide/SHOW_WORKSPACE_SELECTION_DIALOG=true -/instance/org.eclipse.core.net/org.eclipse.core.net.hasMigrated=true -/instance/org.eclipse.core.resources/encoding=UTF-8 -/instance/org.eclipse.core.resources/version=1 -/instance/org.eclipse.debug.core/prefWatchExpressions=\r\n\r\n -/instance/org.eclipse.debug.ui/org.eclipse.debug.ui.PREF_LAUNCH_PERSPECTIVES=\r\n\r\n -/instance/org.eclipse.debug.ui/pref_state_memento.org.eclipse.debug.ui.DebugVieworg.eclipse.debug.ui.DebugView=\r\n -/instance/org.eclipse.debug.ui/pref_state_memento.org.eclipse.debug.ui.ExpressionView=\r\n\r\n\r\n -/instance/org.eclipse.debug.ui/pref_state_memento.org.eclipse.debug.ui.VariableView=\r\n -/instance/org.eclipse.debug.ui/preferredDetailPanes=DefaultDetailPane\:DefaultDetailPane| -/instance/org.eclipse.e4.ui.css.swt.theme/themeid=org.eclipse.e4.ui.css.theme.e4_default6.0,6.1,6.2,6.3,10.0 -/instance/org.eclipse.e4.ui.workbench.renderers.swt/enableMRU=true -/instance/org.eclipse.e4.ui.workbench.renderers.swt/themeEnabled=true -/instance/org.eclipse.egit.core/GitRepositoriesView.GitDirectories=E\:\\10.github.repo\\coding2017.eulerlcs\\.git; -/instance/org.eclipse.egit.core/GitRepositoriesView.GitDirectories.relative=E\:\\10.github.repo\\coding2017.eulerlcs\\.git; -/instance/org.eclipse.epp.logging.aeri.ide/resetSendMode=KEEP -/instance/org.eclipse.epp.logging.aeri.ide/resetSendModeOn=0 -/instance/org.eclipse.epp.logging.aeri.ide/sendMode=NOTIFY -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.codeComplete.visibilityCheck=enabled -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8 -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.compliance=1.8 -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.problem.assertIdentifier=error -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.problem.enumIdentifier=error -/instance/org.eclipse.jdt.core/org.eclipse.jdt.core.compiler.source=1.8 -/instance/org.eclipse.jdt.launching/org.eclipse.jdt.launching.PREF_VM_XML=\r\n\r\n\r\n\r\n\r\n\r\n -/instance/org.eclipse.jdt.ui/content_assist_number_of_computers=24 -/instance/org.eclipse.jdt.ui/content_assist_proposals_background=255,255,255 -/instance/org.eclipse.jdt.ui/content_assist_proposals_foreground=0,0,0 -/instance/org.eclipse.jdt.ui/editor_save_participant_org.eclipse.jdt.ui.postsavelistener.cleanup=true -/instance/org.eclipse.jdt.ui/fontPropagated=true -/instance/org.eclipse.jdt.ui/org.eclipse.jdt.internal.ui.navigator.layout=2 -/instance/org.eclipse.jdt.ui/org.eclipse.jdt.internal.ui.navigator.librariesnode=true -/instance/org.eclipse.jdt.ui/org.eclipse.jdt.ui.editor.tab.width= -/instance/org.eclipse.jdt.ui/org.eclipse.jdt.ui.formatterprofiles.version=12 -/instance/org.eclipse.jdt.ui/org.eclipse.jdt.ui.javadoclocations.migrated=true -/instance/org.eclipse.jdt.ui/org.eclipse.jface.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.jdt.ui/proposalOrderMigrated=true -/instance/org.eclipse.jdt.ui/sourceHoverBackgroundColor=255,255,225 -/instance/org.eclipse.jdt.ui/sp_cleanup.add_default_serial_version_id=true -/instance/org.eclipse.jdt.ui/sp_cleanup.add_generated_serial_version_id=false -/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_annotations=true -/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_deprecated_annotations=true -/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_methods=false -/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_nls_tags=false -/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_override_annotations=true -/instance/org.eclipse.jdt.ui/sp_cleanup.add_missing_override_annotations_interface_methods=true -/instance/org.eclipse.jdt.ui/sp_cleanup.add_serial_version_id=false -/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_blocks=true -/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_parentheses_in_expressions=false -/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_this_for_non_static_field_access=false -/instance/org.eclipse.jdt.ui/sp_cleanup.always_use_this_for_non_static_method_access=false -/instance/org.eclipse.jdt.ui/sp_cleanup.convert_functional_interfaces=false -/instance/org.eclipse.jdt.ui/sp_cleanup.convert_to_enhanced_for_loop=false -/instance/org.eclipse.jdt.ui/sp_cleanup.correct_indentation=false -/instance/org.eclipse.jdt.ui/sp_cleanup.format_source_code=true -/instance/org.eclipse.jdt.ui/sp_cleanup.format_source_code_changes_only=false -/instance/org.eclipse.jdt.ui/sp_cleanup.insert_inferred_type_arguments=false -/instance/org.eclipse.jdt.ui/sp_cleanup.make_local_variable_final=true -/instance/org.eclipse.jdt.ui/sp_cleanup.make_parameters_final=false -/instance/org.eclipse.jdt.ui/sp_cleanup.make_private_fields_final=true -/instance/org.eclipse.jdt.ui/sp_cleanup.make_type_abstract_if_missing_method=false -/instance/org.eclipse.jdt.ui/sp_cleanup.make_variable_declarations_final=false -/instance/org.eclipse.jdt.ui/sp_cleanup.never_use_blocks=false -/instance/org.eclipse.jdt.ui/sp_cleanup.never_use_parentheses_in_expressions=true -/instance/org.eclipse.jdt.ui/sp_cleanup.on_save_use_additional_actions=true -/instance/org.eclipse.jdt.ui/sp_cleanup.organize_imports=true -/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_field_accesses_with_declaring_class=false -/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_member_accesses_through_instances_with_declaring_class=true -/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class=true -/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_member_accesses_with_declaring_class=false -/instance/org.eclipse.jdt.ui/sp_cleanup.qualify_static_method_accesses_with_declaring_class=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_private_constructors=true -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_redundant_type_arguments=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_trailing_whitespaces=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_trailing_whitespaces_all=true -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_trailing_whitespaces_ignore_empty=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unnecessary_casts=true -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unnecessary_nls_tags=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_imports=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_local_variables=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_fields=true -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_members=false -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_methods=true -/instance/org.eclipse.jdt.ui/sp_cleanup.remove_unused_private_types=true -/instance/org.eclipse.jdt.ui/sp_cleanup.sort_members=false -/instance/org.eclipse.jdt.ui/sp_cleanup.sort_members_all=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_anonymous_class_creation=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_blocks=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_blocks_only_for_return_and_throw=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_lambda=true -/instance/org.eclipse.jdt.ui/sp_cleanup.use_parentheses_in_expressions=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_field_access=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_field_access_only_if_necessary=true -/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_method_access=false -/instance/org.eclipse.jdt.ui/sp_cleanup.use_this_for_non_static_method_access_only_if_necessary=true -/instance/org.eclipse.jdt.ui/spelling_locale_initialized=true -/instance/org.eclipse.jdt.ui/tabWidthPropagated=true -/instance/org.eclipse.jdt.ui/useAnnotationsPrefPage=true -/instance/org.eclipse.jdt.ui/useQuickDiffPrefPage=true -/instance/org.eclipse.jst.j2ee.webservice.ui/areThereWebServices=false -/instance/org.eclipse.m2e.discovery/org.eclipse.m2e.discovery.pref.projects= -/instance/org.eclipse.mylyn.context.core/mylyn.attention.migrated=true -/instance/org.eclipse.mylyn.monitor.ui/org.eclipse.mylyn.monitor.activity.tracking.enabled.checked=true -/instance/org.eclipse.mylyn.tasks.ui/migrated.task.repositories.secure.store=true -/instance/org.eclipse.mylyn.tasks.ui/org.eclipse.mylyn.tasks.ui.filters.nonmatching=true -/instance/org.eclipse.mylyn.tasks.ui/org.eclipse.mylyn.tasks.ui.filters.nonmatching.encouraged=true -/instance/org.eclipse.mylyn.tasks.ui/org.eclipse.mylyn.tasks.ui.welcome.message=true -/instance/org.eclipse.oomph.workingsets/working.set.group=\n\n -/instance/org.eclipse.rse.core/org.eclipse.rse.systemtype.local.systemType.defaultUserId=euler -/instance/org.eclipse.rse.ui/org.eclipse.rse.preferences.order.connections=euler-PC.Local -/instance/org.eclipse.team.ui/org.eclipse.team.ui.first_time=false -/instance/org.eclipse.ui.editors/overviewRuler_migration=migrated_3.1 -/instance/org.eclipse.ui.ide/PROBLEMS_FILTERS_MIGRATE=true -/instance/org.eclipse.ui.ide/platformState=1488095469945 -/instance/org.eclipse.ui.ide/quickStart=false -/instance/org.eclipse.ui.ide/tipsAndTricks=true -/instance/org.eclipse.ui.workbench//org.eclipse.ui.commands/state/org.eclipse.ui.navigator.resources.nested.changeProjectPresentation/org.eclipse.ui.commands.radioState=false -/instance/org.eclipse.ui.workbench//org.eclipse.ui.commands/state/org.eclipse.wst.xml.views.XPathView.processor.xpathprocessor/org.eclipse.ui.commands.radioState=xpath10 -/instance/org.eclipse.ui.workbench/ColorsAndFontsPreferencePage.expandedCategories=Torg.eclipse.ui.workbenchMisc\tTorg.eclipse.jdt.ui.presentation\tTorg.eclipse.wst.sse.ui -/instance/org.eclipse.ui.workbench/ColorsAndFontsPreferencePage.selectedElement=Forg.eclipse.jface.textfont -/instance/org.eclipse.ui.workbench/PLUGINS_NOT_ACTIVATED_ON_STARTUP=org.eclipse.m2e.discovery;org.eclipse.rse.ui; -/instance/org.eclipse.ui.workbench/REMOTE_COMMANDS_VIEW_FONT=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.compare.contentmergeviewer.TextMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.debug.ui.DetailPaneFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.debug.ui.MemoryViewTableFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.debug.ui.consoleFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.egit.ui.CommitMessageEditorFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.egit.ui.CommitMessageFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.egit.ui.DiffHeadlineFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.jdt.internal.ui.compare.JavaMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.jdt.internal.ui.compare.PropertiesFileMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.jdt.ui.PropertiesFileEditor.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.jdt.ui.editors.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.jface.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.mylyn.wikitext.ui.presentation.textFont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.pde.internal.ui.compare.ManifestContentMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.pde.internal.ui.compare.PluginContentMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.ui.commands=\r\n -/instance/org.eclipse.ui.workbench/org.eclipse.wst.jsdt.internal.ui.compare.JavaMergeViewer=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.wst.jsdt.ui.editors.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/org.eclipse.wst.sse.ui.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui.workbench/terminal.views.view.font.definition=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.ui/showIntro=false -/instance/org.eclipse.wst.jsdt.ui/fontPropagated=true -/instance/org.eclipse.wst.jsdt.ui/org.eclipse.jface.textfont=1|Consolas|12.0|0|WINDOWS|1|-16|0|0|0|400|0|0|0|0|3|2|1|49|Consolas; -/instance/org.eclipse.wst.jsdt.ui/org.eclipse.wst.jsdt.ui.editor.tab.width= -/instance/org.eclipse.wst.jsdt.ui/org.eclipse.wst.jsdt.ui.formatterprofiles.version=11 -/instance/org.eclipse.wst.jsdt.ui/org.eclipse.wst.jsdt.ui.javadoclocations.migrated=true -/instance/org.eclipse.wst.jsdt.ui/proposalOrderMigrated=true -/instance/org.eclipse.wst.jsdt.ui/tabWidthPropagated=true -/instance/org.eclipse.wst.jsdt.ui/useAnnotationsPrefPage=true -/instance/org.eclipse.wst.jsdt.ui/useQuickDiffPrefPage=true -@org.eclipse.core.net=1.3.0.v20160418-1534 -@org.eclipse.core.resources=3.11.1.v20161107-2032 -@org.eclipse.debug.core=3.10.100.v20160419-1720 -@org.eclipse.debug.ui=3.11.202.v20161114-0338 -@org.eclipse.e4.ui.css.swt.theme=0.10.100.v20160523-0836 -@org.eclipse.e4.ui.workbench.renderers.swt=0.14.0.v20160525-0940 -@org.eclipse.egit.core=4.4.1.201607150455-r -@org.eclipse.epp.logging.aeri.ide=2.0.3.v20161205-0933 -@org.eclipse.jdt.core=3.12.2.v20161117-1814 -@org.eclipse.jdt.launching=3.8.101.v20161111-2014 -@org.eclipse.jdt.ui=3.12.2.v20160929-0804 -@org.eclipse.jst.j2ee.webservice.ui=1.1.500.v201302011850 -@org.eclipse.m2e.discovery=1.7.0.20160603-1933 -@org.eclipse.mylyn.context.core=3.21.0.v20160701-1337 -@org.eclipse.mylyn.monitor.ui=3.21.0.v20160630-1702 -@org.eclipse.mylyn.tasks.ui=3.21.0.v20160913-2131 -@org.eclipse.oomph.workingsets=1.6.0.v20161019-0656 -@org.eclipse.rse.core=3.3.100.201603151753 -@org.eclipse.rse.ui=3.3.300.201610252046 -@org.eclipse.team.ui=3.8.0.v20160518-1906 -@org.eclipse.ui=3.108.1.v20160929-1045 -@org.eclipse.ui.editors=3.10.1.v20161106-1856 -@org.eclipse.ui.ide=3.12.2.v20161115-1450 -@org.eclipse.ui.workbench=3.108.2.v20161025-2029 -@org.eclipse.wst.jsdt.ui=2.0.0.v201608301904 -file_export_version=3.0 diff --git a/students/41689722.eulerlcs/5.settingfile/git cmd help.txt b/students/41689722.eulerlcs/5.settingfile/git cmd help.txt deleted file mode 100644 index 86015b4865..0000000000 --- a/students/41689722.eulerlcs/5.settingfile/git cmd help.txt +++ /dev/null @@ -1,43 +0,0 @@ -open git server deretory -mkdir abc.git -cd abc.git - -run git bash - git --bare init --shared - -git clone -cd abc - -git config --global push. default simple -git push --set-upstream origin master -git push - -get remot branch list - git remote update - - -add deleted files - git rm - git rm $(git ls-files --deleted) - - -delete (remote) branch - git branch -d branch.abc - git push origin :branch.abc - - or - - git push --delete origin branch.abc - - -romote branch douki - git fecth --all --prune - -git log - git log --graph --pretty=format: - -// http://blog.toshimaru.net/git-log-graph/ - [alias] - lg = git log --graph --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit --date=relative - lga = git log --graph --all --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit --date=relative - \ No newline at end of file diff --git a/students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat b/students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat deleted file mode 100644 index ddb704e561..0000000000 --- a/students/41689722.eulerlcs/5.settingfile/tool.161118.git-source-copy.bat +++ /dev/null @@ -1,37 +0,0 @@ -@echo off -setlocal ENABLEDELAYEDEXPANSION - -rem .* -:main - call :ini - - set path_root=d:\abc - set path_desc=pg.%yymmdd%.%hhmmss% - - call :copy_source "" - call :copy_source "" - - call :end - @echo on - -goto :eof -:copy_source - if %1=="" goto :eof - set file_name=%~1 - set file_name=!file_name:/=\! - @echo f | xcopy /r/y/s %path_root%\!file_name! %path_desc%\!file_name! - -goto :eof -:end - @echo. - @echo. - pause - -goto :eof -:ini - set self_path="%cd%" - set yyyymmdd=%date:~0,4%%date:~5,2%%date:~8,2% - set yymmdd=!yyyymmdd:~2,6! - set hhmmss=%time:~0,2%%time:~3,2%%time:~6,2% - if "!hhmmss:~0,1!" == " " set hhmmss=0!hhmmss:~1,7! -goto :eof diff --git a/students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat b/students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat deleted file mode 100644 index 5189f9e130..0000000000 --- a/students/41689722.eulerlcs/5.settingfile/tool.170330.java-maven-source-cleaner.bat +++ /dev/null @@ -1,37 +0,0 @@ -@echo off -setlocal ENABLEDELAYEDEXPANSION - -:main - call :ini - cd /d E:\12.repolist\41689722.eulerlcs\2.code - call :del_resource - call :end - @echo on - -goto :eof -:del_resource - for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".settings"`) do rmdir /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".metadata"`) do rmdir /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/ad-h "target"`) do rmdir /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/ad-h "RemoteSystemsTempFiles"`) do rmdir /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".recommenders"`) do rmdir /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/ad-h ".apt_generated"`) do rmdir /s/q %%a - - for /f "usebackq delims==" %%a in (`dir /b/s/a-d-h ".classpath"`) do del /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/a-d-h ".project"`) do del /s/q %%a - for /f "usebackq delims==" %%a in (`dir /b/s/a-d-h ".factorypath"`) do del /s/q %%a - -goto :eof -:end - @echo. - @echo. - pause - -goto :eof -:ini - set self_path="%cd%" - set yyyymmdd=%date:~0,4%%date:~5,2%%date:~8,2% - set yymmdd=!yyyymmdd:~2,6! - set hhmmss=%time:~0,2%%time:~3,2%%time:~6,2% - if "!hhmmss:~0,1!" == " " set hhmmss=0!hhmmss:~1,7! -goto :eof diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/pom.xml b/students/41689722.eulerlcs/regularexpression/pom.xml similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-71-regularexpression/pom.xml rename to students/41689722.eulerlcs/regularexpression/pom.xml diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java b/students/41689722.eulerlcs/regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java rename to students/41689722.eulerlcs/regularexpression/src/main/java/com/github/eulerlcs/regularexpression/Utils.java diff --git a/students/41689722.eulerlcs/1.article/.gitkeep b/students/41689722.eulerlcs/regularexpression/src/main/resources/.gitkeep similarity index 100% rename from students/41689722.eulerlcs/1.article/.gitkeep rename to students/41689722.eulerlcs/regularexpression/src/main/resources/.gitkeep diff --git a/students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/log4j.xml b/students/41689722.eulerlcs/regularexpression/src/main/resources/log4j.xml similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-11-challenge/src/main/resources/log4j.xml rename to students/41689722.eulerlcs/regularexpression/src/main/resources/log4j.xml diff --git a/students/41689722.eulerlcs/2.code/jmr-01-aggregator/src/site/.gitkeep b/students/41689722.eulerlcs/regularexpression/src/test/java/.gitkeep similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-01-aggregator/src/site/.gitkeep rename to students/41689722.eulerlcs/regularexpression/src/test/java/.gitkeep diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java b/students/41689722.eulerlcs/regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java rename to students/41689722.eulerlcs/regularexpression/src/test/java/com/github/eulerlcs/regularexpression/UtilsTest.java diff --git a/students/41689722.eulerlcs/2.code/jmr-02-parent/src/site/.gitkeep b/students/41689722.eulerlcs/regularexpression/src/test/resources/.gitkeep similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-02-parent/src/site/.gitkeep rename to students/41689722.eulerlcs/regularexpression/src/test/resources/.gitkeep diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01.txt b/students/41689722.eulerlcs/regularexpression/src/test/resources/01.txt similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/01.txt rename to students/41689722.eulerlcs/regularexpression/src/test/resources/01.txt diff --git a/students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/07.txt b/students/41689722.eulerlcs/regularexpression/src/test/resources/07.txt similarity index 100% rename from students/41689722.eulerlcs/2.code/jmr-71-regularexpression/src/test/resources/07.txt rename to students/41689722.eulerlcs/regularexpression/src/test/resources/07.txt