├── CONTRIBUTING.md ├── src ├── main │ └── java │ │ └── com │ │ └── pancm │ │ ├── mq │ │ ├── package-info.java │ │ ├── kafka │ │ │ ├── package-info.java │ │ │ ├── test3 │ │ │ │ └── package-info.java │ │ │ ├── examples │ │ │ │ ├── package-info.java │ │ │ │ ├── KafkaProducerConsumerDemo.java │ │ │ │ ├── Producer.java │ │ │ │ ├── Consumer.java │ │ │ │ └── DataProducer.java │ │ │ ├── others │ │ │ │ ├── package-info.java │ │ │ │ ├── TestConsumer.java │ │ │ │ └── TestProducer.java │ │ │ ├── test2 │ │ │ │ ├── package-info.java │ │ │ │ └── KafkaProducerTest.java │ │ │ └── test1 │ │ │ │ ├── package-info.java │ │ │ │ └── KafkaProducerTest.java │ │ └── rabbitmq │ │ │ ├── package-info.java │ │ │ ├── demo │ │ │ ├── RabbitConsumer.java │ │ │ ├── RabbitProducer.java │ │ │ └── C.java │ │ │ ├── one2one │ │ │ ├── Send.java │ │ │ ├── ClientSend1.java │ │ │ ├── Recv.java │ │ │ └── ClientReceive1.java │ │ │ └── one2more │ │ │ ├── NewTask.java │ │ │ └── Worker.java │ │ ├── nio │ │ ├── package-info.java │ │ ├── mina │ │ │ ├── package-info.java │ │ │ ├── demo1 │ │ │ │ ├── MinaClientHandler.java │ │ │ │ ├── MyTextLineCodecFactory.java │ │ │ │ ├── MyTextLineCodecEncoder.java │ │ │ │ ├── MinaServer.java │ │ │ │ ├── MinaClient.java │ │ │ │ └── MinaServerHandler.java │ │ │ └── demo │ │ │ │ ├── MinaClientHandler.java │ │ │ │ ├── MinaServerHandler.java │ │ │ │ └── MinaServer.java │ │ └── netty │ │ │ ├── package-info.java │ │ │ ├── demo6 │ │ │ ├── package-info.java │ │ │ ├── NettyServerFilter.java │ │ │ └── NettyServer.java │ │ │ ├── demo1 │ │ │ ├── BaseClient2Handler.java │ │ │ ├── BaseClient1Handler.java │ │ │ ├── NettyClientHandler.java │ │ │ └── NettyServerHandler.java │ │ │ ├── demo3 │ │ │ ├── NettyClientHandlerDemo3.java │ │ │ ├── NettyServerHandlerDemo3.java │ │ │ ├── NettyEncoder.java │ │ │ ├── NettyMsg.java │ │ │ ├── NettyDecoder.java │ │ │ └── NettyClientDemo3.java │ │ │ ├── demo4 │ │ │ ├── NettyClientHandlerDemo4.java │ │ │ ├── NettyServerHandlerDemo4.java │ │ │ ├── NettySendBody.java │ │ │ ├── NettyServerDemo4.java │ │ │ └── NettyClientDemo4.java │ │ │ ├── demo2 │ │ │ └── NettyServerHandlerDemo2.java │ │ │ ├── demo │ │ │ ├── NettyClientHandler.java │ │ │ ├── NettyClientFilter.java │ │ │ ├── NettyServerFilter.java │ │ │ ├── NettyServerHandler.java │ │ │ ├── NettyServer.java │ │ │ └── NettyClient.java │ │ │ └── demo5 │ │ │ └── NettyServerHandlerDemo5.java │ │ ├── utils │ │ └── package-info.java │ │ ├── bigdata │ │ ├── package-info.java │ │ ├── hbase │ │ │ └── package-info.java │ │ ├── zookeeper │ │ │ └── package-info.java │ │ └── storm │ │ │ ├── one │ │ │ ├── package-info.java │ │ │ ├── WordNormalizer.java │ │ │ ├── WordCounter.java │ │ │ └── WordCountApp.java │ │ │ ├── package-info.java │ │ │ ├── test │ │ │ ├── package-info.java │ │ │ ├── App.java │ │ │ ├── TestBolt.java │ │ │ └── TestSpout.java │ │ │ ├── test2 │ │ │ ├── package-info.java │ │ │ ├── App.java │ │ │ ├── TestBolt.java │ │ │ └── Test2Bolt.java │ │ │ ├── example │ │ │ ├── package-info.java │ │ │ ├── WordNormalizer.java │ │ │ ├── WordCounter.java │ │ │ └── WordCountApp.java │ │ │ └── example1 │ │ │ ├── package-info.java │ │ │ ├── SplitSentenceBolt.java │ │ │ └── ReportBolt.java │ │ ├── code │ │ ├── package-info.java │ │ └── MapCodeTest.java │ │ ├── others │ │ ├── package-info.java │ │ └── LogbackTest.java │ │ ├── pojo │ │ ├── package-info.java │ │ ├── Student.java │ │ └── User.java │ │ ├── redis │ │ ├── package-info.java │ │ └── RedisTest.java │ │ ├── sql │ │ └── package-info.java │ │ ├── arithmetic │ │ ├── package-info.java │ │ └── jzoffer │ │ │ └── package-info.java │ │ ├── basics │ │ ├── package-info.java │ │ ├── FinalTest.java │ │ ├── PolymorphicTest.java │ │ ├── PackagingTest.java │ │ ├── AbstractTest.java │ │ ├── ExtendTest.java │ │ ├── SuperTest.java │ │ ├── ForTest.java │ │ ├── User.java │ │ ├── ExtendsTest2.java │ │ ├── StaticTest.java │ │ ├── ServletTest.java │ │ └── ReflectTest2.java │ │ ├── design │ │ ├── proxy │ │ │ └── package-info.java │ │ ├── adapter │ │ │ ├── package-info.java │ │ │ └── AdapterTest.java │ │ ├── bridge │ │ │ ├── package-info.java │ │ │ └── BridgeTest.java │ │ ├── builder │ │ │ └── package-info.java │ │ ├── command │ │ │ └── package-info.java │ │ ├── facade │ │ │ ├── package-info.java │ │ │ └── FacadeTest.java │ │ ├── filter │ │ │ └── package-info.java │ │ ├── strategy │ │ │ └── package-info.java │ │ ├── template │ │ │ └── package-info.java │ │ ├── visitor │ │ │ └── package-info.java │ │ ├── composite │ │ │ ├── package-info.java │ │ │ └── CompositeTest.java │ │ ├── decorator │ │ │ └── package-info.java │ │ ├── flyweight │ │ │ └── package-info.java │ │ ├── iterator │ │ │ └── package-info.java │ │ ├── mediator │ │ │ └── package-info.java │ │ ├── state │ │ │ └── package-info.java │ │ ├── interpreter │ │ │ ├── package-info.java │ │ │ └── InterpreterTest.java │ │ ├── memento │ │ │ └── package-info.java │ │ ├── observer │ │ │ └── package-info.java │ │ ├── nullobject │ │ │ ├── package-info.java │ │ │ └── NullObjectTest.java │ │ ├── responsibility │ │ │ └── package-info.java │ │ ├── prototype │ │ │ ├── package-info.java │ │ │ └── PrototypeTest.java │ │ ├── factory │ │ │ └── package-info.java │ │ ├── singleton │ │ │ └── package-info.java │ │ └── package-info.java │ │ ├── question │ │ ├── package-info.java │ │ ├── QuestionTest3.java │ │ ├── QuestionTest2.java │ │ └── QuestionTest1.java │ │ ├── thread │ │ ├── package-info.java │ │ ├── test │ │ │ ├── package-info.java │ │ │ ├── MyThread.java │ │ │ ├── TheadTest3.java │ │ │ ├── ThreadTest6.java │ │ │ ├── Test22.java │ │ │ ├── threadTest2.java │ │ │ ├── YieldTest.java │ │ │ ├── executorTest.java │ │ │ ├── MyRunnable.java │ │ │ ├── PriorityTest.java │ │ │ ├── NotifyTest.java │ │ │ ├── JoinTest.java │ │ │ ├── ThreadTest1.java │ │ │ ├── ThreadTest4.java │ │ │ ├── threadPrinter.java │ │ │ └── Test.java │ │ ├── lock │ │ │ ├── package-info.java │ │ │ ├── LockTest2.java │ │ │ └── LockTest1.java │ │ └── concurrent │ │ │ ├── package-info.java │ │ │ └── liveLock │ │ │ ├── package-info.java │ │ │ ├── test.java │ │ │ ├── Producer.java │ │ │ ├── Consumer.java │ │ │ └── Drop.java │ │ ├── commons │ │ ├── google │ │ │ ├── package-info.java │ │ │ └── GoogleTest.java │ │ ├── others │ │ │ └── package-info.java │ │ ├── package-info.java │ │ └── apache │ │ │ ├── package-info.java │ │ │ └── CompressTest.java │ │ ├── elasticsearch │ │ └── package-info.java │ │ ├── ftp │ │ └── package-info.java │ │ ├── excel │ │ ├── package-info.java │ │ └── DemoData.java │ │ ├── ffmpeg │ │ ├── package-info.java │ │ ├── FFmpegTest.java │ │ └── FFmpegUtil.java │ │ ├── jdk8 │ │ └── package-info.java │ │ └── App.java └── test │ └── java │ └── com │ └── pancm │ └── AppTest.java ├── .github └── workflows │ └── maven.yml └── .gitignore /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 消息中间件的一些类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.mq; -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: nio 相关的代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.nio; -------------------------------------------------------------------------------- /src/main/java/com/pancm/utils/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 一些工具类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.utils; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 大数据相关代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.bigdata; -------------------------------------------------------------------------------- /src/main/java/com/pancm/code/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 源码相关类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年11月29日 7 | */ 8 | package com.pancm.code; -------------------------------------------------------------------------------- /src/main/java/com/pancm/others/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 一些其他的测试代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.others; -------------------------------------------------------------------------------- /src/main/java/com/pancm/pojo/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 一些pojo类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2017年11月7日 7 | */ 8 | package com.pancm.pojo; -------------------------------------------------------------------------------- /src/main/java/com/pancm/redis/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: redis 相关代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.redis; -------------------------------------------------------------------------------- /src/main/java/com/pancm/sql/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 数据库相关的代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.sql; -------------------------------------------------------------------------------- /src/main/java/com/pancm/arithmetic/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 算法相关类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月14日 7 | */ 8 | package com.pancm.arithmetic; -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: Java 基础知识的相关代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.basics; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/proxy/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 代理模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.proxy; -------------------------------------------------------------------------------- /src/main/java/com/pancm/question/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 一些面试可能会问到的题型 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.question; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/adapter/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 适配器模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.adapter; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/bridge/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 桥接模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.bridge; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/builder/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description:建造者模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月7日 7 | */ 8 | package com.pancm.design.builder; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/command/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 命令模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.command; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/facade/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 外观模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.facade; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/filter/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 过滤器模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.filter; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/strategy/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 策略模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.strategy; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/template/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 模板模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.template; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/visitor/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 访问者模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.visitor; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * Title: package-info 3 | * Description: kafka的相关代码 4 | * Version:1.0.0 5 | * @author pancm 6 | * @date 2018年1月11日 7 | */ 8 | package com.pancm.mq.kafka; -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 4 | * 线程相关的测试类 5 | * Version:1.0.0 6 | * @author pancm 7 | * @date 2018年3月1日 8 | */ 9 | package com.pancm.thread; -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 线程相关的一些类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.thread.test; -------------------------------------------------------------------------------- /src/main/java/com/pancm/arithmetic/jzoffer/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @description: 剑指 Offer 中的题目 3 | * @author: Zhoust 4 | * @date: 2019/04/28 10:57 5 | * @version: V1.0 6 | */ 7 | package com.pancm.arithmetic.jzoffer; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/hbase/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: hbase相关的代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.bigdata.hbase; -------------------------------------------------------------------------------- /src/main/java/com/pancm/commons/google/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 谷歌的相关测试代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.commons.google; -------------------------------------------------------------------------------- /src/main/java/com/pancm/commons/others/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 其它的工具包测试 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月21日 7 | */ 8 | package com.pancm.commons.others; -------------------------------------------------------------------------------- /src/main/java/com/pancm/commons/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 这里的commons指第三方的一些工具测试类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.commons; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/composite/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 组合模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.composite; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/decorator/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 装饰器模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.decorator; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/flyweight/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 享元模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.flyweight; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/iterator/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 迭代器模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.iterator; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/mediator/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 中介者模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.mediator; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/state/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 状态模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.state; -------------------------------------------------------------------------------- /src/main/java/com/pancm/elasticsearch/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: es 相关测试类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2019年2月28日 7 | */ 8 | package com.pancm.elasticsearch; -------------------------------------------------------------------------------- /src/main/java/com/pancm/ftp/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: pancm_project 3 | * @Description: ftp的工具类 4 | * @Version:1.0.0 5 | * @Since:jdk1.8 6 | * @author pancm 7 | * @date 2021/1/26 8 | */ 9 | package com.pancm.ftp; -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/lock/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 一些锁的测试代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2017年11月7日 7 | */ 8 | package com.pancm.thread.lock; -------------------------------------------------------------------------------- /src/main/java/com/pancm/commons/apache/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: apache相关的工具类 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.commons.apache; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/interpreter/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 解释器模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.interpreter; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/memento/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 备忘录模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.memento; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/observer/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 观察者模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.observer; -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/concurrent/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 并发相关的测试代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年9月20日 7 | */ 8 | package com.pancm.thread.concurrent; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/zookeeper/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: zookeeper相关代码 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年4月28日 7 | */ 8 | package com.pancm.bigdata.zookeeper; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/nullobject/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 空对象模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.nullobject; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/responsibility/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 责任链模式 4 | * @Version:1.0.0 5 | * @author pancm 6 | * @date 2018年8月8日 7 | */ 8 | package com.pancm.design.responsibility; -------------------------------------------------------------------------------- /src/main/java/com/pancm/excel/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: pancm_project 3 | * @Description: excel的工具类 4 | * @Version:1.0.0 5 | * @Since:jdk1.8 6 | * @author pancm 7 | * @date 2021/1/26 8 | */ 9 | package com.pancm.excel; -------------------------------------------------------------------------------- /src/main/java/com/pancm/ffmpeg/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: pancm_project 3 | * @Description: ffmpeg的工具类 4 | * @Version:1.0.0 5 | * @Since:jdk1.8 6 | * @author pancm 7 | * @date 2021/1/26 8 | */ 9 | package com.pancm.ffmpeg; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/prototype/package-info.java: -------------------------------------------------------------------------------- 1 | 2 | /** 3 | * @Title: package-info 4 | * @Description: 5 | * 原型模式 6 | * @Version:1.0.0 7 | * @author pancm 8 | * @date 2018年8月7日 9 | */ 10 | package com.pancm.design.prototype; -------------------------------------------------------------------------------- /src/main/java/com/pancm/jdk8/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * @Title: package-info 6 | * @Description: 7 | * jdk1.8测试用例 8 | * @Version:1.0.0 9 | * @author pancm 10 | * @date 2018年5月14日 11 | */ 12 | package com.pancm.jdk8; -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: Mina测试 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017-3-27 10 | */ 11 | package com.pancm.nio.mina; -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: Netty 测试 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017-8-31 10 | */ 11 | package com.pancm.nio.netty; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/test3/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2018年3月15日 10 | */ 11 | package com.pancm.mq.kafka.test3; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/one/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年12月28日 10 | */ 11 | package com.pancm.bigdata.storm.one; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: strom相关代码 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2018年1月11日 10 | */ 11 | package com.pancm.bigdata.storm; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/factory/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 工厂测试 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年10月13日 10 | */ 11 | package com.pancm.design.factory; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/examples/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年12月29日 10 | */ 11 | package com.pancm.mq.kafka.examples; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/others/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年12月29日 10 | */ 11 | package com.pancm.mq.kafka.others; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2018年3月15日 10 | */ 11 | package com.pancm.bigdata.storm.test; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test2/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2018年3月15日 10 | */ 11 | package com.pancm.bigdata.storm.test2; -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/singleton/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 单例模式测试 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年11月7日 10 | */ 11 | package com.pancm.design.singleton; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: rabbitMq 消息队列测试 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年11月7日 10 | */ 11 | package com.pancm.mq.rabbitmq; -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo6/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: Http服务测试 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年10月26日 10 | */ 11 | package com.pancm.nio.netty.demo6; -------------------------------------------------------------------------------- /src/main/java/com/pancm/App.java: -------------------------------------------------------------------------------- 1 | package com.pancm; 2 | 3 | /** 4 | * Hello world! 5 | * 6 | */ 7 | public class App 8 | { 9 | public static void main( String[] args ) 10 | { 11 | System.out.println( "Hello World!" ); 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年12月28日 10 | */ 11 | package com.pancm.bigdata.storm.example; -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example1/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * Version:1.0.0 8 | * @author pancm 9 | * @date 2017年12月29日 10 | */ 11 | package com.pancm.bigdata.storm.example1; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/test2/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * kafka消费者 8 | * Version:1.0.0 9 | * @author pancm 10 | * @date 2018年2月9日 11 | */ 12 | package com.pancm.mq.kafka.test2; -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/test1/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * kafka demo 8 | * Version:1.0.0 9 | * @author pancm 10 | * @date 2018年2月9日 11 | */ 12 | package com.pancm.mq.kafka.test1; -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/concurrent/liveLock/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | /** 5 | * Title: package-info 6 | * Description: 7 | * 活锁测试 8 | * 一个线程常常处于响应另一个线程的动作,如果其他线程也常常处于该线程的动作,那么就可能出现活锁。 9 | * Version:1.0.0 10 | * @author pancm 11 | * @date 2018年3月8日 12 | */ 13 | package com.pancm.thread.concurrent.liveLock; -------------------------------------------------------------------------------- /.github/workflows/maven.yml: -------------------------------------------------------------------------------- 1 | name: Java CI 2 | 3 | on: [push] 4 | 5 | jobs: 6 | build: 7 | 8 | runs-on: ubuntu-latest 9 | 10 | steps: 11 | - uses: actions/checkout@v1 12 | - name: Set up JDK 1.8 13 | uses: actions/setup-java@v1 14 | with: 15 | java-version: 1.8 16 | - name: Build with Maven 17 | run: mvn -B package --file pom.xml 18 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/examples/KafkaProducerConsumerDemo.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.examples; 2 | 3 | public class KafkaProducerConsumerDemo { 4 | 5 | public static final String KAFKASTR = "master:9092"; 6 | 7 | public static void main(String[] args) { 8 | new Producer(KAFKASTR, "pcm_test1").start(); // args[0] 为要发送的 topic 9 | // new Consumer(KAFKASTR, "pcm_test1").start(); // args[0] 为要接收的 topic 10 | } 11 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/excel/DemoData.java: -------------------------------------------------------------------------------- 1 | package com.pancm.excel; 2 | 3 | import lombok.Data; 4 | import lombok.EqualsAndHashCode; 5 | 6 | import java.util.Date; 7 | 8 | /** 9 | * @author pancm 10 | * @Title: pancm_project 11 | * @Description: 12 | * @Version:1.0.0 13 | * @Since:jdk1.8 14 | * @date 2023/3/23 15 | */ 16 | @Data 17 | @EqualsAndHashCode 18 | public class DemoData { 19 | private String string; 20 | private Date date; 21 | private Double doubleData; 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/concurrent/liveLock/test.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.concurrent.liveLock; 2 | 3 | 4 | 5 | /** 6 | * 7 | * Title: 8 | * Description: 9 | * 多线程共享测试 10 | * Version:1.0.0 11 | * @author pancm 12 | * @date 2018年3月8日 13 | */ 14 | public class test{ 15 | 16 | public static void main(String[] args) { 17 | Drop drop=new Drop(); 18 | (new Thread(new Producer(drop))).start(); 19 | (new Thread(new Consumer(drop))).start(); 20 | } 21 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/MyThread.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | /** 3 | * @author ZERO 4 | * @Data 2017-5-24 下午2:20:29 5 | * @Description 6 | */ 7 | public class MyThread extends Thread{ 8 | 9 | private int i = 0; 10 | 11 | @Override 12 | public void run() { 13 | for (i = 0; i < 10; i++) { 14 | System.out.println("MyThread:"+Thread.currentThread().getName() + "第" + i+ "次"); 15 | } 16 | } 17 | 18 | 19 | 20 | 21 | } 22 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo1/BaseClient2Handler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo1; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | 6 | /** 7 | * 8 | * Title: BaseClient2Handler 9 | * Description: 客户端自定义解码器其二 10 | * Version:1.0.0 11 | * @author panchengming 12 | * @date 2017年9月17日 13 | */ 14 | public class BaseClient2Handler extends ChannelInboundHandlerAdapter{ 15 | 16 | @Override 17 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 18 | System.out.println("BaseClient2Handler Active"); 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/code/MapCodeTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.code; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | /** 7 | * @Title: MapCodeTest 8 | * @Description: Map源码学习相关类 9 | * @Version:1.0.0 10 | * @author pancm 11 | * @date 2018年11月29日 12 | */ 13 | public class MapCodeTest { 14 | 15 | /** 16 | * @param args 17 | */ 18 | public static void main(String[] args) { 19 | test1(); 20 | } 21 | 22 | 23 | /** 24 | * 25 | */ 26 | private static void test1() { 27 | Map map =new HashMap<>(); 28 | map.put("1", 1); 29 | map.put("2", 2); 30 | } 31 | } 32 | 33 | 34 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | /target/ 2 | /classes/ 3 | /log/ 4 | /logs/ 5 | .classpath 6 | .project 7 | .settings 8 | .myeclipse 9 | ##filter databfile��sln file## 10 | *.mdb 11 | *.ldb 12 | *.sln 13 | ##class file## 14 | *.com 15 | *.class 16 | *.dll 17 | *.exe 18 | *.o 19 | *.so 20 | # compression file 21 | *.7z 22 | *.dmg 23 | *.gz 24 | *.iso 25 | *.jar 26 | *.rar 27 | *.tar 28 | *.zip 29 | *.via 30 | *.iml 31 | *.tmp 32 | *.err 33 | *.log 34 | # OS generated files # 35 | /.idea 36 | .DS_Store 37 | .DS_Store? 38 | ._* 39 | .Spotlight-V100 40 | .Trashes 41 | Icon? 42 | ehthumbs.db 43 | Thumbs.db 44 | /.github/ 45 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/question/QuestionTest3.java: -------------------------------------------------------------------------------- 1 | package com.pancm.question; 2 | 3 | /** 4 | * @Title: QuestionTest1 5 | * @Description: 6 | * @Version:1.0.0 7 | * @author pancm 8 | * @date 2017年7月21日 9 | */ 10 | public class QuestionTest3 { 11 | 12 | 13 | /** 14 | * @param args 15 | */ 16 | public static void main(String[] args) { 17 | /* 18 | * 请实现字符串反转,也就是 输入 abc,输出 cba 19 | */ 20 | String str="hello xuwujing"; 21 | System.out.println(reverseString(str)); 22 | } 23 | 24 | public static String reverseString(String str){ 25 | if(str==null||str.length()<=1){ 26 | return str; 27 | } 28 | return reverseString(str.substring(1))+str.charAt(0); 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/TheadTest3.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | public class TheadTest3 { 4 | 5 | public static void main(String[] args) throws InterruptedException { 6 | MyRunnable myRunnable=new MyRunnable(); 7 | for(int i=1;i<=5;i++){ 8 | Thread thread=new Thread(myRunnable); 9 | thread.setName("myRunnable-"+i); 10 | thread.start(); 11 | } 12 | Thread.sleep(2000); 13 | myRunnable.set(true); 14 | Thread.sleep(3000); 15 | myRunnable.set(false); 16 | for(int i=1;i<=5;i++){ 17 | MyThread myThread=new MyThread(); 18 | myThread.setName("myThread-"+i); 19 | myThread.start(); 20 | } 21 | 22 | 23 | System.out.println("结束..."); 24 | } 25 | 26 | 27 | 28 | } 29 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo3/NettyClientHandlerDemo3.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo3; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | 6 | /** 7 | * 8 | * Description: 9 | * Version:1.0.0 10 | * @author pancm 11 | * @date 2017年9月21日 12 | */ 13 | public class NettyClientHandlerDemo3 extends ChannelInboundHandlerAdapter { 14 | 15 | /** 16 | * 连接时发送消息 17 | */ 18 | @Override 19 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 20 | NettyMsg customMsg = new NettyMsg((byte)0xAB, (byte)0xCD, "Hello,Netty".length(), "Hello,Netty"); 21 | ctx.writeAndFlush(customMsg); 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo4/NettyClientHandlerDemo4.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo4; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | 6 | /** 7 | * 8 | * Description: 9 | * Version:1.0.0 10 | * @author pancm 11 | * @date 2017年9月21日 12 | */ 13 | public class NettyClientHandlerDemo4 extends ChannelInboundHandlerAdapter { 14 | 15 | /** 16 | * 连接时发送消息 17 | */ 18 | @Override 19 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 20 | NettySendBody nst = new NettySendBody(); 21 | nst.put("1111", "2222"); 22 | ctx.writeAndFlush(nst); 23 | System.out.println(nst); 24 | } 25 | 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo3/NettyServerHandlerDemo3.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo3; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.SimpleChannelInboundHandler; 5 | 6 | /** 7 | * 8 | * Description:服务端业务逻辑处理类 9 | * Version:1.0.0 10 | * @author pancm 11 | * @date 2017年9月21日 12 | */ 13 | public class NettyServerHandlerDemo3 extends SimpleChannelInboundHandler { 14 | 15 | @Override 16 | protected void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception { 17 | if(msg instanceof NettyMsg) { 18 | NettyMsg customMsg = (NettyMsg)msg; 19 | System.out.println("接受的数据:"+ctx.channel().remoteAddress()+" send "+customMsg.getBody()); 20 | } 21 | 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/ThreadTest6.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import java.util.ArrayList; 4 | import java.util.HashMap; 5 | import java.util.List; 6 | import java.util.Map; 7 | 8 | /** 9 | * @Title: ThreadTest6 10 | * @Description: 11 | * @Version:1.0.0 12 | * @author pancm 13 | * @date 2018年7月23日 14 | */ 15 | public class ThreadTest6 { 16 | 17 | 18 | /** 19 | * @param args 20 | */ 21 | public static void main(String[] args) { 22 | Map map=new HashMap(); 23 | List l=new ArrayList<>(); 24 | Thread99 t9=new Thread99(); 25 | Thread t=new Thread(t9); 26 | 27 | } 28 | } 29 | 30 | 31 | 32 | 33 | class Thread99 implements Runnable{ 34 | 35 | @Override 36 | public void run() { 37 | System.out.println("===="); 38 | } 39 | } 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /src/test/java/com/pancm/AppTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm; 2 | 3 | import junit.framework.Test; 4 | import junit.framework.TestCase; 5 | import junit.framework.TestSuite; 6 | 7 | /** 8 | * Unit test for simple App. 9 | */ 10 | public class AppTest 11 | extends TestCase 12 | { 13 | /** 14 | * Create the test case 15 | * 16 | * @param testName name of the test case 17 | */ 18 | public AppTest( String testName ) 19 | { 20 | super( testName ); 21 | } 22 | 23 | /** 24 | * @return the suite of tests being tested 25 | */ 26 | public static Test suite() 27 | { 28 | return new TestSuite( AppTest.class ); 29 | } 30 | 31 | /** 32 | * Rigourous Test :-) 33 | */ 34 | public void testApp() 35 | { 36 | assertTrue( true ); 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo1/BaseClient1Handler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo1; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | 6 | /** 7 | * 8 | * Title: BaseClient1Handler 9 | * Description: 客户端自定义解码器其一 10 | * Version:1.0.0 11 | * @author panchengming 12 | * @date 2017年9月17日 13 | */ 14 | public class BaseClient1Handler extends ChannelInboundHandlerAdapter{ 15 | @Override 16 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 17 | System.out.println("BaseClient1Handler channelActive"); 18 | // ctx.fireChannelActive(); 19 | } 20 | 21 | @Override 22 | public void channelInactive(ChannelHandlerContext ctx) throws Exception { 23 | System.out.println("BaseClient1Handler channelInactive"); 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/FinalTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | import java.util.Date; 4 | 5 | 6 | /** 7 | * 8 | * Title: FinalTest 9 | * Description: 10 | * final测试 11 | * Version:1.0.0 12 | * @author pancm 13 | * @date 2018年3月21日 14 | */ 15 | public class FinalTest{ 16 | //定义一个final修饰的变量 17 | public static final String name="xuwujing"; 18 | 19 | public static void main(String[] args) { 20 | //这句会报错 因为该变量已经被final修饰了 21 | // name="张三"; 22 | } 23 | //类加上final之后,该类是无法被继承的 24 | final class Test2{ 25 | } 26 | //这句会报错,因为Test2是被final修饰的类 27 | // class Test3 extends Test2{ 28 | // } 29 | 30 | class Test4{ 31 | //定义一个被final修饰的方法 32 | final Date getTime(){ 33 | return new Date(); 34 | } 35 | } 36 | 37 | class Test5 extends Test4{ 38 | //这句会报错,因为final方法是不能被子类修改的。 39 | // Date getTime(){ 40 | // return new Date(); 41 | // } 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/Test22.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | 7 | public class Test22 { 8 | 9 | public static void main(String[] args) { 10 | Map map=new HashMap(); 11 | map.put(0, 0); 12 | map.put(1, 1); 13 | for(Integer type:map.keySet()){ 14 | Thread3 t3=new Thread3(type); 15 | t3.start(); 16 | } 17 | } 18 | } 19 | 20 | class Thread3 extends Thread{ 21 | 22 | private int type; 23 | 24 | public Thread3(int type){ 25 | this.type=type; 26 | } 27 | 28 | @Override 29 | public void run() { 30 | if(type==0){ 31 | //连接mysql 32 | System.out.println("线程ID:"+getId()+"连接mysql"); 33 | }else if(type==1){ 34 | //连接oracle 35 | System.out.println("线程ID:"+getId()+"连接oracle"); 36 | } 37 | } 38 | 39 | 40 | 41 | 42 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo1/MinaClientHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo1; 2 | 3 | import org.apache.log4j.Logger; 4 | import org.apache.mina.core.service.IoHandlerAdapter; 5 | import org.apache.mina.core.session.IoSession; 6 | 7 | /** 8 | * @author ZERO 9 | * @version 2017-3-27 下午6:01:31 10 | * 业务逻辑过滤器代码 11 | */ 12 | public class MinaClientHandler extends IoHandlerAdapter { 13 | private static Logger logger = Logger.getLogger(MinaClientHandler.class); 14 | 15 | @Override 16 | public void messageReceived(IoSession session, Object message) 17 | throws Exception { 18 | String msg = message.toString(); 19 | logger.info("客户端接收到的信息为:" + msg); 20 | } 21 | 22 | @Override 23 | public void exceptionCaught(IoSession session, Throwable cause) 24 | throws Exception { 25 | logger.error("客户端发生异常...", cause); 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/PolymorphicTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * 5 | * @Title: PolymorphicTest 6 | * @Description: 多态测试 7 | * @Version:1.0.0 8 | * @author pancm 9 | * @date 2018年3月27日 10 | */ 11 | public class PolymorphicTest { 12 | 13 | public static void main(String[] args) { 14 | Animal2 animal = new Cat2(); 15 | animal.eat(); 16 | } 17 | } 18 | 19 | class Animal2 { 20 | private String name = "Animal"; 21 | 22 | public void eat() { 23 | System.out.println(name + "正在吃东西..."); 24 | sleep(); 25 | } 26 | 27 | public void sleep() { 28 | System.out.println(name + "正在睡觉..."); 29 | } 30 | } 31 | 32 | class Cat2 extends Animal2 { 33 | private String name = "Cat"; 34 | 35 | public void eat(String name) { 36 | System.out.println(name + "吃完了"); 37 | sleep(); 38 | } 39 | 40 | public void sleep() { 41 | System.out.println(name + "正在睡觉"); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/threadTest2.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import org.junit.Test; 4 | 5 | /** 6 | * @author ZERO 7 | * @Data 2017-5-18 上午9:47:55 8 | * @Description 线程测试 9 | */ 10 | public class threadTest2 { 11 | 12 | /** 13 | * @param args 14 | */ 15 | public static void main(String[] args) { 16 | 17 | 18 | } 19 | 20 | @Test 21 | public void createThread1(){ 22 | Thread t1 = new Thread(){ 23 | public void run(){ 24 | System.out.println("创建线程的方式1"); 25 | } 26 | }; 27 | t1.start(); 28 | } 29 | 30 | @Test 31 | public void createThread2(){ 32 | Thread t2 = new Thread(new Runnable(){ 33 | @Override 34 | public void run() { 35 | System.out.println("创建线程的方式2"); 36 | } 37 | 38 | }); 39 | t2.start(); 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/YieldTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | /** 4 | * @Title: YaildTest 5 | * @Description: 线程中的 Yaild方法测试 6 | * @Version:1.0.0 7 | * @author pancm 8 | * @date 2018年5月22日 9 | */ 10 | public class YieldTest { 11 | public static void main(String[] args) { 12 | Test1 t1 = new Test1("张三"); 13 | Test1 t2 = new Test1("李四"); 14 | 15 | new Thread(t1).start(); 16 | new Thread(t2).start(); 17 | } 18 | } 19 | 20 | class Test1 implements Runnable { 21 | private String name; 22 | public Test1(String name) { 23 | this.name=name; 24 | } 25 | @Override 26 | public void run() { 27 | System.out.println(name + " 线程运行开始!"); 28 | for (int i = 1; i <= 5; i++) { 29 | System.out.println("子线程"+name+ "运行 : " + i); 30 | // 当为3的时候,让出资源 31 | if (i == 3) { 32 | Thread.yield(); 33 | } 34 | } 35 | System.out.println(name + " 线程运行结束!"); 36 | } 37 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/concurrent/liveLock/Producer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.concurrent.liveLock; 2 | 3 | import java.util.Random; 4 | 5 | /** 6 | * 7 | * Title: Producer 8 | * Description: 9 | * 消息生产者 10 | * Version:1.0.0 11 | * @author pancm 12 | * @date 2018年3月8日 13 | */ 14 | public class Producer implements Runnable { 15 | private Drop drop; 16 | public Producer(Drop drop) { 17 | this.drop = drop; 18 | } 19 | 20 | public void run() { 21 | String importantInfo[] = { "第一条数据", "第二条数据", "第三条数据", 22 | "第四条数据" }; 23 | Random random = new Random(); 24 | for (int i = 0; i < importantInfo.length; i++) { 25 | drop.put(importantInfo[i]); 26 | try { 27 | Thread.sleep(random.nextInt(1000)); 28 | } catch (InterruptedException e) { 29 | } 30 | } 31 | //表示已经发送完 32 | drop.put("DONE"); 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/PackagingTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * 5 | * @Title: PackagingTest 6 | * @Description: 7 | * 封装 8 | * @Version:1.0.0 9 | * @author pancm 10 | * @date 2018年3月27日 11 | */ 12 | public class PackagingTest { 13 | 14 | public static void main(String[] args) { 15 | User9 user=new User9(); 16 | //这里会报错,因为id和name是私有的,用于保护该数据 17 | // user.id=10; 18 | // user.name="张三"; 19 | user.setId(1); 20 | user.setName("张三"); 21 | System.out.println(user.getId()); 22 | System.out.println(user.getName()); 23 | } 24 | 25 | } 26 | 27 | class User9{ 28 | private int id; 29 | private String name; 30 | public int getId() { 31 | return id; 32 | } 33 | public void setId(int id) { 34 | this.id = id; 35 | } 36 | public String getName() { 37 | return name; 38 | } 39 | public void setName(String name) { 40 | this.name = name; 41 | } 42 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/pojo/Student.java: -------------------------------------------------------------------------------- 1 | package com.pancm.pojo; 2 | 3 | import lombok.AllArgsConstructor; 4 | import lombok.Data; 5 | import lombok.NoArgsConstructor; 6 | import lombok.ToString; 7 | import lombok.extern.log4j.Log4j; 8 | 9 | /** 10 | * 11 | * Title: Class 12 | * Description: 13 | * 学生信息表 14 | * Version:1.0.0 15 | * @author pancm 16 | * @date 2018年1月11日 17 | */ 18 | /*@Data :注解在类上;提供类所有属性的 getting 和 setting 方法,此外还提供了equals、canEqual、hashCode、toString 方法 19 | @Setter:注解在属性上;为属性提供 setting 方法 20 | @Getter:注解在属性上;为属性提供 getting 方法 21 | @Log4j :注解在类上;为类提供一个 属性名为log 的 log4j 日志对象 22 | @NoArgsConstructor:注解在类上;为类提供一个无参的构造方法 23 | @AllArgsConstructor:注解在类上;为类提供一个全参的构造方法*/ 24 | @Data 25 | @Log4j 26 | @NoArgsConstructor 27 | @AllArgsConstructor 28 | @ToString(exclude = {"id","name"}) 29 | @SuppressWarnings("unused") 30 | public class Student { 31 | /** 学生id */ 32 | private int id; 33 | /** 学生姓名 */ 34 | private String name; 35 | /** 班级ID */ 36 | private int classId; 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/executorTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import java.util.concurrent.Executors; 4 | import java.util.concurrent.ScheduledExecutorService; 5 | import java.util.concurrent.ScheduledFuture; 6 | import java.util.concurrent.TimeUnit; 7 | 8 | /** 9 | * 10 | * Title: executorTest 11 | * Description:线程池 12 | * Version:1.0.0 13 | * @author pancm 14 | * @date 2017年11月20日 15 | */ 16 | public class executorTest { 17 | 18 | public static void main(String[] args) { 19 | //创建一个其线程池具有 10 个线程的ScheduledExecutorService 20 | ScheduledExecutorService executor =Executors.newScheduledThreadPool(10); 21 | System.out.println("开始..."); 22 | //创建一个 Runnable,以供调度稍后执行 23 | ScheduledFuture future = executor.schedule( 24 | new Runnable() { 25 | @Override 26 | public void run() { 27 | System.out.println("30 seconds later"); 28 | } 29 | }, 30, TimeUnit.SECONDS); //调度任务在从现在开始的 60 秒之后执行 30 | executor.shutdown(); //执行完毕,释放资源 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo2/NettyServerHandlerDemo2.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo2; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | 6 | /** 7 | * 8 | * Title: NettyServerHandlerDemo2 9 | * Description: Netty服务端业务逻辑处理 用于测试粘包、拆包 10 | * Version:1.0.0 11 | * @author pancm 12 | * @date 2017年9月20日 13 | */ 14 | public class NettyServerHandlerDemo2 extends ChannelInboundHandlerAdapter{ 15 | 16 | 17 | private int counter; 18 | 19 | @Override 20 | public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception { 21 | 22 | String body = (String)msg; 23 | System.out.println("接受的数据是: " + body + ";条数是: " + ++counter); 24 | } 25 | 26 | 27 | @Override 28 | public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception { 29 | cause.printStackTrace(); 30 | ctx.close(); 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo/NettyClientHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.SimpleChannelInboundHandler; 5 | 6 | /** 7 | * 8 | * Title: NettyClientHandler 9 | * Description: 客户端业务逻辑实现 10 | * Version:1.0.0 11 | * @author Administrator 12 | * @date 2017-8-31 13 | */ 14 | public class NettyClientHandler extends SimpleChannelInboundHandler { 15 | 16 | @Override 17 | protected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception { 18 | System.out.println("客户端接受的消息: " + msg); 19 | } 20 | 21 | // 22 | @Override 23 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 24 | System.out.println("正在连接... "); 25 | super.channelActive(ctx); 26 | } 27 | 28 | @Override 29 | public void channelInactive(ChannelHandlerContext ctx) throws Exception { 30 | System.out.println("连接关闭! "); 31 | super.channelInactive(ctx); 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo3/NettyEncoder.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo3; 2 | 3 | import java.nio.charset.Charset; 4 | 5 | import io.netty.buffer.ByteBuf; 6 | import io.netty.channel.ChannelHandlerContext; 7 | import io.netty.handler.codec.MessageToByteEncoder; 8 | 9 | /** 10 | * 11 | * Description:Netty自定义编码器 12 | * Version:1.0.0 13 | * @author pancm 14 | * @date 2017年9月21日 15 | */ 16 | public class NettyEncoder extends MessageToByteEncoder { 17 | 18 | @Override 19 | protected void encode(ChannelHandlerContext ctx, NettyMsg msg, ByteBuf out) throws Exception { 20 | if(null == msg){ 21 | throw new Exception("消息不能为空!"); 22 | } 23 | 24 | String body = msg.getBody(); 25 | byte[] bodyBytes = body.getBytes(Charset.forName("utf-8")); 26 | out.writeByte(msg.getType()); 27 | out.writeByte(msg.getFlag()); 28 | out.writeInt(bodyBytes.length); 29 | out.writeBytes(bodyBytes); 30 | 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/package-info.java: -------------------------------------------------------------------------------- 1 | /** 2 | * @Title: package-info 3 | * @Description: 设计模式相关测试代码 4 | 设计模式有23种类型。按照主要分类可以分为三大类: 5 | 6 | 一、创建型模式 7 | 8 | 这些设计模式提供了一种在创建对象的同时隐藏创建逻辑的方式,而不是使用 new运算符直接实例化对象。这使得程序在判断针对某个给定实例需要创建哪些对象时更加灵活。 9 | 10 | 单例模式 11 | 工厂模式 12 | 抽象工厂模式 13 | 建造者模式 14 | 原型模式 15 | 二、结构型模式 16 | 17 | 这些设计模式关注类和对象的组合。继承的概念被用来组合接口和定义组合对象获得新功能的方式。 18 | 19 | 适配器模式 20 | 桥接模式 21 | 过滤器模式 22 | 组合模式 23 | 装饰器模式 24 | 外观模式 25 | 享元模式 26 | 代理模式 27 | 三、行为型模式 28 | 29 | 这些设计模式特别关注对象之间的通信。 30 | 31 | 责任链模式 32 | 命令模式 33 | 解释器模式 34 | 迭代器模式 35 | 中介者模式 36 | 备忘录模式 37 | 观察者模式 38 | 状态模式 39 | 空对象模式 40 | 策略模式 41 | 模板模式 42 | 访问者模式 43 | 44 | 45 | 设计模式的原则 46 | 设计模式的六大原则 47 | 开闭原则:对扩展开放,对修改关闭。 48 | 里氏代换原则:对开闭原则的补充。任何基类可以出现的地方,子类一定可以出现。LSP 是继承复用的基石,只有当派生类可以替换掉基类,且软件单位的功能不受到影响时,基类才能真正被复用,而派生类也能够在基类的基础上增加新的行为。 49 | 依赖倒转原则:针对接口编程,依赖于抽象而不依赖于具体。 50 | 接口隔离原则:尽量使用多个隔离的接口,为了降低类之间的耦合度。 51 | 迪米特法则:一个实体应当尽量少地与其他实体之间发生相互作用,使得系统功能模块相对独立。 52 | 合成复用原则:尽量使用合成/聚合的方式,而不是使用继承。 53 | 54 | 55 | 56 | * @Version:1.0.0 57 | * @author pancm 58 | * @date 2018年7月7日 59 | */ 60 | package com.pancm.design; -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo1/NettyClientHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo1; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.SimpleChannelInboundHandler; 5 | 6 | /** 7 | * 8 | * Title: NettyClientHandler 9 | * Description:客户端业务逻辑 10 | * Version:1.0.0 11 | * @author Administrator 12 | * @date 2017-8-31 13 | */ 14 | public class NettyClientHandler extends SimpleChannelInboundHandler { 15 | 16 | @Override 17 | protected void channelRead0(ChannelHandlerContext chc, String str) 18 | throws Exception { 19 | // TODO Auto-generated method stub 20 | System.out.println("消息为:"+str); 21 | 22 | } 23 | 24 | @Override 25 | public void channelActive(ChannelHandlerContext chc) throws Exception { 26 | System.out.println("正在连接..."); 27 | super.channelActive(chc); 28 | } 29 | 30 | @Override 31 | public void channelInactive(ChannelHandlerContext chc) throws Exception { 32 | System.out.println("连接关闭"); 33 | super.channelInactive(chc); 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo/NettyClientFilter.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo; 2 | 3 | 4 | import io.netty.channel.ChannelInitializer; 5 | import io.netty.channel.ChannelPipeline; 6 | import io.netty.channel.socket.SocketChannel; 7 | import io.netty.handler.codec.string.StringDecoder; 8 | import io.netty.handler.codec.string.StringEncoder; 9 | /** 10 | * 11 | * Title: NettyClientFilter 12 | * Description: Netty客户端 过滤器 13 | * Version:1.0.0 14 | * @author Administrator 15 | * @date 2017-8-31 16 | */ 17 | public class NettyClientFilter extends ChannelInitializer { 18 | 19 | @Override 20 | protected void initChannel(SocketChannel ch) throws Exception { 21 | ChannelPipeline ph = ch.pipeline(); 22 | /* 23 | * 解码和编码,应和服务端一致 24 | * */ 25 | // ph.addLast("framer", new DelimiterBasedFrameDecoder(8192, Delimiters.lineDelimiter())); 26 | ph.addLast("decoder", new StringDecoder()); 27 | ph.addLast("encoder", new StringEncoder()); 28 | ph.addLast("handler", new NettyClientHandler()); //客户端的逻辑 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo/MinaClientHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo; 2 | 3 | import org.apache.log4j.Logger; 4 | import org.apache.mina.core.service.IoHandlerAdapter; 5 | import org.apache.mina.core.session.IoSession; 6 | 7 | 8 | /** 9 | * @author ZERO 10 | * @version 2017-3-27 ??6:01:31 11 | * 客户端handle 12 | */ 13 | public class MinaClientHandler extends IoHandlerAdapter { 14 | private static Logger logger = Logger.getLogger(MinaClientHandler.class); 15 | 16 | @Override 17 | public void messageReceived(IoSession session, Object message) 18 | throws Exception { 19 | String msg = message.toString(); 20 | logger.info("客户端接收的数据:" + msg); 21 | // if(msg.equals(XiaoaiConstant.CMD_HEARTBEAT_REQUEST)){ 22 | logger.warn("成功收到心跳包"); 23 | // session.write(XiaoaiConstant.CMD_HEARTBEAT_RESPONSE); 24 | // } 25 | 26 | } 27 | 28 | @Override 29 | public void exceptionCaught(IoSession session, Throwable cause) 30 | throws Exception { 31 | logger.error("发生错误...", cause); 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo/NettyServerFilter.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo; 2 | 3 | 4 | import io.netty.channel.ChannelInitializer; 5 | import io.netty.channel.ChannelPipeline; 6 | import io.netty.channel.socket.SocketChannel; 7 | import io.netty.handler.codec.string.StringDecoder; 8 | import io.netty.handler.codec.string.StringEncoder; 9 | 10 | /** 11 | * 12 | * Title: HelloServerInitializer 13 | * Description: Netty 服务端过滤器 14 | * Version:1.0.0 15 | * @author Administrator 16 | * @date 2017-8-31 17 | */ 18 | public class NettyServerFilter extends ChannelInitializer { 19 | 20 | @Override 21 | protected void initChannel(SocketChannel ch) throws Exception { 22 | ChannelPipeline ph = ch.pipeline(); 23 | // 以("\n")为结尾分割的 解码器 24 | // ph.addLast("framer", new DelimiterBasedFrameDecoder(8192, Delimiters.lineDelimiter())); 25 | // 解码和编码,应和客户端一致 26 | ph.addLast("decoder", new StringDecoder()); 27 | ph.addLast("encoder", new StringEncoder()); 28 | ph.addLast("handler", new NettyServerHandler());// 服务端业务逻辑 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/MyRunnable.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | /** 3 | * @author ZERO 4 | * @Data 2017-5-24 下午2:29:39 5 | * @Description 6 | */ 7 | public class MyRunnable implements Runnable{ 8 | private int i = 0; 9 | private boolean stop=false; 10 | public void set(boolean falg) throws InterruptedException{ 11 | if(!falg){ 12 | synchronized (this) { 13 | this.notify(); 14 | stop=true; 15 | System.out.println("启动的线程:"+Thread.currentThread().getId()); 16 | } 17 | } 18 | 19 | } 20 | 21 | @Override 22 | public void run() { 23 | for (;;) { 24 | synchronized (this) { 25 | if(stop){ 26 | try { 27 | this.wait(); 28 | System.out.println("暂停的线程:"+Thread.currentThread().getId()); 29 | } catch (InterruptedException e) { 30 | e.printStackTrace(); 31 | } 32 | } 33 | i++; 34 | System.out.println("MyRunnable:"+Thread.currentThread().getName() + "第" + i+ "次"); 35 | try { 36 | Thread.sleep(100); 37 | } catch (InterruptedException e) { 38 | e.printStackTrace(); 39 | } 40 | } 41 | } 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo1/MyTextLineCodecFactory.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo1; 2 | 3 | import java.nio.charset.Charset; 4 | 5 | import org.apache.mina.core.session.IoSession; 6 | import org.apache.mina.filter.codec.ProtocolCodecFactory; 7 | import org.apache.mina.filter.codec.ProtocolDecoder; 8 | import org.apache.mina.filter.codec.ProtocolEncoder; 9 | 10 | /** 11 | * @author ZERO 12 | * @version 2017-3-28 上午11:39:50 13 | * 编码格式工厂 14 | */ 15 | public class MyTextLineCodecFactory implements ProtocolCodecFactory { 16 | 17 | private Charset charset; // 编码格式 18 | private String delimiter; // 文本分隔符 19 | public MyTextLineCodecFactory(Charset charset, String delimiter) { 20 | this.charset = charset; 21 | this.delimiter = delimiter; 22 | } 23 | 24 | 25 | public ProtocolDecoder getDecoder(IoSession session) throws Exception { 26 | return new MyTextLineCodecDecoder(charset, delimiter); 27 | } 28 | 29 | 30 | public ProtocolEncoder getEncoder(IoSession session) throws Exception { 31 | return new MyTextLineCodecEncoder(charset, delimiter); 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo6/NettyServerFilter.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo6; 2 | 3 | 4 | import io.netty.channel.ChannelInitializer; 5 | import io.netty.channel.ChannelPipeline; 6 | import io.netty.channel.socket.SocketChannel; 7 | import io.netty.handler.codec.http.HttpObjectAggregator; 8 | import io.netty.handler.codec.http.HttpRequestDecoder; 9 | import io.netty.handler.codec.http.HttpResponseEncoder; 10 | 11 | 12 | /** 13 | * 14 | * Title: NettyServerFilter 15 | * Description: Netty 服务端过滤器 16 | * Version:1.0.0 17 | * @author pancm 18 | * @date 2017年10月26日 19 | */ 20 | public class NettyServerFilter extends ChannelInitializer { 21 | 22 | @Override 23 | protected void initChannel(SocketChannel ch) throws Exception { 24 | ChannelPipeline ph = ch.pipeline(); 25 | //处理http服务的关键handler 26 | ph.addLast("encoder",new HttpResponseEncoder()); 27 | ph.addLast("decoder",new HttpRequestDecoder()); 28 | ph.addLast("aggregator", new HttpObjectAggregator(10*1024*1024)); 29 | ph.addLast("handler", new NettyServerHandler());// 服务端业务逻辑 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/PriorityTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import java.util.Random; 4 | 5 | /** 6 | * @Title: PriorityTest 7 | * @Description: 8 | * 线程优先级测试 9 | * @Version:1.0.0 10 | * @author pancm 11 | * @date 2018年5月27日 12 | */ 13 | public class PriorityTest { 14 | 15 | public static void main(String[] args) { 16 | Test3 t1 = new Test3("张三"); 17 | Test3 t2 = new Test3("李四"); 18 | t1.setPriority(Thread.MIN_PRIORITY); 19 | t2.setPriority(Thread.MAX_PRIORITY); 20 | t1.start(); 21 | t2.start(); 22 | } 23 | } 24 | 25 | class Test3 extends Thread { 26 | public Test3(String name) { 27 | super(name); 28 | } 29 | @Override 30 | public void run() { 31 | System.out.println(this.getName() + " 线程运行开始!"); 32 | for (int i = 1; i <= 5; i++) { 33 | System.out.println("子线程"+this.getName() + "运行 : " + i); 34 | try { 35 | sleep(new Random().nextInt(10)); 36 | } catch (InterruptedException e) { 37 | e.printStackTrace(); 38 | } 39 | } 40 | System.out.println(this.getName() + " 线程运行结束!"); 41 | } 42 | } 43 | 44 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/concurrent/liveLock/Consumer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.concurrent.liveLock; 2 | 3 | import java.util.Random; 4 | 5 | 6 | public class Consumer implements Runnable { 7 | private Drop drop; 8 | 9 | public Consumer(Drop drop) { 10 | this.drop = drop; 11 | } 12 | public void run() { 13 | Random random = new Random(); 14 | // String message=""; 15 | // do{ 16 | // message= drop.take(); 17 | // System.out.format("MESSAGE RECEIVED: %s%n", message); 18 | // try { 19 | // Thread.sleep(random.nextInt(1000)); 20 | // } catch (InterruptedException e) { 21 | // e.printStackTrace(); 22 | // } 23 | // } while(!message.equals("DONE")); 24 | 25 | for (String message = drop.take(); !message.equals("DONE"); message = drop.take()) { 26 | System.out.format("MESSAGE RECEIVED: %s%n", message); 27 | try { 28 | Thread.sleep(random.nextInt(1000)); 29 | } catch (InterruptedException e) { 30 | e.printStackTrace(); 31 | } 32 | } 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/commons/google/GoogleTest.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | package com.pancm.commons.google; 5 | 6 | import java.util.ArrayList; 7 | import java.util.List; 8 | 9 | import com.google.common.base.Function; 10 | import com.google.common.collect.Lists; 11 | import com.pancm.pojo.User; 12 | 13 | /** 14 | * @Title: googleTest 15 | * @Description: 16 | * @Version:1.0.0 17 | * @author pancm 18 | * @date 2018年5月14日 19 | */ 20 | public class GoogleTest { 21 | 22 | /** 23 | * @param args 24 | */ 25 | public static void main(String[] args) { 26 | test(); 27 | } 28 | 29 | /** 30 | * 数组里所有对象的某个属性的值改变 31 | */ 32 | private static void test(){ 33 | List userList=new ArrayList<>(); 34 | User user=new User(); 35 | user.setId(1); 36 | user.setName("张三"); 37 | userList.add(user); 38 | User user2=new User(); 39 | user2.setId(2); 40 | user2.setName("李四"); 41 | userList.add(user2); 42 | System.out.println("更改之前的数据:"+userList); 43 | userList=Lists.transform(userList,new Function() { 44 | @Override 45 | public User apply(User user) { 46 | user.setName("王五"); 47 | return user; 48 | } 49 | }); 50 | System.out.println("更改之后的数据:"+userList); 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/concurrent/liveLock/Drop.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.concurrent.liveLock; 2 | 3 | /** 4 | * 5 | * Title: Drop 6 | * Description: 7 | * 数据协同 8 | * Version:1.0.0 9 | * @author pancm 10 | * @date 2018年3月8日 11 | */ 12 | public class Drop { 13 | // 发送的消息 14 | private String message; 15 | //true 表示消费者应该等待生产者发送消息 16 | // flase 表示生产者应该等待消费者获取消息 17 | private boolean empty = true; 18 | 19 | public synchronized String take() { 20 | // 等待消息可用 21 | while (empty) { 22 | try { 23 | wait(); 24 | } catch (InterruptedException e) { 25 | e.printStackTrace(); 26 | } 27 | } 28 | // 改变状态 29 | empty = true; 30 | // 通知消费者状态改变 31 | notifyAll(); 32 | return message; 33 | } 34 | 35 | public synchronized void put(String message) { 36 | //等待消息被检索到 37 | while (!empty) { 38 | try { 39 | wait(); 40 | } catch (InterruptedException e) { 41 | e.printStackTrace(); 42 | } 43 | } 44 | // 改变状态 45 | empty = false; 46 | this.message = message; 47 | // 通知消费者状态改变 48 | notifyAll(); 49 | } 50 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/AbstractTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * @author pancm 5 | * @Data 2017-6-1 6 | * @Description abstract 抽象类测试 7 | */ 8 | public class AbstractTest { 9 | public static void main(String[] args) { 10 | // 这句会报错,因为抽象类不能实例化 11 | // Animal a=new Animal(); 12 | Animal a = new Dog(); 13 | a.show(); 14 | 15 | E p = new F(); 16 | p.show(); 17 | E q = new G(); 18 | q.show(); 19 | 20 | /* 21 | * 22 | * 1、抽象类和抽象方法都需要被abstract修饰。抽象方法一定要定义在抽象类中。 23 | * 24 | * 2、抽象类不可以创建实例,原因:调用抽象方法没有意义。 25 | * 26 | * 3、只有覆盖了抽象类中所有的抽象方法后,其子类才可以实例化。否则该子类还是一个抽象类。 27 | * 28 | * 之所以继承,更多的是在思想,是面对共性类型操作会更简单。 29 | * 30 | */ 31 | } 32 | } 33 | 34 | abstract class Animal { 35 | abstract void show(); 36 | 37 | public void print() { 38 | System.out.println("Animal"); 39 | } 40 | } 41 | 42 | class Dog extends Animal { 43 | @Override 44 | void show() { 45 | System.out.println("This is Dog!"); 46 | } 47 | } 48 | 49 | abstract class E { 50 | public abstract void show(); 51 | } 52 | 53 | class F extends E { 54 | public void show() { 55 | System.out.print("test all FFFF \n"); 56 | } 57 | } 58 | 59 | class G extends E { 60 | public void show() { 61 | System.out.print("test all GGGG \n"); 62 | } 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/ExtendTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | 4 | /** 5 | * 6 | * @Title: ExtendTest 7 | * @Description: 8 | * 继承测试 9 | * @Version:1.0.0 10 | * @author pancm 11 | * @date 2018年3月27日 12 | */ 13 | public class ExtendTest { 14 | 15 | public static void main(String[] args) { 16 | Cat1 cat=new Cat1(); 17 | Dog1 dog=new Dog1(); 18 | cat.eat(); 19 | cat.sleep("cat"); 20 | cat.climbTree(); 21 | dog.eat("dog"); 22 | dog.sleep("dog"); 23 | } 24 | } 25 | 26 | class Animal1{ 27 | public void eat(String name){ 28 | System.out.println(name+"正在吃东西..."); 29 | } 30 | public void sleep(String name){ 31 | System.out.println(name+"正在睡觉..."); 32 | } 33 | } 34 | 35 | class Cat1 extends Animal1{ 36 | private String name="Cat"; 37 | public void eat(){ 38 | super.eat(name); 39 | System.out.println(name+"吃完了"); 40 | } 41 | public void sleep(){ 42 | this.sleep(name); 43 | } 44 | 45 | public void sleep(String name){ 46 | System.out.println(name+"刚刚睡觉!"); 47 | } 48 | 49 | public void climbTree(){ 50 | System.out.println(name+"正在爬树!"); 51 | } 52 | } 53 | 54 | class Dog1 extends Animal1{ 55 | 56 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo/NettyServerHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo; 2 | 3 | import java.net.InetAddress; 4 | import java.util.Date; 5 | 6 | import io.netty.channel.ChannelHandlerContext; 7 | import io.netty.channel.SimpleChannelInboundHandler; 8 | 9 | 10 | /** 11 | * 12 | * Title: HelloServerHandler 13 | * Description: 服务端业务逻辑 14 | * Version:1.0.0 15 | * @author Administrator 16 | * @date 2017-8-31 17 | */ 18 | public class NettyServerHandler extends SimpleChannelInboundHandler { 19 | /* 20 | * 收到消息时,返回信息 21 | */ 22 | @Override 23 | protected void channelRead0(ChannelHandlerContext ctx, String msg) 24 | throws Exception { 25 | // 收到消息直接打印输出 26 | System.out.println("服务端接受的消息 : " + msg); 27 | if("quit".equals(msg)){//服务端断开的条件 28 | ctx.close(); 29 | } 30 | // 返回客户端消息 31 | // ctx.writeAndFlush("收到消息:"+ msg+",当前的时间是:"+MyTools.getNowTime("")+"\n"); 32 | ctx.writeAndFlush("收到消息:"+ msg+",当前的时间是:"+new Date()); 33 | } 34 | 35 | /* 36 | * 建立连接时,返回消息 37 | */ 38 | @Override 39 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 40 | System.out.println("连接的客户端地址:" + ctx.channel().remoteAddress()); 41 | ctx.writeAndFlush("客户端"+ InetAddress.getLocalHost().getHostName() + "成功与服务端建立连接! "); 42 | super.channelActive(ctx); 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/NotifyTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import java.util.Random; 4 | 5 | /** 6 | * @Title: NotifyTest 7 | * @Description: 8 | * wait 和 notify测试 9 | * @Version:1.0.0 10 | * @author pancm 11 | * @date 2018年5月22日 12 | */ 13 | public class NotifyTest { 14 | 15 | public static void main(String[] args) { 16 | Test4 t1 = new Test4("张三"); 17 | Test4 t2 = new Test4("李四"); 18 | t1.start(); 19 | t2.start(); 20 | } 21 | } 22 | 23 | class Test4 extends Thread { 24 | private String name; 25 | public Test4(String name) { 26 | super(name); 27 | this.name=name; 28 | } 29 | 30 | @Override 31 | public void run() { 32 | System.out.println(this.getName() + " 线程运行开始!"); 33 | 34 | for (int i = 0; i < 5; i++) { 35 | System.out.println("子线程" + this.getName() + "运行 : " + i); 36 | try { 37 | sleep(new Random().nextInt(100)); 38 | } catch (InterruptedException e) { 39 | e.printStackTrace(); 40 | } 41 | try { 42 | if("李四".equals(this.getName())){ 43 | this.getName().wait(); 44 | } 45 | } catch (InterruptedException e) { 46 | e.printStackTrace(); 47 | } 48 | this.getName().notify(); 49 | 50 | } 51 | System.out.println(this.getName() + " 线程运行结束!"); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/SuperTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * 5 | * @Title: SuperTest 6 | * @Description: super测试 7 | * @Version:1.0.0 8 | * @author pancm 9 | * @date 2017-5-24 10 | */ 11 | public class SuperTest extends Person8 { 12 | SuperTest() { 13 | super(); // 调用父类构造函数(1) 14 | prt("A chinese.");// (4) 15 | } 16 | 17 | SuperTest(String name) { 18 | super(name);// 调用父类具有相同形参的构造函数(2) 调用了Person中的Person(String name)方法 19 | prt("his name is:" + name); 20 | } 21 | 22 | SuperTest(String name, int age) { 23 | this(name);// 调用当前具有相同形参的构造函数(3) 调用了SuperTest(String name) 24 | prt("his age is:" + age); 25 | } 26 | 27 | public static void main(String[] args) { 28 | SuperTest cn = new SuperTest(); // A Person. A chinese. 29 | cn = new SuperTest("kevin"); //A person name is:kevin his name is:kevin 30 | cn = new SuperTest("kevin", 22);//A person name is:kevin his name is:kevin his age is:22 31 | } 32 | } 33 | 34 | 35 | class Person8 { 36 | 37 | public static void prt(String s) { 38 | System.out.println(s); 39 | } 40 | 41 | Person8() { 42 | prt("A Person."); 43 | } 44 | 45 | Person8(String name) { 46 | prt("A person name is:" + name); 47 | 48 | } 49 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/ForTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | import java.util.ArrayList; 4 | import java.util.Iterator; 5 | import java.util.List; 6 | 7 | /** 8 | * 9 | * @Title: ForTest 10 | * @Description: 循环测试 11 | * @Version:1.0.0 12 | * @author pancm 13 | * @date 2017年9月29日 14 | */ 15 | public class ForTest { 16 | public static void main(String[] args) { 17 | /* 18 | * 阿里巴巴开发手册中的遍历移除测试 19 | */ 20 | iteratorTest(); 21 | forEachTest(); 22 | } 23 | private static void forEachTest(){ 24 | List list = new ArrayList(); 25 | list.add("1"); 26 | list.add("2"); 27 | System.out.println("list1:"+list); 28 | for (String item : list) { 29 | //如果是1就不会出现 30 | if ("2".equals(item)) { 31 | list.remove(item); 32 | //加上break就不会抛异常 33 | // break; 34 | } 35 | } 36 | System.out.println("list2:"+list); 37 | } 38 | private static void iteratorTest(){ 39 | List list = new ArrayList(); 40 | list.add("1"); 41 | list.add("2"); 42 | System.out.println("list3:"+list); 43 | Iterator iterator = list.iterator(); 44 | while (iterator.hasNext()) { 45 | String item = iterator.next(); 46 | if ("2".equals(item)) { 47 | iterator.remove(); 48 | } 49 | } 50 | System.out.println("list4:"+list); 51 | } 52 | 53 | 54 | } 55 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/question/QuestionTest2.java: -------------------------------------------------------------------------------- 1 | package com.pancm.question; 2 | 3 | /** 4 | * @Title: QuestionTest1 5 | * @Description: 6 | * @Version:1.0.0 7 | * @author pancm 8 | * @date 2017年7月21日 9 | */ 10 | public class QuestionTest2 { 11 | 12 | /** 13 | * @param args 14 | */ 15 | public static void main(String[] args) { 16 | 17 | /* 18 | * 请实现一个函数,将一个字符串中的空格替换成“%20”。 19 | * 例如,当字符串为We Are Happy.则经过替换之后的字符串为We%20Are%20Happy。 20 | */ 21 | StringBuffer str=new StringBuffer("We Are Happy"); 22 | System.out.println(replaceString(str)); 23 | System.out.println(replaceString2(str)); 24 | 25 | 26 | } 27 | 28 | /** 29 | * 方法一:利用String的replace 直接替换 30 | * @param str 31 | * @return String 32 | */ 33 | public static String replaceString(StringBuffer str){ 34 | if(str==null){ 35 | return null; 36 | } 37 | return str.toString().replaceAll(" ", "%20"); 38 | } 39 | 40 | /** 41 | * 方法二:利用数组循环取出 42 | * @param str 43 | * @return 44 | */ 45 | public static String replaceString2(StringBuffer str){ 46 | if(str==null){ 47 | return null; 48 | } 49 | char []c =str.toString().toCharArray(); 50 | StringBuffer sb=new StringBuffer(); 51 | for(int i=0;i0){ //有参数时,表示向集群提交作业,并把第一个参数当做topology名称 33 | System.out.println("远程模式"); 34 | StormSubmitter.submitTopology(args[0], conf, builder.createTopology()); 35 | } else{//没有参数时,本地提交 36 | //启动本地模式 37 | System.out.println("本地模式"); 38 | LocalCluster cluster = new LocalCluster(); 39 | cluster.submitTopology("111" ,conf, builder.createTopology() ); 40 | // Thread.sleep(2000); 41 | // //关闭本地集群 42 | // cluster.shutdown(); 43 | } 44 | }catch (Exception e){ 45 | e.printStackTrace(); 46 | } 47 | 48 | } 49 | 50 | } 51 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/facade/FacadeTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.facade; 2 | 3 | /** 4 | * @Title: FacadeTest 5 | * @Description: 6 | * 外观模式测试代码 7 | * 8 | * 为子系统中的一组接口提供一个一致的界面,外观模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。 9 | * 10 | * 比如windows开机:启动CPU、启动内存、启动硬盘 11 | * windows关机:关闭硬盘、关闭内存、关闭CPU 12 | * 13 | * @Version:1.0.0 14 | * @author pancm 15 | * @date 2018年8月8日 16 | */ 17 | public class FacadeTest { 18 | 19 | public static void main(String[] args) { 20 | 21 | /* 22 | * 对外提供 一个界面 23 | * 游戏装在电脑上,想玩游戏就在电脑启动游戏就可以了 24 | */ 25 | Computer computer=new Computer(); 26 | computer.playDNF(); 27 | computer.playLOL(); 28 | computer.playWOW(); 29 | } 30 | } 31 | 32 | interface Game{ 33 | void play(); 34 | } 35 | 36 | class DNF implements Game{ 37 | 38 | @Override 39 | public void play() { 40 | System.out.println("正在玩DNF..."); 41 | } 42 | } 43 | 44 | class LOL implements Game{ 45 | @Override 46 | public void play() { 47 | System.out.println("正在玩LOL..."); 48 | } 49 | } 50 | 51 | class WOW implements Game{ 52 | @Override 53 | public void play() { 54 | System.out.println("正在玩WOW..."); 55 | } 56 | } 57 | 58 | class Computer{ 59 | 60 | private Game dnf; 61 | private Game lol; 62 | private Game wow; 63 | 64 | public Computer() { 65 | dnf=new DNF(); 66 | lol=new LOL(); 67 | wow=new WOW(); 68 | } 69 | 70 | public void playDNF(){ 71 | dnf.play(); 72 | } 73 | 74 | public void playLOL(){ 75 | lol.play(); 76 | } 77 | 78 | public void playWOW(){ 79 | wow.play(); 80 | } 81 | 82 | 83 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo/NettyServer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo; 2 | 3 | import io.netty.bootstrap.ServerBootstrap; 4 | import io.netty.channel.ChannelFuture; 5 | import io.netty.channel.EventLoopGroup; 6 | import io.netty.channel.nio.NioEventLoopGroup; 7 | import io.netty.channel.socket.nio.NioServerSocketChannel; 8 | 9 | /** 10 | * 11 | * Title: NettyServer 12 | * Description: Netty服务端 13 | * Version:1.0.0 14 | * @author Administrator 15 | * @date 2017-8-31 16 | */ 17 | public class NettyServer { 18 | private static final int port = 6789; //设置服务端端口 19 | private static EventLoopGroup group = new NioEventLoopGroup(); // 通过nio方式来接收连接和处理连接 20 | private static ServerBootstrap b = new ServerBootstrap(); 21 | 22 | /** 23 | * Netty创建全部都是实现自AbstractBootstrap。 24 | * 客户端的是Bootstrap,服务端的则是 ServerBootstrap。 25 | **/ 26 | public static void main(String[] args) throws InterruptedException { 27 | try { 28 | b.group(group); 29 | b.channel(NioServerSocketChannel.class); 30 | b.childHandler(new NettyServerFilter()); //设置过滤器 31 | // 异步地绑定服务器;调用 sync()方法阻塞 等待直到绑定完成 32 | ChannelFuture f = b.bind(port).sync(); 33 | System.out.println("服务端启动成功,端口是:"+port); 34 | // 获取 Channel 的 CloseFuture,并且阻塞当前线程直到它完成 35 | f.channel().closeFuture().sync(); 36 | } finally { 37 | group.shutdownGracefully(); //关闭EventLoopGroup,释放掉所有资源包括创建的线程 38 | } 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/redis/RedisTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.redis; 2 | 3 | import java.util.Iterator; 4 | import java.util.List; 5 | import java.util.Set; 6 | 7 | import redis.clients.jedis.Jedis; 8 | 9 | /** 10 | * 11 | * @Title: RedisTest 12 | * @Description: redis测试代码 13 | * @Version:1.0.0 14 | * @author pancm 15 | * @date 2017-8-19 16 | */ 17 | public class RedisTest { 18 | 19 | /** 20 | * @param args 21 | */ 22 | public static void main(String[] args) { 23 | // 连接到本地的 redis服务 24 | Jedis jedis = new Jedis("127.0.0.1"); 25 | System.out.println("连接成功"); 26 | // 查看服务是否运行 27 | System.out.println("服务正在运行: " + jedis.ping()); 28 | // 存储到列表中 29 | jedis.lpush("list", "redis"); 30 | jedis.lpush("list", "java"); 31 | jedis.lpush("list", "mysql"); 32 | // 获取存储的数据并输出 33 | List list = jedis.lrange("list", 0, 2); 34 | for (int i = 0, j = list.size(); i < j; i++) { 35 | System.out.println("list的输出结果:" + list.get(i)); 36 | } 37 | // 设置 redis 字符串数据 38 | jedis.set("rst", "redisStringTest"); 39 | // 获取存储的数据并输出 40 | System.out.println("redis 存储的字符串为: " + jedis.get("rst")); 41 | 42 | // 存储数据 43 | jedis.sadd("setTest1", "abc"); 44 | jedis.sadd("setTest1", "abcd"); 45 | jedis.sadd("setTest1", "abcde"); 46 | // 获取数据并输出 47 | Set keys = jedis.keys("*"); 48 | // Set keys=jedis.smembers("setTest1"); 49 | // 定义迭代器输出 50 | Iterator it = keys.iterator(); 51 | while (it.hasNext()) { 52 | String key = it.next(); 53 | System.out.println(key); 54 | } 55 | 56 | } 57 | 58 | } 59 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/commons/apache/CompressTest.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | package com.pancm.commons.apache; 5 | 6 | import java.io.File; 7 | import java.io.FileInputStream; 8 | import java.io.FileNotFoundException; 9 | import java.io.IOException; 10 | 11 | import org.apache.commons.compress.archivers.zip.ZipArchiveEntry; 12 | import org.apache.commons.compress.archivers.zip.ZipArchiveOutputStream; 13 | 14 | /** 15 | * @Title: compressTest 16 | * @Description: 17 | * 压缩测试 18 | * @Version:1.0.0 19 | * @author pancm 20 | * @date 2018年5月14日 21 | */ 22 | public class CompressTest { 23 | 24 | /** 25 | * @param args 26 | */ 27 | public static void main(String[] args) { 28 | test(); 29 | } 30 | 31 | /** 32 | * 压缩文件测试 33 | */ 34 | private static void test() { 35 | 36 | // 创建压缩对象 37 | ZipArchiveEntry entry = new ZipArchiveEntry("CompressTest"); 38 | // 要压缩的文件 39 | File f = new File("d:\\user.txt"); 40 | FileInputStream fis; 41 | try { 42 | fis = new FileInputStream(f); 43 | // 输出的对象 压缩的文件 44 | ZipArchiveOutputStream zipOutput = new ZipArchiveOutputStream(new File("d:\\user.zip")); 45 | zipOutput.putArchiveEntry(entry); 46 | int i = 0, j; 47 | while ((j = fis.read()) != -1) { 48 | zipOutput.write(j); 49 | i++; 50 | } 51 | System.out.println("压缩成功!遍历了:" + i + "次"); 52 | zipOutput.closeArchiveEntry(); 53 | zipOutput.close(); 54 | fis.close(); 55 | } catch (FileNotFoundException e) { 56 | e.printStackTrace(); 57 | } catch (IOException e) { 58 | e.printStackTrace(); 59 | } 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/JoinTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | import java.util.Random; 4 | 5 | /** 6 | * @Title: JoinTest 7 | * @Description: 8 | * join方法测试 9 | * @Version:1.0.0 10 | * @author pancm 11 | * @date 2018年5月22日 12 | */ 13 | public class JoinTest { 14 | 15 | public static void main(String[] args) { 16 | System.out.println(Thread.currentThread().getName()+ "主线程开始运行!"); 17 | Test2 t1=new Test2("A"); 18 | Test2 t2=new Test2("B"); 19 | t1.start(); 20 | t2.start(); 21 | try { 22 | t1.join(); 23 | } catch (InterruptedException e) { 24 | e.printStackTrace(); 25 | } 26 | try { 27 | t2.join(); 28 | } catch (InterruptedException e) { 29 | e.printStackTrace(); 30 | } 31 | System.out.println(Thread.currentThread().getName()+ "主线程运行结束!"); 32 | } 33 | 34 | } 35 | 36 | class Test2 extends Thread{ 37 | public Test2(String name) { 38 | super(name); 39 | } 40 | public void run() { 41 | System.out.println(this.getName() + " 线程运行开始!"); 42 | for (int i = 0; i < 5; i++) { 43 | System.out.println("子线程"+this.getName() + "运行 : " + i); 44 | try { 45 | sleep(new Random().nextInt(10)); 46 | } catch (InterruptedException e) { 47 | e.printStackTrace(); 48 | } 49 | } 50 | System.out.println(this.getName() + " 线程运行结束!"); 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/bridge/BridgeTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.bridge; 2 | 3 | /** 4 | * @Title: BridgeTest 5 | * @Description:桥接模式 6 | * 将抽象部分与实现部分分离,使它们都可以独立的变化。 7 | * @Version:1.0.0 8 | * @author pancm 9 | * @date 2018年8月8日 10 | */ 11 | public class BridgeTest { 12 | public static void main(String[] args) { 13 | Paper paper=new ExaminationPaper(); 14 | paper.setPen(new RedPen()); 15 | paper.writing(); 16 | 17 | Paper paper2=new NewsPaper(); 18 | paper2.setPen(new BlackPen()); 19 | paper2.writing(); 20 | } 21 | } 22 | 23 | /** 24 | * 25 | * @Title: ColourPen 26 | * @Description: 27 | * 笔 28 | * @Version:1.0.0 29 | * @author pancm 30 | * @date 2018年8月22日 31 | */ 32 | interface Pen{ 33 | void write(); 34 | } 35 | 36 | class RedPen implements Pen{ 37 | @Override 38 | public void write() { 39 | System.out.println("红色的字"); 40 | } 41 | } 42 | 43 | class BlackPen implements Pen{ 44 | @Override 45 | public void write() { 46 | System.out.println("黑色的字"); 47 | } 48 | } 49 | 50 | 51 | abstract class Paper{ 52 | protected Pen pen; 53 | 54 | void setPen(Pen pen){ 55 | this.pen=pen; 56 | } 57 | 58 | abstract void writing(); 59 | } 60 | 61 | /** 62 | * 63 | * @Title: ExaminationPaper 64 | * @Description:考试用的卷子 65 | * @Version:1.0.0 66 | * @author pancm 67 | * @date 2018年8月22日 68 | */ 69 | class ExaminationPaper extends Paper{ 70 | @Override 71 | void writing() { 72 | pen.write(); 73 | } 74 | } 75 | 76 | class NewsPaper extends Paper{ 77 | @Override 78 | void writing() { 79 | pen.write(); 80 | } 81 | } 82 | 83 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/prototype/PrototypeTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.prototype; 2 | 3 | /** 4 | * @Title: PrototypeTest 5 | * @Description: 原型模式 6 | * 用原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象。 7 | * 所谓原型模式,就是java中的克隆技术,以某个对象为原型。复制出新的对象。显然新的对象具备原型对象的特点。 8 | * 1、实现克隆操作,在 JAVA 继承 Cloneable,重写 clone()。 9 | * 2、原型模式同样用于隔离类对象的使用者和具体类型(易变类)之间的耦合关系,它同样要求这些"易变类"拥有稳定的接口。 10 | * 11 | * @Version:1.0.0 12 | * @author pancm 13 | * @date 2018年8月13日 14 | */ 15 | public class PrototypeTest { 16 | 17 | public static void main(String[] args) { 18 | Mail mail=new Mail(); 19 | mail.setMsg("生日快乐!"); 20 | Mail mail2=(Mail) mail.clone(); 21 | System.out.println("小明:"+mail.getMsg()); 22 | System.out.println("小红:"+mail2.getMsg()); 23 | } 24 | } 25 | 26 | /** 27 | * @Title: 28 | * @Description: 定义一个原型的邮件信息 29 | * @Version:1.0.0 30 | * @author pancm 31 | * @date 2018年8月15日 32 | */ 33 | class Mail implements Cloneable { 34 | protected String msg; 35 | 36 | public String getMsg() { 37 | return msg; 38 | } 39 | 40 | public void setMsg(String msg) { 41 | this.msg = msg; 42 | } 43 | 44 | 45 | public Object clone() { 46 | Object clone = null; 47 | try { 48 | clone = super.clone(); 49 | } catch (CloneNotSupportedException e) { 50 | e.printStackTrace(); 51 | } 52 | return clone; 53 | } 54 | void sendMail() { 55 | } 56 | } 57 | 58 | class BirthdayMail extends Mail { 59 | 60 | public BirthdayMail() { 61 | msg = "生日快乐!"; 62 | } 63 | 64 | @Override 65 | void sendMail() { 66 | System.out.println(msg); 67 | } 68 | } 69 | 70 | 71 | 72 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/User.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * 5 | * @Title: User 6 | * @Description: 7 | * 反射测试实体类 8 | * Version:1.0.0 9 | * @author pancm 10 | * @date 2018年2月9日 11 | */ 12 | public class User { 13 | private String name; 14 | 15 | //构造方法1(默认构造方法)*********************** 16 | public User(){ 17 | 18 | } 19 | //构造方法2 20 | public User(String name){ 21 | this.name=name; 22 | } 23 | //******自定义方法************* 24 | public void getMessage(){ 25 | System.out.print("反射测试"); 26 | } 27 | 28 | //******自定义方法2************* 29 | public String getMessage2(int num){ 30 | String str=num+"反射测试!"; 31 | System.out.print(str); 32 | return str; 33 | } 34 | 35 | //******自定义方法3************* 36 | private String getMessage3(){ 37 | String str="这是一个私有的方法!"; 38 | System.out.print(str); 39 | return str; 40 | } 41 | 42 | 43 | //******自定义方法4************* 44 | public static String getMessage4(String s){ 45 | String str=s+"这是一个静态的方法!"; 46 | System.out.print(str); 47 | return str; 48 | } 49 | 50 | //******重写toString方法,在测试的时候会用到***** 51 | @Override 52 | public String toString() { 53 | return "name:"+this.name; 54 | } 55 | //************************** 56 | public String getName() { 57 | return name; 58 | } 59 | public void setName(String name) { 60 | this.name = name; 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/ThreadTest1.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | /** 3 | * @author ZERO 4 | * @Data 2017-5-24 下午2:22:41 5 | * @Description 6 | */ 7 | public class ThreadTest1 { 8 | 9 | public static void main(String[] args) { 10 | myThread(); 11 | System.out.println("\r\n"); 12 | myRunnable(); 13 | } 14 | 15 | 16 | public static void myThread(){ 17 | for (int i = 0; i < 10; i++) { 18 | System.out.println("myThreadTest:"+Thread.currentThread().getName() + " " + i); 19 | if (i == 3) { 20 | Thread myThread1 = new MyThread(); // 创建一个新的线程 myThread1 此线程进入新建状态 21 | Thread myThread2 = new MyThread(); // 创建一个新的线程 myThread2 此线程进入新建状态 22 | myThread1.start(); // 调用start()方法使得线程进入就绪状态 23 | myThread2.start(); // 调用start()方法使得线程进入就绪状态 24 | } 25 | } 26 | } 27 | 28 | public static void myRunnable(){ 29 | for (int i = 0; i < 10; i++) { 30 | System.out.println("myRunnableTest:"+Thread.currentThread().getName() + " " + i); 31 | if (i == 3) { 32 | Runnable myRunnable = new MyRunnable(); // 创建一个Runnable实现类的对象 33 | Thread thread1 = new Thread(myRunnable); // 将myRunnable作为Thread target创建新的线程 34 | Thread thread2 = new Thread(myRunnable); 35 | thread1.start(); // 调用start()方法使得线程进入就绪状态 36 | thread2.start(); 37 | } 38 | } 39 | } 40 | 41 | 42 | } 43 | 44 | 45 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo4/NettyServerHandlerDemo4.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo4; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | 6 | /** 7 | * 8 | * Description:服务端业务逻辑处理类 9 | * Version:1.0.0 10 | * @author pancm 11 | * @date 2017年9月21日 12 | */ 13 | public class NettyServerHandlerDemo4 extends ChannelInboundHandlerAdapter { 14 | 15 | /** 16 | * 处理业务逻辑消息 17 | */ 18 | protected void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception { 19 | System.out.println(" ----- "+msg); 20 | if(msg instanceof NettySendBody) { 21 | NettySendBody nsb = (NettySendBody)msg; 22 | System.out.println("服务端接受的消息为:"+nsb.toString()); 23 | NettySendBody nsb1 = new NettySendBody(); 24 | nsb1.put("3333","44444"); 25 | ctx.writeAndFlush(nsb1); 26 | }else{ 27 | System.out.println("收到非法请求"); 28 | } 29 | } 30 | 31 | @Override 32 | public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception { 33 | System.out.println(" ----- "+msg); 34 | if(msg instanceof NettySendBody) { 35 | NettySendBody nsb = (NettySendBody)msg; 36 | System.out.println("服务端接受的消息为:"+nsb.toString()); 37 | NettySendBody nsb1 = new NettySendBody(); 38 | nsb1.put("3333","44444"); 39 | ctx.writeAndFlush(nsb1); 40 | }else{ 41 | System.out.println("收到非法请求"); 42 | } 43 | } 44 | 45 | } 46 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo/NettyClient.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo; 2 | 3 | 4 | import java.io.IOException; 5 | 6 | import io.netty.bootstrap.Bootstrap; 7 | import io.netty.channel.Channel; 8 | import io.netty.channel.EventLoopGroup; 9 | import io.netty.channel.nio.NioEventLoopGroup; 10 | import io.netty.channel.socket.nio.NioSocketChannel; 11 | /** 12 | * 13 | * Title: NettyClient 14 | * Description: Netty客户端 15 | * Version:1.0.0 16 | * @author Administrator 17 | * @date 2017-8-31 18 | */ 19 | public class NettyClient { 20 | 21 | public static String host = "127.0.0.1"; //ip地址 22 | public static int port = 6789; //端口 23 | /// 通过nio方式来接收连接和处理连接 24 | private static EventLoopGroup group = new NioEventLoopGroup(); 25 | private static Bootstrap b = new Bootstrap(); 26 | private static Channel ch; 27 | 28 | /** 29 | * Netty创建全部都是实现自AbstractBootstrap。 30 | * 客户端的是Bootstrap,服务端的则是 ServerBootstrap。 31 | **/ 32 | public static void main(String[] args) throws InterruptedException, IOException { 33 | System.out.println("客户端成功启动..."); 34 | b.group(group); 35 | b.channel(NioSocketChannel.class); 36 | b.handler(new NettyClientFilter()); 37 | // 连接服务端 38 | ch = b.connect(host, port).sync().channel(); 39 | star(); 40 | } 41 | 42 | public static void star() throws IOException{ 43 | String str="Hello Netty"; 44 | ch.writeAndFlush(str); 45 | // ch.writeAndFlush(str+ "\r\n"); 46 | System.out.println("客户端发送数据:"+str); 47 | } 48 | 49 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/ExtendsTest2.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * 5 | * @Title: ExtendsTest2 6 | * @Description: 继承测试 经典题 7 | * @Version:1.0.0 8 | * @author pancm 9 | * @date 2017年6月2日 10 | */ 11 | public class ExtendsTest2 { 12 | public static void main(String[] args) { 13 | A a1 = new A(); 14 | A a2 = new B(); 15 | B b = new B(); 16 | C c = new C(); 17 | D d = new D(); 18 | 19 | System.out.println("1--" + a1.show(b)); //A and A 20 | System.out.println("2--" + a1.show(c)); //A and A 21 | System.out.println("3--" + a1.show(d)); //A and D 22 | System.out.println("4--" + a2.show(b)); //B and A 23 | System.out.println("5--" + a2.show(c)); //B and A 24 | System.out.println("6--" + a2.show(d)); //A and D 25 | System.out.println("7--" + b.show(b)); //B and B 26 | System.out.println("8--" + b.show(c)); //B and B 27 | System.out.println("9--" + b.show(d)); //A and D 28 | } 29 | } 30 | 31 | class A { 32 | public String show(D obj) { 33 | return ("A and D"); 34 | } 35 | 36 | public String show(A obj) { 37 | return ("A and A"); 38 | } 39 | 40 | } 41 | 42 | class B extends A{ 43 | public String show(B obj){ 44 | return ("B and B"); 45 | } 46 | 47 | public String show(A obj){ 48 | return ("B and A"); 49 | } 50 | } 51 | 52 | class C extends B{ 53 | 54 | } 55 | 56 | class D extends B{ 57 | 58 | } 59 | 60 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/demo/RabbitProducer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.demo; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import com.alibaba.fastjson.JSON; 7 | import com.rabbitmq.client.Channel; 8 | import com.rabbitmq.client.Connection; 9 | import com.rabbitmq.client.ConnectionFactory; 10 | 11 | //生产者 12 | public class RabbitProducer { 13 | private final static String QUEUE_NAME = "RabbitMQ_Hello"; //消息队列名 14 | 15 | public static void main(String[] argv) throws Exception { 16 | //创建连接连接到RabbitMQ 17 | ConnectionFactory factory = new ConnectionFactory(); 18 | // 设置ip 19 | factory.setHost("127.0.0.1"); 20 | /* //设置端口 21 | factory.setPort(15672); 22 | //设置用户名 23 | factory.setUsername("guest"); 24 | //设置密码 25 | factory.setPassword("guest"); 26 | //设置url(包括ip、端口、用户名、密码) 27 | factory.setUri("amqp://guest:guest@localhost:15672"); 28 | */ 29 | // 创建一个连接 30 | Connection connection = factory.newConnection(); 31 | // 创建一个频道 32 | Channel channel = connection.createChannel(); 33 | // 指定一个队列 34 | channel.queueDeclare(QUEUE_NAME, false, false, false, null); 35 | Map map=new HashMap(); 36 | map.put("java", "hello"); 37 | map.put("RabbitMQ", "Hello"); 38 | //发送的消息 39 | String message = JSON.toJSONString(map); 40 | // 往队列中发出一条消息 41 | channel.basicPublish("", QUEUE_NAME, null, message.getBytes()); 42 | System.out.println(" [x] Sent '" + message + "'"); 43 | // 关闭频道和连接 44 | channel.close(); 45 | connection.close(); 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/one2one/Send.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.one2one; 2 | import java.util.HashMap; 3 | import java.util.Map; 4 | 5 | import com.alibaba.fastjson.JSON; 6 | import com.rabbitmq.client.Channel; 7 | //生产者 ( Producer:数据的发送方) 8 | //单发送单接收 //单发送单接收 Send.java和Recv.java类 9 | import com.rabbitmq.client.Connection; 10 | import com.rabbitmq.client.ConnectionFactory; 11 | 12 | public class Send { 13 | 14 | private final static String QUEUE_NAME = "header_exchange"; //消息队列名 15 | 16 | public static void main(String[] argv) throws Exception { 17 | Map map=new HashMap(); 18 | map.put("aa", 11); 19 | map.put("bb", 22); 20 | map.put("cc", 33); 21 | map.put("dd", 44); 22 | map.put("ff", 1); 23 | System.out.println("你好啊!"); 24 | //创建连接连接到MabbitMQ 25 | ConnectionFactory factory = new ConnectionFactory(); 26 | // 设置MabbitMQ所在主机ip或者主机名 27 | // factory.setHost("localhost"); 28 | //factory.setHost("127.0.0.1"); 29 | 30 | factory.setUri("amqp://guest:guest@172.26.129.3:5672");//获取url 31 | // 创建一个连接 32 | Connection connection = factory.newConnection(); 33 | // 创建一个频道 34 | Channel channel = connection.createChannel(); 35 | // 指定一个队列 36 | channel.queueDeclare(QUEUE_NAME, false, false, false, null); 37 | //发送的消息 38 | String message = JSON.toJSONString(map); 39 | // 往队列中发出一条消息 40 | channel.basicPublish("", QUEUE_NAME, null, message.getBytes()); //发送 41 | System.out.println(" [x] Sent '" + message + "'"); 42 | // 关闭频道和连接 43 | channel.close(); 44 | connection.close(); 45 | 46 | 47 | 48 | } 49 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/demo/C.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.demo; 2 | 3 | import java.io.IOException; 4 | 5 | import com.rabbitmq.client.AMQP; 6 | import com.rabbitmq.client.Channel; 7 | import com.rabbitmq.client.Connection; 8 | import com.rabbitmq.client.ConnectionFactory; 9 | import com.rabbitmq.client.Consumer; 10 | import com.rabbitmq.client.DefaultConsumer; 11 | import com.rabbitmq.client.Envelope; 12 | 13 | 14 | //消费者 15 | public class C { 16 | 17 | private final static String QUEUE_NAME = "RabbitMQ_Hello"; //消息队列名 18 | 19 | public static void main(String[] argv) throws Exception { 20 | // 创建连接工厂 21 | ConnectionFactory factory = new ConnectionFactory(); 22 | // 设置RabbitMQ地址 23 | factory.setHost("127.0.0.1"); 24 | // 创建一个新的连接 25 | Connection connection = factory.newConnection(); 26 | // 创建一个频道 27 | Channel channel = connection.createChannel(); 28 | // 声明要关注的队列 -- 在RabbitMQ中,队列声明是幂等性的(一个幂等操作的特点是其任意多次执行所产生的影响均与一次执行的影响相同),也就是说,如果不存在,就创建,如果存在,不会对已经存在的队列产生任何影响。 29 | channel.queueDeclare(QUEUE_NAME, false, false, false, null); 30 | System.out.println("C [*] Waiting for messages. To exit press CTRL+C"); 31 | // DefaultConsumer类实现了Consumer接口,通过传入一个频道,告诉服务器我们需要那个频道的消息,如果频道中有消息,就会执行回调函数handleDelivery 32 | Consumer consumer = new DefaultConsumer(channel) { 33 | @Override 34 | public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException { 35 | String message = new String(body, "UTF-8"); 36 | System.out.println("C [x] Received '" + message + "'"); 37 | } 38 | }; 39 | // 自动回复队列应答 -- RabbitMQ中的消息确认机制 40 | channel.basicConsume(QUEUE_NAME, true, consumer); 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/one2one/ClientSend1.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.one2one; 2 | import java.net.URISyntaxException; 3 | import java.security.KeyManagementException; 4 | import java.security.NoSuchAlgorithmException; 5 | import java.util.concurrent.TimeoutException; 6 | 7 | import com.rabbitmq.client.Channel; 8 | import com.rabbitmq.client.Connection; 9 | import com.rabbitmq.client.ConnectionFactory; 10 | import com.rabbitmq.client.MessageProperties; 11 | public class ClientSend1 { 12 | public static final String queue_name="my_queue"; 13 | public static final boolean durable=true; //消息队列持久化 14 | public static void main(String[] args) 15 | throws java.io.IOException, TimeoutException, KeyManagementException, NoSuchAlgorithmException, URISyntaxException{ 16 | ConnectionFactory factory=new ConnectionFactory(); //创建连接工厂 17 | // factory.setHost("localhost"); 18 | // factory.setVirtualHost("my_mq"); 19 | // factory.setUsername("zhxia"); 20 | // factory.setPassword("123456"); 21 | factory.setUri("amqp://guest:guest@172.26.129.3:5672");//获取url 22 | Connection connection=factory.newConnection(); //创建连接 23 | Channel channel=connection.createChannel();//创建信道 24 | channel.queueDeclare(queue_name, durable, false, false, null); //声明消息队列,且为可持久化的 25 | String message="Hello world"+Math.random(); 26 | //将队列设置为持久化之后,还需要将消息也设为可持久化的,MessageProperties.PERSISTENT_TEXT_PLAIN 27 | channel.basicPublish("", queue_name, MessageProperties.PERSISTENT_TEXT_PLAIN,message.getBytes()); 28 | System.out.println("Send message:"+message); 29 | channel.close(); 30 | connection.close(); 31 | } 32 | 33 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/one2one/Recv.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.one2one; 2 | import java.util.ArrayList; 3 | import java.util.List; 4 | 5 | import com.rabbitmq.client.Channel; 6 | import com.rabbitmq.client.Connection; 7 | import com.rabbitmq.client.ConnectionFactory; 8 | import com.rabbitmq.client.QueueingConsumer; 9 | 10 | 11 | //消费者 (Consumer:数据的接收方) 12 | //单发送单接收 Send.java和Recv.java类 13 | public class Recv { 14 | 15 | private final static String QUEUE_NAME = "header_exchange"; 16 | 17 | public static void main(String[] argv) throws Exception { 18 | 19 | ConnectionFactory factory = new ConnectionFactory(); 20 | // factory.setHost("localhost"); 21 | // factory.setHost("127.0.0.1"); 22 | factory.setUri("amqp://guest:guest@172.26.129.3:5672");//获取url 23 | // 打开连接和创建频道,与发送端一样 24 | Connection connection = factory.newConnection(); 25 | Channel channel = connection.createChannel(); 26 | // 声明队列,主要为了防止消息接收者先运行此程序,队列还不存在时创建队列。 27 | channel.queueDeclare(QUEUE_NAME, false, false, false, null); 28 | System.out.println(" [*] Waiting for messages. To exit press CTRL+C"); 29 | // 创建队列消费者 30 | QueueingConsumer consumer = new QueueingConsumer(channel); 31 | // 指定消费队列 32 | channel.basicConsume(QUEUE_NAME, true, consumer); 33 | while (true) { //消费者程序运行开着 如果生产者新增了数据会自动获取 34 | Thread.sleep(500); 35 | List aa=new ArrayList(); 36 | // nextDelivery是一个阻塞方法(内部实现其实是阻塞队列的take方法) 37 | QueueingConsumer.Delivery delivery = consumer.nextDelivery(); 38 | String message = new String(delivery.getBody()); 39 | aa.add(message); 40 | System.out.println("你好吗!"+" [x] Received '" + message + "'"+aa); 41 | } 42 | 43 | } 44 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/others/TestConsumer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.others; 2 | 3 | import java.util.Arrays; 4 | import java.util.Properties; 5 | 6 | import org.apache.kafka.clients.consumer.ConsumerRecord; 7 | import org.apache.kafka.clients.consumer.ConsumerRecords; 8 | import org.apache.kafka.clients.consumer.KafkaConsumer; 9 | 10 | public class TestConsumer { 11 | 12 | public static void main(String[] args) { 13 | Properties props = new Properties(); 14 | 15 | props.put("bootstrap.servers", "192.169.0.23:9092"); 16 | System.out.println("this is the group part test 1"); 17 | //消费者的组id 18 | props.put("group.id", "GroupA");//这里是GroupA或者GroupB 19 | 20 | props.put("enable.auto.commit", "true"); 21 | props.put("auto.commit.interval.ms", "1000"); 22 | 23 | //从poll(拉)的回话处理时长 24 | props.put("session.timeout.ms", "30000"); 25 | //poll的数量限制 26 | //props.put("max.poll.records", "100"); 27 | 28 | props.put("key.deserializer", "org.apache.kafka.common.serialization.StringDeserializer"); 29 | 30 | props.put("value.deserializer", "org.apache.kafka.common.serialization.StringDeserializer"); 31 | 32 | KafkaConsumer consumer = new KafkaConsumer(props); 33 | //订阅主题列表topic 34 | consumer.subscribe(Arrays.asList("foo")); 35 | while (true) { 36 | ConsumerRecords records =consumer.poll(100); 37 | for (ConsumerRecord record : records) 38 | // 正常这里应该使用线程池处理,不应该在这里处理 39 | System.out.printf("offset = %d, key = %s, value = %s", record.offset(), record.key(), record.value()+"\n"); 40 | } 41 | } 42 | 43 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/ThreadTest4.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | 3 | /** 4 | * 5 | * Title: ThreadTest4 6 | * Description: 7 | * 死锁测试 8 | * Version:1.0.0 9 | * @author pancm 10 | * @date 2018年3月8日 11 | */ 12 | public class ThreadTest4 { 13 | static class Friend { 14 | private final String name; 15 | 16 | public Friend(String name) { 17 | this.name = name; 18 | } 19 | 20 | public String getName() { 21 | return this.name; 22 | } 23 | 24 | public synchronized void bow(Friend bower) { 25 | System.out.format("%s: %s" + " 早上好!%n", this.name, bower.getName()); 26 | bower.bowBack(this); 27 | } 28 | 29 | public synchronized void bowBack(Friend bower) { 30 | System.out.format("%s: %s" + " 你也是!%n", this.name, bower.getName()); 31 | } 32 | } 33 | 34 | /** 35 | * 两个线程都在等在对方释放资源,但是都不会释放,这就是死锁。 36 | * @param args 37 | */ 38 | public static void main(String[] args) { 39 | final Friend zhangsan = new Friend("张三"); 40 | final Friend lisi = new Friend("李四"); 41 | new Thread(new Runnable() { 42 | public void run() { 43 | zhangsan.bow(lisi); 44 | } 45 | }).start(); 46 | new Thread(new Runnable() { 47 | public void run() { 48 | lisi.bow(zhangsan); 49 | } 50 | }).start(); 51 | 52 | /** 53 | * 正常的返回结果应该是: 54 | * 张三: 李四 早上好! 55 | 李四: 张三 你也是! 56 | 李四: 张三 早上好! 57 | 张三: 李四 你也是! 58 | * 因为去掉了synchronized同步锁! 59 | * 60 | * 但实际结果是: 61 | * 张三: 李四 早上好! 62 | 李四: 张三 早上好! 63 | * 并且线程不会结束! 64 | */ 65 | 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo1/MyTextLineCodecEncoder.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo1; 2 | 3 | import java.nio.charset.Charset; 4 | 5 | import org.apache.log4j.Logger; 6 | import org.apache.mina.core.buffer.IoBuffer; 7 | import org.apache.mina.core.session.IoSession; 8 | import org.apache.mina.filter.codec.ProtocolEncoder; 9 | import org.apache.mina.filter.codec.ProtocolEncoderOutput; 10 | 11 | /** 12 | * @author ZERO 13 | * @version 2017-3-28 上午11:30:55 14 | * 设置编码构造器 15 | */ 16 | public class MyTextLineCodecEncoder implements ProtocolEncoder{ 17 | 18 | private static Logger logger = Logger.getLogger(MyTextLineCodecEncoder.class); 19 | 20 | private Charset charset; // 编码格式 21 | private String delimiter; // 文本分隔符 22 | public MyTextLineCodecEncoder(Charset charset, String delimiter) { 23 | this.charset = charset; 24 | this.delimiter = delimiter; 25 | } 26 | 27 | public void encode(IoSession session, Object message, ProtocolEncoderOutput out) throws Exception { 28 | logger.info("开始进入编码方法-----------------------------------------------------------------"); 29 | // 如果文本换行符未指定,使用默认值 30 | if (delimiter == null || "".equals(delimiter)) { 31 | delimiter = "\r\n"; 32 | } 33 | 34 | if (charset == null) { 35 | charset = Charset.forName("utf-8"); 36 | } 37 | 38 | String value = message.toString(); 39 | IoBuffer buf = IoBuffer.allocate(value.length()).setAutoExpand(true); 40 | //真实数据 41 | buf.putString(value, charset.newEncoder()); 42 | //文本换行符 43 | buf.putString(delimiter, charset.newEncoder()); 44 | buf.flip(); 45 | out.write(buf); 46 | } 47 | 48 | public void dispose(IoSession session) throws Exception {} 49 | 50 | } 51 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo4/NettySendBody.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo4; 2 | 3 | import java.io.Serializable; 4 | import java.util.concurrent.ConcurrentHashMap; 5 | 6 | /** 7 | * 8 | * Description: Netty 传输对象 9 | * Version:1.0.0 10 | * @author pancm 11 | * @date 2017年9月24日 12 | */ 13 | public class NettySendBody implements Serializable{ 14 | 15 | /** 16 | * 序列化 17 | */ 18 | private static final long serialVersionUID = 1L; 19 | 20 | 21 | /** 创建集合 */ 22 | private ConcurrentHashMap data; 23 | /** 时间戳 */ 24 | private long timestamp; 25 | 26 | public NettySendBody() { 27 | data = new ConcurrentHashMap(); 28 | timestamp = System.currentTimeMillis(); //取当前时间 29 | } 30 | 31 | 32 | public ConcurrentHashMap getData() { 33 | return data; 34 | } 35 | 36 | public void setData(ConcurrentHashMap data) { 37 | this.data = data; 38 | } 39 | 40 | public long getTimestamp() { 41 | return timestamp; 42 | } 43 | 44 | public void setTimestamp(long timestamp) { 45 | this.timestamp = timestamp; 46 | } 47 | 48 | public String get(String k) { 49 | return data.get(k); 50 | } 51 | 52 | public void put(String k, String v) { 53 | data.put(k, v); 54 | } 55 | 56 | 57 | @Override 58 | public String toString() { 59 | StringBuffer buffer = new StringBuffer(); 60 | buffer.append(""); 61 | buffer.append(""); 62 | buffer.append("").append(timestamp).append(""); 63 | buffer.append(""); 64 | for (String key : data.keySet()) { 65 | buffer.append("<" + key + ">").append(data.get(key)).append( 66 | ""); 67 | } 68 | buffer.append(""); 69 | buffer.append(""); 70 | return buffer.toString(); 71 | } 72 | 73 | 74 | } 75 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/StaticTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | /** 4 | * 5 | * @Title: StaticTest 6 | * @Description: 构造块和静态方法测试 7 | * @Version:1.0.0 8 | * @author Administrator 9 | * @date 2017-8-14 10 | */ 11 | public class StaticTest { 12 | public static StaticTest t1 = new StaticTest(); 13 | public static StaticTest t2 = new StaticTest(); 14 | { 15 | System.out.println("构造块"); 16 | } 17 | static { 18 | System.out.println("静态块"); 19 | } 20 | 21 | public static void main(String[] args) { 22 | StaticTest t = new StaticTest(); // 构造块 构造块 静态块 构造块 23 | 24 | 25 | // new HelloA(); extends HelloA 26 | new HelloB(); //3 27 | /* 28 | * 总结:创建对象时构造器的调用顺序是:先初始化静态成员,然后调用父类构造器,再初始化非静态成员,最后调用自身构造器。 29 | */ 30 | 31 | /* 32 | * 总结 开始时JVM加载B.class,对所有的静态成员进行声明,t1 t2被初始化为默认值,为null, 又因为t1 33 | * t2需要被显式初始化,所以对t1进行显式初始化,初始化代码块→构造函数(没有就是调用默认的构造函数), 34 | * 咦!静态代码块咋不初始化?因为在开始时已经对static部分进行了初始化,虽然只对static变量进行了初始化, 35 | * 但在初始化t1时也不会再执行static块了,因为JVM认为这是第二次加载类B了,所以static会在t1初始化时被忽略掉, 36 | * 所以直接初始化非static部分,也就是构造块部分(输出''构造块'')接着构造函数(无输出)。 37 | * 接着对t2进行初始化过程同t1相同(输出'构造块'),此时就对所有的static变量都完成了初始化, 38 | * 接着就执行static块部分(输出'静态块'),接着执行,main方法,同样也,new了对象, 调用构造函数输出('构造块') 39 | * 40 | */ 41 | 42 | } 43 | 44 | } 45 | 46 | class HelloA { 47 | private int i=10; 48 | public HelloA() { 49 | System.out.println("HelloA"); //5 50 | } 51 | 52 | { System.out.println("I'm A class"); } //4 53 | 54 | static { System.out.println("static A"); } //1 55 | 56 | } 57 | class HelloB extends HelloA{ 58 | private int j=12; 59 | public HelloB() { 60 | System.out.println("HelloB"); //7 61 | } 62 | 63 | { System.out.println("I'm B class"); } //6 64 | 65 | static { System.out.println("static B"); } //2 66 | 67 | 68 | 69 | 70 | 71 | } 72 | 73 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/composite/CompositeTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.composite; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | /** 7 | * @Title: CompositeTest 8 | * @Description: 组合模式 9 | * 将对象组合成树形结构以表示"部分-整体"的层次结构。组合模式使得用户对单个对象和组合对象的使用具有一致性。 10 | * @Version:1.0.0 11 | * @author pancm 12 | * @date 2018年8月8日 13 | */ 14 | public class CompositeTest { 15 | 16 | public static void main(String[] args) { 17 | /* 18 | * 建立一个学生类,包含学生姓名和职位 19 | * 20 | */ 21 | Student studentLeader=new Student("小明","学生会主席"); 22 | 23 | Student committeeMember=new Student("小刚","学生会委员"); 24 | 25 | Student student=new Student("小红","学生"); 26 | 27 | committeeMember.add(student); 28 | studentLeader.add(committeeMember); 29 | 30 | System.out.println("-"+studentLeader); 31 | studentLeader.get().forEach(sl->{ 32 | System.out.println("--"+sl); 33 | sl.get().forEach(cm->{ 34 | System.out.println("---"+cm); 35 | }); 36 | }); 37 | 38 | /* 39 | * -Student [name=小明, position=学生会主席] 40 | --Student [name=小刚, position=学生会委员] 41 | ---Student [name=小红, position=学生] 42 | */ 43 | } 44 | 45 | } 46 | 47 | class Student{ 48 | private String name; 49 | 50 | private String position; 51 | 52 | private List students; 53 | 54 | public Student(String name, String position) { 55 | this.name = name; 56 | this.position = position; 57 | students=new ArrayList(); 58 | } 59 | 60 | 61 | public void add(Student student){ 62 | students.add(student); 63 | } 64 | 65 | public void remove(Student student){ 66 | students.remove(student); 67 | } 68 | 69 | public List get(){ 70 | return students; 71 | } 72 | 73 | 74 | /** 75 | * 76 | */ 77 | @Override 78 | public String toString() { 79 | return "Student [name=" + name + ", position=" + position + "]"; 80 | } 81 | 82 | 83 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/one2more/NewTask.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.one2more; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import com.rabbitmq.client.Channel; 7 | import com.rabbitmq.client.Connection; 8 | import com.rabbitmq.client.ConnectionFactory; 9 | import com.rabbitmq.client.MessageProperties; 10 | 11 | //生产者 ( Producer:数据的发送方) 12 | //单发送多接收 Worker.java和NewTask.java 13 | public class NewTask { 14 | 15 | private static final String TASK_QUEUE_NAME = "task_queue"; 16 | 17 | public static void main(String[] argv) throws Exception { 18 | // 创建工厂类 19 | ConnectionFactory factory = new ConnectionFactory(); 20 | //factory.setHost("localhost"); 21 | factory.setUri("amqp://guest:guest@172.26.129.3:5672"); 22 | Connection connection = factory.newConnection(); 23 | Channel channel = connection.createChannel(); 24 | 25 | channel.queueDeclare(TASK_QUEUE_NAME, true, false, false, null); 26 | Map map=new HashMap(); 27 | map.put("aa", 11); 28 | map.put("bb", 22); 29 | map.put("cc", 33); 30 | String message = getMessage(argv); 31 | 32 | channel.basicPublish("", TASK_QUEUE_NAME, 33 | MessageProperties.PERSISTENT_TEXT_PLAIN, message.getBytes()); 34 | System.out.println(" [x] Sent '" + message + "'"); 35 | 36 | channel.close(); 37 | connection.close(); 38 | } 39 | 40 | private static String getMessage(String[] strings) { 41 | if (strings.length < 1) { 42 | return "Hello!"; 43 | } 44 | return joinStrings(strings, " "); 45 | } 46 | 47 | private static String joinStrings(String[] strings, String delimiter) { 48 | int length = strings.length; 49 | if (length == 0) { 50 | return ""; 51 | } 52 | StringBuilder words = new StringBuilder(strings[0]); 53 | for (int i = 1; i < length; i++) { 54 | words.append(delimiter).append(strings[i]); 55 | } 56 | return words.toString(); 57 | } 58 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/question/QuestionTest1.java: -------------------------------------------------------------------------------- 1 | package com.pancm.question; 2 | 3 | /** 4 | * @Title: QuestionTest1 5 | * @Description: 6 | * @Version:1.0.0 7 | * @author pancm 8 | * @date 2017年7月21日 9 | */ 10 | public class QuestionTest1 { 11 | 12 | /** 13 | * @param args 14 | */ 15 | public static void main(String[] args) { 16 | 17 | /* 18 | * 在一个二维数组中,每一行都按照从左到右递增的顺序排序, 每一列都按照从上到下递增的顺序排序。请完成一个函数, 19 | * 输入这样的一个二维数组和一个整数,判断数组中是否含有该整数。 20 | */ 21 | int target = 4; 22 | int target1 = 5; 23 | int target2 = 6; 24 | int[][] array = { { 1, 2, 3, 4 }, { 1, 2, 3, 4, 5 } }; 25 | System.out.println(Find(target, array)); 26 | System.out.println(Find(target1, array)); 27 | System.out.println(Find(target2, array)); 28 | System.out.println(Find2(target, array)); 29 | System.out.println(Find2(target1, array)); 30 | System.out.println(Find2(target2, array)); 31 | 32 | 33 | 34 | } 35 | 36 | /** 37 | * 方法一:最笨的方法,利用双重循环找到 38 | * 39 | * @param target 40 | * @param array 41 | * @return 42 | */ 43 | public static boolean Find(int target, int[][] array) { 44 | for (int[] i : array) { 45 | for (int j : i) { 46 | if (j == target) { 47 | return true; 48 | } 49 | } 50 | } 51 | return false; 52 | } 53 | 54 | /** 55 | * 方法二: 最优解法。 思路:首先我们选择从左下角开始搜寻, (为什么不从左上角开始搜寻,左上角向右和向下都是递增,那么对于一个点, 56 | * 对于向右和向下会产生一个岔路;如果我们选择从左下脚开始搜寻的话, 如果大于就向右,如果小于就向下)。 57 | * 58 | * @param target 59 | * @param array 60 | * @return 61 | */ 62 | public static boolean Find2(int target, int[][] array) { 63 | int len = array.length - 1; // 得出二维数组的列长度 64 | int i = 0; 65 | while ((len > 0) && (i < array[0].length)) { 66 | if (array[len][i] > target) { // 如果左下角的数值大于要找的数字,则向右,否则向下 67 | len--; 68 | } else if (array[len][i] < target) { 69 | i++; 70 | } else { 71 | return true; 72 | } 73 | } 74 | return false; 75 | } 76 | 77 | } 78 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/examples/Producer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.examples; 2 | 3 | import java.util.Properties; 4 | 5 | import org.apache.kafka.clients.producer.KafkaProducer; 6 | import org.apache.kafka.clients.producer.ProducerRecord; 7 | import org.apache.kafka.common.serialization.StringSerializer; 8 | 9 | /** 10 | * 11 | * Title: Producer 12 | * Description: kafka生产者 由于生产消息 13 | * Version:1.0.0 14 | * @author pancm 15 | * @date 2017年12月29日 16 | */ 17 | public class Producer extends Thread { 18 | 19 | private final KafkaProducer producer; 20 | private final String topic; 21 | 22 | /** 23 | * 24 | * @param kafkaStr kafka地址 25 | * @param topic 消息名称 26 | * @param 27 | */ 28 | public Producer(String kafkaStr, String topic) { 29 | Properties props = new Properties(); 30 | props.put("bootstrap.servers", kafkaStr); 31 | props.put("acks", "all"); 32 | props.put("retries", 0); 33 | props.put("batch.size", 16384); 34 | props.put("linger.ms", 1); 35 | props.put("buffer.memory", 33554432); 36 | props.put("key.serializer", StringSerializer.class.getName()); 37 | props.put("value.serializer", StringSerializer.class.getName()); 38 | this.producer = new KafkaProducer(props); 39 | this.topic = topic; 40 | } 41 | 42 | @Override 43 | public void run() { 44 | int messageNo = 1; 45 | try { 46 | while (true) { 47 | String messageStr = "Message_" + messageNo; 48 | //生产了100条就打印 49 | if(messageNo%100==0){ 50 | System.out.println("Send:" + messageStr); 51 | } 52 | //生产1000条就退出 53 | // if(messageNo%1000==0){ 54 | // break; 55 | // } 56 | producer.send(new ProducerRecord(topic, "Message", messageStr)); 57 | messageNo++; 58 | sleep(10); 59 | } 60 | } catch (Exception e) { 61 | e.printStackTrace(); 62 | } finally { 63 | producer.close(); 64 | } 65 | } 66 | 67 | } 68 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test2/App.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.test2; 2 | 3 | import org.apache.storm.Config; 4 | import org.apache.storm.LocalCluster; 5 | import org.apache.storm.StormSubmitter; 6 | import org.apache.storm.topology.TopologyBuilder; 7 | import org.apache.storm.tuple.Fields; 8 | 9 | /** 10 | * 11 | * Title: App 12 | * Description: 13 | * storm测试 14 | * Version:1.0.0 15 | * @author pancm 16 | * @date 2018年3月6日 17 | */ 18 | public class App { 19 | 20 | private static final String test_spout="test_spout"; 21 | private static final String test_bolt="test_bolt"; 22 | private static final String test2_bolt="test2_bolt"; 23 | 24 | public static void main(String[] args) { 25 | //定义一个拓扑 26 | TopologyBuilder builder=new TopologyBuilder(); 27 | //设置两个Executeor(线程),默认一个 28 | builder.setSpout(test_spout, new TestSpout(),2); 29 | //shuffleGrouping:表示是随机分组 30 | //设置两个Executeor(线程),和两个task 31 | builder.setBolt(test_bolt, new TestBolt(),2).setNumTasks(2).shuffleGrouping(test_spout); 32 | //fieldsGrouping:表示是按字段分组 33 | //设置两个Executeor(线程),和两个task 34 | builder.setBolt(test2_bolt, new Test2Bolt(),2).setNumTasks(2).fieldsGrouping(test_bolt, new Fields("count")); 35 | Config conf = new Config(); 36 | conf.put("test", "test"); 37 | try{ 38 | //运行拓扑 39 | if(args !=null&&args.length>0){ //有参数时,表示向集群提交作业,并把第一个参数当做topology名称 40 | System.out.println("运行远程模式"); 41 | StormSubmitter.submitTopology(args[0], conf, builder.createTopology()); 42 | } else{//没有参数时,本地提交 43 | //启动本地模式 44 | System.out.println("运行本地模式"); 45 | LocalCluster cluster = new LocalCluster(); 46 | cluster.submitTopology("Word-counts" ,conf, builder.createTopology() ); 47 | Thread.sleep(20000); 48 | // //关闭本地集群 49 | cluster.shutdown(); 50 | } 51 | }catch (Exception e){ 52 | e.printStackTrace(); 53 | } 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/one2one/ClientReceive1.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.one2one; 2 | import java.net.URISyntaxException; 3 | import java.security.KeyManagementException; 4 | import java.security.NoSuchAlgorithmException; 5 | import java.util.concurrent.TimeoutException; 6 | 7 | import com.rabbitmq.client.Channel; 8 | import com.rabbitmq.client.Connection; 9 | import com.rabbitmq.client.ConnectionFactory; 10 | import com.rabbitmq.client.QueueingConsumer; 11 | public class ClientReceive1 { 12 | public static final String queue_name="my_queue"; 13 | public static final boolean autoAck=false; 14 | public static final boolean durable=true; 15 | public static void main(String[] args) 16 | throws java.io.IOException,java.lang.InterruptedException, TimeoutException, KeyManagementException, NoSuchAlgorithmException, URISyntaxException{ 17 | ConnectionFactory factory=new ConnectionFactory(); 18 | // factory.setHost("localhost"); 19 | // factory.setVirtualHost("my_mq"); 20 | // factory.setUsername("zhxia"); 21 | // factory.setPassword("123456"); 22 | factory.setUri("amqp://guest:guest@172.26.129.3:5672");//获取url 23 | Connection connection=factory.newConnection(); 24 | Channel channel=connection.createChannel(); 25 | channel.queueDeclare(queue_name, durable, false, false, null); 26 | System.out.println("Wait for message"); 27 | channel.basicQos(1); //消息分发处理 28 | QueueingConsumer consumer=new QueueingConsumer(channel); 29 | channel.basicConsume(queue_name, autoAck, consumer); 30 | while(true){ 31 | Thread.sleep(500); 32 | QueueingConsumer.Delivery deliver=consumer.nextDelivery(); 33 | String message=new String(deliver.getBody()); 34 | System.out.println("Message received:"+message); 35 | channel.basicAck(deliver.getEnvelope().getDeliveryTag(), false); 36 | } 37 | } 38 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo1/MinaServer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo1; 2 | 3 | import java.net.InetSocketAddress; 4 | import java.nio.charset.Charset; 5 | 6 | import org.apache.log4j.Logger; 7 | import org.apache.mina.core.service.IoAcceptor; 8 | import org.apache.mina.core.session.IdleStatus; 9 | import org.apache.mina.filter.codec.ProtocolCodecFilter; 10 | import org.apache.mina.transport.socket.nio.NioSocketAcceptor; 11 | 12 | 13 | 14 | 15 | 16 | 17 | /** 18 | * @author ZERO: 19 | * @version 2017-3-28 上午10:20:11 20 | * 创建服务端 21 | */ 22 | public class MinaServer { 23 | //记录日志 24 | public static Logger logger=Logger.getLogger(MinaServer.class); 25 | private static int PORT=3305; 26 | 27 | /* 启动此类 提示服务端运行成功后 28 | * Windows 命令 输入 telnet 127.0.0.1 3305 29 | * 然后输入消息 message 30 | * 消息为bye的时候关闭连接 31 | * */ 32 | public static void main(String[] args) { 33 | new MinaServer().start(); 34 | } 35 | 36 | public void start() { 37 | IoAcceptor ia=null; 38 | try{ 39 | //创建一个非堵塞的server端Socket 40 | ia=new NioSocketAcceptor(); 41 | //创建 自定义协议编码解码过滤器ProtocolCodecFilter 42 | ProtocolCodecFilter pf=new ProtocolCodecFilter((new MyTextLineCodecFactory(Charset .forName("utf-8"), "\r\n"))); 43 | //设置端口 44 | InetSocketAddress pt=new InetSocketAddress(PORT); 45 | // 设置过滤器(使用Mina提供的文本换行符编解码器) 46 | ia.getFilterChain().addLast("codec", pf); 47 | //设置读取数据的缓存区大小 48 | ia.getSessionConfig().setReadBufferSize(2048); 49 | //读写通道10秒内无操作进入空闲状态 50 | ia.getSessionConfig().setIdleTime(IdleStatus.BOTH_IDLE, 10); 51 | //绑定逻辑处理器 52 | ia.setHandler(new MinaServerHandler()); 53 | //绑定端口 54 | ia.bind(pt); 55 | logger.info("服务端启动成功...端口号为:"+PORT); 56 | 57 | }catch(Exception e){ 58 | logger.error("服务器的异常..."+e); 59 | e.printStackTrace(); 60 | } 61 | 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/lock/LockTest2.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.lock; 2 | 3 | import java.util.concurrent.locks.Condition; 4 | import java.util.concurrent.locks.Lock; 5 | import java.util.concurrent.locks.ReentrantLock; 6 | 7 | /** 8 | * 9 | * @Title: LockTest2 10 | * @Description: 显示锁的唤醒测试 11 | * @Version:1.0.0 12 | * @author pancm 13 | * @date 2018年2月28日 14 | */ 15 | public class LockTest2 { 16 | final Lock lock = new ReentrantLock(); 17 | 18 | final Condition notfull = lock.newCondition(); 19 | 20 | final Condition notempty = lock.newCondition(); 21 | 22 | final Object[] items = new Object[100]; 23 | 24 | int putptr, takeptr, count; 25 | 26 | public static void main(String[] args) throws InterruptedException { 27 | LockTest2 lt = new LockTest2(); 28 | Object obj = 2; 29 | lt.put(obj); 30 | lt.take(); 31 | } 32 | 33 | /** 34 | * 而现在锁是指定对象lock。所以查找等待唤醒机制方式需要通过lock接口来完成。 35 | * 而lock接口中并没有直接操作等待唤醒的方法,而是将这些方式又单独封装到了一个对象中。 36 | * 这个对象就是condition,将object中的三个方法进行单独的封装。 并提供了功能一致的方法 37 | * await()、signal()、signalall()体现新版本对象的好处。 38 | * 39 | * @param x 40 | * @throws InterruptedException 41 | */ 42 | public void put(Object x) throws InterruptedException { 43 | lock.lock(); 44 | try { 45 | while (count == items.length) { 46 | notfull.await(); 47 | } 48 | items[putptr] = x; 49 | 50 | if (++putptr == items.length) { 51 | putptr = 0; 52 | } 53 | ++count; 54 | //唤醒一个等待的线程 55 | notempty.signal(); 56 | 57 | } finally { 58 | lock.unlock(); 59 | } 60 | } 61 | 62 | private Object take() throws InterruptedException { 63 | lock.lock(); 64 | try { 65 | while (count == 0) { 66 | notempty.await(); 67 | } 68 | Object x = items[takeptr]; 69 | 70 | if (++takeptr == items.length) { 71 | takeptr = 0; 72 | } 73 | --count; 74 | //唤醒一个等待的线程 75 | notfull.signal(); 76 | return x; 77 | 78 | } finally { 79 | lock.unlock(); 80 | } 81 | } 82 | 83 | } 84 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test2/TestBolt.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.test2; 2 | 3 | import java.util.Map; 4 | 5 | import org.apache.storm.task.OutputCollector; 6 | import org.apache.storm.task.TopologyContext; 7 | import org.apache.storm.topology.OutputFieldsDeclarer; 8 | import org.apache.storm.topology.base.BaseRichBolt; 9 | import org.apache.storm.tuple.Fields; 10 | import org.apache.storm.tuple.Tuple; 11 | import org.apache.storm.tuple.Values; 12 | 13 | 14 | /** 15 | * 16 | * Title: TestBolt 17 | * Description: 18 | * 对单词进行分割 19 | * Version:1.0.0 20 | * @author pancm 21 | * @date 2018年3月16日 22 | */ 23 | public class TestBolt extends BaseRichBolt{ 24 | 25 | /** 26 | * 27 | */ 28 | private static final long serialVersionUID = 4743224635827696343L; 29 | 30 | private OutputCollector collector; 31 | 32 | /** 33 | * 在Bolt启动前执行,提供Bolt启动环境配置的入口 34 | * 一般对于不可序列化的对象进行实例化。 35 | * 注:如果是可以序列化的对象,那么最好是使用构造函数。 36 | */ 37 | @Override 38 | public void prepare(Map map, TopologyContext arg1, OutputCollector collector) { 39 | System.out.println("prepare:"+map.get("test")); 40 | this.collector=collector; 41 | } 42 | 43 | /** 44 | * execute()方法是Bolt实现的核心。 45 | * 也就是执行方法,每次Bolt从流接收一个订阅的tuple,都会调用这个方法。 46 | */ 47 | @Override 48 | public void execute(Tuple tuple) { 49 | String msg=tuple.getStringByField("word"); 50 | System.out.println("开始分割单词:"+msg); 51 | String[] words = msg.toLowerCase().split(" "); 52 | for (String word : words) { 53 | this.collector.emit(new Values(word));//向下一个bolt发射数据 54 | } 55 | 56 | } 57 | 58 | /** 59 | * 声明数据格式 60 | */ 61 | @Override 62 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 63 | declarer.declare(new Fields("count")); 64 | } 65 | 66 | /** 67 | * cleanup是IBolt接口中定义,用于释放bolt占用的资源。 68 | * Storm在终止一个bolt之前会调用这个方法。 69 | */ 70 | @Override 71 | public void cleanup() { 72 | System.out.println("TestBolt的资源释放"); 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/rabbitmq/one2more/Worker.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.rabbitmq.one2more; 2 | import com.rabbitmq.client.Channel; 3 | import com.rabbitmq.client.Connection; 4 | import com.rabbitmq.client.ConnectionFactory; 5 | import com.rabbitmq.client.QueueingConsumer; 6 | //消费者 (Consumer:数据的接收方) 7 | //单发送多接收 Worker.java和NewTask.java 8 | public class Worker { 9 | 10 | private static final String TASK_QUEUE_NAME = "task_queue"; 11 | // private static final String TASK_QUEUE_NAME = "tsk.hybris.productbrand.tsk"; 12 | 13 | public static void main(String[] argv) throws Exception { 14 | 15 | ConnectionFactory factory = new ConnectionFactory(); 16 | //factory.setHost("localhost"); 17 | factory.setUri("amqp://guest:guest@172.26.129.3:5672"); 18 | Connection connection = factory.newConnection(); 19 | Channel channel = connection.createChannel(); 20 | 21 | channel.queueDeclare(TASK_QUEUE_NAME, true, false, false, null);//queue的持久化需要在声明时指定durable=True 22 | System.out.println(" [*] Waiting for messages. To exit press CTRL+C"); 23 | //保证在接收端一个消息没有处理完时不会接收另一个消息 24 | channel.basicQos(1); 25 | // channel.basicQos(0, 1, false); //这样RabbitMQ就会使得每个Consumer在同一个时间点最多处理一个Message。换句话说,在接收到该Consumer的ack前,他它不会将新的Message分发给它。 26 | 27 | QueueingConsumer consumer = new QueueingConsumer(channel); 28 | channel.basicConsume(TASK_QUEUE_NAME, false, consumer); 29 | 30 | while (true) { 31 | QueueingConsumer.Delivery delivery = consumer.nextDelivery(); 32 | String message = new String(delivery.getBody()); 33 | 34 | System.out.println(" [x] Received '" + message + "'"); 35 | doWork(message); 36 | System.out.println(" [x] Done"); 37 | 38 | channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false); 39 | } 40 | } 41 | 42 | private static void doWork(String task) throws InterruptedException { 43 | for (char ch: task.toCharArray()) { 44 | if (ch == '.') { 45 | Thread.sleep(1000); 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo5/NettyServerHandlerDemo5.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo5; 2 | 3 | import io.netty.channel.ChannelHandlerContext; 4 | import io.netty.channel.ChannelInboundHandlerAdapter; 5 | import io.netty.handler.timeout.IdleState; 6 | import io.netty.handler.timeout.IdleStateEvent; 7 | 8 | /** 9 | * 10 | * Description:服务端业务逻辑处理类 11 | * Version:1.0.0 12 | * @author pancm 13 | * @date 2017年9月21日 14 | */ 15 | public class NettyServerHandlerDemo5 extends ChannelInboundHandlerAdapter { 16 | /** 时间 */ 17 | private int loss_connect_time = 0; 18 | /** 发送次数 */ 19 | private int count = 1; 20 | 21 | @Override 22 | public void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception { 23 | if (evt instanceof IdleStateEvent) { 24 | IdleStateEvent event = (IdleStateEvent) evt; 25 | System.out.println("event.state():"+event.state()+",IdleState.READER_IDLE:"+IdleState.READER_IDLE); 26 | if (event.state() == IdleState.READER_IDLE) { 27 | loss_connect_time++; 28 | System.out.println("5 秒没有接收到客户端的信息了"); 29 | if (loss_connect_time > 2) { 30 | System.out.println("关闭这个不活跃的channel"); 31 | ctx.channel().close(); 32 | } 33 | } 34 | } else { 35 | super.userEventTriggered(ctx, evt); 36 | } 37 | } 38 | 39 | 40 | /** 41 | * 处理业务逻辑 42 | */ 43 | @Override 44 | public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception { 45 | System.out.println(" ----- "+msg); 46 | String a="你好啊"+",count:"+count; 47 | ctx.writeAndFlush(a); 48 | count++; 49 | } 50 | 51 | /** 52 | * 异常处理 53 | */ 54 | @Override 55 | public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception { 56 | cause.printStackTrace(); 57 | ctx.close(); 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/examples/Consumer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.examples; 2 | 3 | import java.util.Arrays; 4 | import java.util.Properties; 5 | 6 | import org.apache.kafka.clients.consumer.ConsumerRecord; 7 | import org.apache.kafka.clients.consumer.ConsumerRecords; 8 | import org.apache.kafka.clients.consumer.KafkaConsumer; 9 | import org.apache.kafka.common.serialization.StringDeserializer; 10 | 11 | /** 12 | * 13 | * Title: Consumer 14 | * Description: kafka消费者 15 | * Version:1.0.0 16 | * @author pancm 17 | * @date 2017年12月29日 18 | */ 19 | public class Consumer extends Thread { 20 | 21 | private final KafkaConsumer consumer; 22 | private final String topic; 23 | private static final String GROUPID = "test-consumer-group"; 24 | 25 | public Consumer(String kafkaStr, String topic) { 26 | Properties props = new Properties(); 27 | props.put("bootstrap.servers", kafkaStr); 28 | props.put("group.id", GROUPID); 29 | props.put("enable.auto.commit", "true"); 30 | props.put("auto.commit.interval.ms", "1000"); 31 | props.put("session.timeout.ms", "30000"); 32 | props.put("key.deserializer", StringDeserializer.class.getName()); 33 | props.put("value.deserializer", StringDeserializer.class.getName()); 34 | this.consumer = new KafkaConsumer(props); 35 | this.topic = topic; 36 | } 37 | 38 | @Override 39 | public void run() { 40 | this.consumer.subscribe(Arrays.asList(topic)); 41 | int messageNo = 1; 42 | System.out.println("消费开始---------"); 43 | try { 44 | while (true) { 45 | ConsumerRecords records = consumer.poll(100); 46 | for (ConsumerRecord record : records) { 47 | //消费100条就打印 48 | //打印的数据不一定是这个规律的 49 | if(messageNo%100==0){ 50 | System.out.println("receive: key = " + record.key() + ", value = " + record.value()); 51 | } 52 | } 53 | //当消费了1000条就退出 54 | if(messageNo%1000==0){ 55 | break; 56 | } 57 | messageNo++; 58 | } 59 | } finally { 60 | consumer.close(); 61 | } 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo3/NettyMsg.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo3; 2 | 3 | /** 4 | * 5 | * Description: Netty 自定义消息 6 | * Version:1.0.0 7 | * @author pancm 8 | * @date 2017年9月21日 9 | */ 10 | public class NettyMsg { 11 | 12 | 13 | /** 类型 系统编号 0xAB 表示A系统,0xBC 表示B系统 */ 14 | private byte type; 15 | 16 | /** 信息标志 0xAB 表示心跳包 0xBC 表示超时包 0xCD 业务信息包 */ 17 | private byte flag; 18 | 19 | /** 主题信息的长度 */ 20 | private int length; 21 | 22 | /** 主题信息 */ 23 | private String body; 24 | 25 | public NettyMsg() { 26 | 27 | } 28 | 29 | 30 | /** 31 | * 32 | * @param type 类型 系统编号 0xAB 表示A系统,0xBC 表示B系统 33 | * @param flag 信息标志 0xAB 表示心跳包 0xBC 表示超时包 0xCD 业务信息包 34 | * @param length 主题信息的长度 35 | * @param body 主题信息 36 | */ 37 | public NettyMsg(byte type, byte flag, int length, String body) { 38 | this.type = type; 39 | this.flag = flag; 40 | this.length = length; 41 | this.body = body; 42 | } 43 | 44 | public byte getType() { 45 | return type; 46 | } 47 | 48 | public void setType(byte type) { 49 | this.type = type; 50 | } 51 | 52 | public byte getFlag() { 53 | return flag; 54 | } 55 | 56 | public void setFlag(byte flag) { 57 | this.flag = flag; 58 | } 59 | 60 | public int getLength() { 61 | return length; 62 | } 63 | 64 | public void setLength(int length) { 65 | this.length = length; 66 | } 67 | 68 | public String getBody() { 69 | return body; 70 | } 71 | 72 | public void setBody(String body) { 73 | this.body = body; 74 | } 75 | 76 | /** 77 | * 重写toString方法,方便打印日志 78 | */ 79 | @Override 80 | public String toString() { 81 | return "NettyMsg [type=" + type + ", flag=" + flag + ", length=" 82 | + length + ", body=" + body + "]"; 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/ServletTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | import java.io.IOException; 4 | import java.io.PrintWriter; 5 | 6 | import javax.servlet.ServletException; 7 | import javax.servlet.http.HttpServlet; 8 | import javax.servlet.http.HttpServletRequest; 9 | import javax.servlet.http.HttpServletResponse; 10 | 11 | /** 12 | * 13 | * Title: ServletTest 14 | * Description: 15 | * 部署在tomcat之后,在web.xml添加: 16 | * 17 | testServlet 18 | com.pancm.test.servletTest.testServlet 19 | 20 | 21 | 22 | testServlet 23 | /test.do 24 | 25 | 然后启动tomcat,在浏览器输入 ip:端口/项目名/设置的地址 26 | 就可以访问了 27 | * Version:1.0.0 28 | * @author pancm 29 | * @date 2018年3月20日 30 | */ 31 | public class ServletTest extends HttpServlet { 32 | 33 | /** 34 | * 35 | */ 36 | private static final long serialVersionUID = 1L; 37 | 38 | /** 39 | * 返回结果 40 | */ 41 | private String result = null; 42 | 43 | private long count=1; 44 | 45 | /** 46 | * 47 | */ 48 | @Override 49 | protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 50 | doPost(req, resp); 51 | } 52 | 53 | /** 54 | * 55 | */ 56 | @Override 57 | protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 58 | System.out.println("============"); 59 | System.out.println(req.getParameter("param")); 60 | PrintWriter printWriter=resp.getWriter(); 61 | result = "这是第"+count+"次响应!"; 62 | try { 63 | resp.setCharacterEncoding("utf-8"); 64 | count++; 65 | printWriter.print(result); 66 | } catch (Exception e) { 67 | result="第"+count+"次请求错误!"; 68 | printWriter.print(result); 69 | }finally{ 70 | req=null; 71 | printWriter=null; 72 | resp=null; 73 | } 74 | } 75 | 76 | @Override 77 | public void destroy() { 78 | super.destroy(); 79 | } 80 | } 81 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/lock/LockTest1.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.lock; 2 | 3 | import java.util.concurrent.locks.Lock; 4 | import java.util.concurrent.locks.ReentrantReadWriteLock; 5 | 6 | /** 7 | * 8 | * @Title: LockTest1 9 | * @Description: Lock(显示锁)和synchronized(内部锁) 测试 10 | * @Version:1.0.0 11 | * @author pancm 12 | * @date 2017年10月23日 13 | */ 14 | public class LockTest1 { 15 | 16 | public static void main(String[] args) { 17 | 18 | } 19 | 20 | } 21 | 22 | class Foo{ 23 | /** 可重入的读写锁 */ 24 | private final ReentrantReadWriteLock rwl=new ReentrantReadWriteLock(); 25 | 26 | /** 读锁 */ 27 | private final Lock r=rwl.readLock(); 28 | 29 | /** 写锁 */ 30 | private final Lock w=rwl.writeLock(); 31 | 32 | 33 | //读操作,可并发执行 34 | public void read(){ 35 | try{ 36 | r.lock(); 37 | Thread.sleep(1000); 38 | System.out.println("read......"); 39 | }catch(InterruptedException e){ 40 | e.printStackTrace(); 41 | }finally{ 42 | r.unlock(); 43 | } 44 | } 45 | 46 | //写操作,同时值允许一个执行 47 | public void write(){ 48 | try{ 49 | w.lock(); 50 | Thread.sleep(1000); 51 | System.out.println("write......"); 52 | }catch(InterruptedException e){ 53 | e.printStackTrace(); 54 | }finally{ 55 | w.unlock(); 56 | } 57 | } 58 | 59 | /* 60 | * 1.Lock支持更细粒度的锁控制; 61 | * 2.Lock是无阻塞锁,synchronized是阻塞锁; 62 | * 例:当线程A持有锁的时,线程B也期望获得锁,此时,如果线程是使用的显示锁,则B线程为等待状态(即阻塞); 63 | * 如果使用的是内部锁则为阻塞状态。 64 | * 65 | * 3.Lock可以实现公平锁,而synchronized只能是非公平锁; 66 | * 非公平锁:当一个线程A持有锁,而线程B、C处于阻塞状态时, 若线程A释放锁,JVM将从线程B、C随机选择一个线程持有锁并使其获得执行权, 67 | * 这叫做非公平锁(因为它抛弃了先来后到的顺序); 68 | * 公平锁:若JVM选择了等待时间最长的一个线程持有锁,则为公平锁(保证每个线程的等待时间均衡)。 69 | * 需要注意的是,即使是公平锁,JVM也无法做到准确的“公平”,在程序中不能以此作为计算。 70 | * 显示锁默认是非公平锁,可以在构造函数中增加true来声明公平锁,而synchronized只能是实现非公平锁。 71 | * 72 | * 4.Lock是代码级,synchronized是JVM级的 73 | * Lock是通过编码实现的,synchronized是在运行期由JVM解释的,相对来说synchronized的优化可能性更高, 74 | * 毕竟是在最核心部分支持的,Lock的优化则需要用户自行考虑。 75 | * 灵活、强大选择Lock;快捷、安全选择synchronized。 76 | * 77 | * 78 | * 79 | * 80 | * 81 | */ 82 | 83 | 84 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/one/WordNormalizer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.one; 2 | 3 | import java.util.Map; 4 | 5 | import org.apache.storm.task.OutputCollector; 6 | import org.apache.storm.task.TopologyContext; 7 | import org.apache.storm.topology.IRichBolt; 8 | import org.apache.storm.topology.OutputFieldsDeclarer; 9 | import org.apache.storm.tuple.Fields; 10 | import org.apache.storm.tuple.Tuple; 11 | import org.apache.storm.tuple.Values; 12 | 13 | 14 | /** 15 | * 16 | * Title: WordNormalizer 17 | * Description:该类主要用于格式化数据 18 | * Version:1.0.0 19 | * @author pancm 20 | * @date 2017年12月28日 21 | */ 22 | public class WordNormalizer implements IRichBolt { 23 | /** 24 | * 25 | */ 26 | private static final long serialVersionUID = 3644849073824009317L; 27 | private OutputCollector collector; 28 | 29 | /** 30 | * *bolt*从单词文件接收到文本行,并标准化它。 文本行会全部转化成小写,并切分它,从中得到所有单词。 31 | */ 32 | public void execute(Tuple input) { 33 | System.out.println("WordNormalizer.execute()"); 34 | String sentence = input.getString(0); 35 | String[] words = sentence.split(" "); 36 | for (String word : words) { 37 | word = word.trim(); 38 | if (!word.isEmpty()) { 39 | word = word.toLowerCase(); 40 | /* //发布这个单词 */ 41 | collector.emit(input, new Values(word)); 42 | } 43 | } 44 | // 对元组做出应答 45 | collector.ack(input); 46 | } 47 | 48 | public void prepare(Map stormConf, TopologyContext context, 49 | OutputCollector collector) { 50 | System.out.println("WordNormalizer.prepare()"); 51 | this.collector = collector; 52 | } 53 | 54 | /** 55 | * 这个*bolt*只会发布“word”域 56 | */ 57 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 58 | System.out.println("WordNormalizer.declareOutputFields()"); 59 | declarer.declare(new Fields("word")); 60 | } 61 | 62 | @Override 63 | public Map getComponentConfiguration() { 64 | System.out.println("WordNormalizer.getComponentConfiguration()"); 65 | return null; 66 | } 67 | 68 | public void cleanup() { 69 | System.out.println("WordNormalizer.cleanup()"); 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/ffmpeg/FFmpegTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.ffmpeg; 2 | 3 | import java.io.BufferedReader; 4 | import java.io.IOException; 5 | import java.io.InputStreamReader; 6 | import java.util.ArrayList; 7 | import java.util.List; 8 | 9 | /** 10 | * @author pancm 11 | * @Title: FFmpegTest 12 | * @Description: FFmpeg获取视频图片 13 | * 调用FFmpeg的命令获取ts视频的图片 14 | * @Version:1.0.0 15 | * @Since:jdk1.8 16 | * @Date 2021/4/14 17 | **/ 18 | public class FFmpegTest { 19 | 20 | 21 | public static void main(String[] args) { 22 | 23 | String ffmpegExePath = "C:\\ffmpeg\\bin\\ffmpeg.exe"; 24 | 25 | String inputFilePath = "D:\\video\\ts\\25-16_940.ts"; 26 | 27 | String outputFilePath = "D:\\video\\ts\\t2.jpg"; 28 | 29 | List command = new ArrayList(); 30 | command.add(ffmpegExePath); 31 | command.add("-i"); 32 | command.add(inputFilePath); 33 | command.add("-f"); 34 | command.add("image2"); 35 | command.add("-ss"); 36 | command.add("1"); 37 | command.add("-t"); 38 | command.add("0.001"); 39 | command.add("-s"); 40 | command.add("320*240"); 41 | command.add(outputFilePath); 42 | ProcessBuilder builder = new ProcessBuilder(); 43 | builder.command(command); 44 | //正常信息和错误信息合并输出 45 | builder.redirectErrorStream(true); 46 | try { 47 | //开始执行命令 48 | Process process = builder.start(); 49 | //如果你想获取到执行完后的信息,那么下面的代码也是需要的 50 | StringBuffer sbf = new StringBuffer(); 51 | String line = null; 52 | BufferedReader br = new BufferedReader(new InputStreamReader(process.getInputStream())); 53 | while ((line = br.readLine()) != null) { 54 | sbf.append(line); 55 | sbf.append(" "); 56 | } 57 | String resultInfo = sbf.toString(); 58 | System.out.println(resultInfo); 59 | } catch (IOException e) { 60 | e.printStackTrace(); 61 | } 62 | 63 | } 64 | 65 | 66 | } 67 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo/MinaServerHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo; 2 | 3 | import java.net.InetSocketAddress; 4 | import java.util.Date; 5 | 6 | import org.apache.log4j.Logger; 7 | import org.apache.mina.core.service.IoHandlerAdapter; 8 | import org.apache.mina.core.session.IdleStatus; 9 | import org.apache.mina.core.session.IoSession; 10 | 11 | 12 | /** 13 | * @author ZERO: 14 | * @version 2017-3-27 下午3:59:33 15 | * 业务逻辑实现 16 | */ 17 | public class MinaServerHandler extends IoHandlerAdapter { 18 | public static Logger logger=Logger.getLogger(MinaServerHandler.class); 19 | 20 | @Override 21 | public void sessionCreated(IoSession iosession) throws Exception{ 22 | InetSocketAddress sa=(InetSocketAddress)iosession.getRemoteAddress(); 23 | String address=sa.getAddress().getHostAddress(); //访问的ip 24 | logger.info("服务端与客户端创建连接..."+"访问的IP:"+address); 25 | } 26 | 27 | 28 | @Override 29 | public void sessionOpened(IoSession iosession) throws Exception{ 30 | logger.info("服务端与客户端连接打开..."); 31 | } 32 | 33 | @Override 34 | public void messageReceived(IoSession session,Object message) throws Exception{ 35 | String msg=message.toString(); 36 | logger.info("服务端收到的数据为:"+msg); 37 | if("bye".equals(msg)){ //服务端断开的条件 38 | session.close(); 39 | } 40 | Date date=new Date(); 41 | session.write(date); //返回给服务端数据 42 | } 43 | 44 | @Override 45 | public void messageSent(IoSession session, Object message) throws Exception { 46 | // session.close(); //发送成功后主动断开与客户端的连接 47 | logger.info("服务端发送信息成功..."); 48 | } 49 | 50 | @Override 51 | public void sessionClosed(IoSession session) throws Exception { 52 | } 53 | 54 | @Override 55 | public void sessionIdle(IoSession session, IdleStatus status) 56 | throws Exception { 57 | logger.info("服务端进入空闲状态..."); 58 | } 59 | 60 | @Override 61 | public void exceptionCaught(IoSession session, Throwable cause) 62 | throws Exception { 63 | logger.error("服务端发送异常...", cause); 64 | } 65 | 66 | 67 | } 68 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo/MinaServer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo; 2 | 3 | import java.net.InetSocketAddress; 4 | 5 | import org.apache.log4j.Logger; 6 | import org.apache.mina.core.service.IoAcceptor; 7 | import org.apache.mina.core.session.IdleStatus; 8 | import org.apache.mina.filter.codec.ProtocolCodecFilter; 9 | import org.apache.mina.filter.codec.serialization.ObjectSerializationCodecFactory; 10 | import org.apache.mina.transport.socket.nio.NioSocketAcceptor; 11 | 12 | 13 | /** 14 | * @author ZERO: 15 | * @version 2017-3-27 下午3:20:11 16 | * 创建服务端 17 | */ 18 | public class MinaServer { 19 | //记录日志 20 | public static Logger logger=Logger.getLogger(MinaServer.class); 21 | private static int PORT=3333; 22 | 23 | /* 启动此类 提示服务端运行成功后 24 | * Windows 命令 输入 telnet 127.0.0.1 3305 25 | * 然后输入消息 message 26 | * 消息为bye的时候关闭连接 27 | * */ 28 | public static void main(String[] args) { 29 | IoAcceptor ia=null; 30 | try{ 31 | //创建一个非堵塞的server端Socket 32 | ia=new NioSocketAcceptor(); 33 | //创建 协议编码解码过滤器ProtocolCodecFilter 34 | // ProtocolCodecFilter pf=new ProtocolCodecFilter(new TextLineCodecFactory(Charset 35 | // .forName("UTF-8"), 36 | // LineDelimiter.WINDOWS.getValue(), 37 | // LineDelimiter.WINDOWS.getValue())); 38 | //设置端口 39 | InetSocketAddress pt=new InetSocketAddress(PORT); 40 | // 设置过滤器(使用Mina提供的文本换行符编解码器) 41 | ia.getFilterChain().addLast("codec", new ProtocolCodecFilter(new ObjectSerializationCodecFactory())); 42 | //设置读取数据的缓存区大小 43 | ia.getSessionConfig().setReadBufferSize(2048); 44 | //读写通道10秒内无操作进入空闲状态 45 | ia.getSessionConfig().setIdleTime(IdleStatus.BOTH_IDLE, 10); 46 | //绑定逻辑处理器 47 | ia.setHandler(new MinaServerHandler()); 48 | //绑定端口 49 | ia.bind(pt); 50 | logger.info("服务端启动成功...端口号为:"+PORT); 51 | 52 | }catch(Exception e){ 53 | logger.error("服务器的异常..."+e); 54 | e.printStackTrace(); 55 | } 56 | } 57 | 58 | } 59 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test/TestBolt.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.test; 2 | 3 | import java.util.Map; 4 | 5 | import org.apache.storm.task.OutputCollector; 6 | import org.apache.storm.task.TopologyContext; 7 | import org.apache.storm.topology.OutputFieldsDeclarer; 8 | import org.apache.storm.topology.base.BaseRichBolt; 9 | import org.apache.storm.tuple.Tuple; 10 | 11 | /** 12 | * 13 | * Title: TestBolt 14 | * Description: 15 | * 用于处理消息 16 | * Version:1.0.0 17 | * @author pancm 18 | * @date 2018年3月6日 19 | */ 20 | public class TestBolt extends BaseRichBolt{ 21 | 22 | /** 23 | * 24 | */ 25 | private static final long serialVersionUID = 4743224635827696343L; 26 | 27 | private OutputCollector collector; 28 | private long count=1; 29 | /** 30 | * 在Bolt启动前执行,提供Bolt启动环境配置的入口 31 | * 一般对于不可序列化的对象进行实例化。 32 | * 注:如果是可以序列化的对象,那么最好是使用构造函数。 33 | */ 34 | @Override 35 | public void prepare(Map map, TopologyContext arg1, OutputCollector collector) { 36 | System.out.println("prepare:"+map.get("test")); 37 | this.collector=collector; 38 | } 39 | 40 | /** 41 | * execute()方法是Bolt实现的核心。 42 | * 也就是执行方法,每次Bolt从流接收一个订阅的tuple,都会调用这个方法。 43 | */ 44 | @Override 45 | public void execute(Tuple tuple) { 46 | /** 47 | * 接受消息可以使用这两种方式进行接收。 48 | * 个人推荐第二种。 49 | */ 50 | // String msg=tuple.getString(0); 51 | String msg=tuple.getStringByField("test"); 52 | //这里我们就不做消息的处理,只打印 53 | System.out.println("Bolt第"+count+"接受的消息:"+msg); 54 | count++; 55 | /** 56 | * 57 | * 没次调用处理一个输入的tuple,所有的tuple都必须在一定时间内应答。 58 | * 可以是ack或者fail。否则,spout就会重发tuple。 59 | * 如果继承的是IRichBolt,则需要手动ack。 60 | * 这里就不用了,BaseRichBolt会自动帮我们应答。 61 | */ 62 | // collector.ack(tuple); 63 | } 64 | 65 | /** 66 | * 声明数据格式 67 | */ 68 | @Override 69 | public void declareOutputFields(OutputFieldsDeclarer arg0) { 70 | 71 | } 72 | 73 | /** 74 | * cleanup是IBolt接口中定义,用于释放bolt占用的资源。 75 | * Storm在终止一个bolt之前会调用这个方法。 76 | */ 77 | @Override 78 | public void cleanup() { 79 | System.out.println("资源释放"); 80 | } 81 | } 82 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo1/MinaClient.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo1; 2 | 3 | import java.net.InetSocketAddress; 4 | import java.nio.charset.Charset; 5 | 6 | import org.apache.log4j.Logger; 7 | import org.apache.mina.core.future.ConnectFuture; 8 | import org.apache.mina.core.service.IoConnector; 9 | import org.apache.mina.core.session.IoSession; 10 | import org.apache.mina.filter.codec.ProtocolCodecFilter; 11 | import org.apache.mina.transport.socket.nio.NioSocketConnector; 12 | 13 | /** 14 | * @author ZERO 15 | * @version 2017-3-27 下午5:59:54 16 | * mina 客户端 17 | */ 18 | public class MinaClient { 19 | private static Logger logger = Logger.getLogger(MinaClient.class); 20 | private static String HOST = "127.0.0.1"; 21 | private static int PORT = 3305; 22 | 23 | /* 24 | * 测试服务端与客户端程序! 25 | a. 启动服务端,然后再启动客户端(客户端发送的消息是"why are you so diao ") 26 | b. 服务端接收消息并处理成功; 27 | */ 28 | public static void main(String[] args) { 29 | // 创建一个非阻塞的客户端程序 30 | IoConnector connector = new NioSocketConnector(); 31 | // 设置链接超时时间 32 | connector.setConnectTimeout(30000); 33 | ProtocolCodecFilter pf=new ProtocolCodecFilter((new MyTextLineCodecFactory(Charset .forName("utf-8"), "\r\n"))); 34 | // 添加过滤器 35 | connector.getFilterChain().addLast("codec", pf); 36 | // 添加业务逻辑处理器类 37 | connector.setHandler(new MinaClientHandler()); 38 | IoSession session = null; 39 | try { 40 | ConnectFuture future = connector.connect(new InetSocketAddress( 41 | HOST, PORT));// 创建连接 42 | future.awaitUninterruptibly();// 等待连接创建完成 43 | session = future.getSession();// 获得session 44 | String msg="hello \r\n"; 45 | session.write(msg);// 发送消息 46 | logger.info("客户端与服务端建立连接成功...发送的消息为:"+msg); 47 | } catch (Exception e) { 48 | e.printStackTrace(); 49 | logger.error("客户端链接异常...", e); 50 | } 51 | session.getCloseFuture().awaitUninterruptibly();// 等待连接断开 52 | connector.dispose(); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example1/SplitSentenceBolt.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.example1; 2 | 3 | import java.util.Map; 4 | 5 | import org.apache.storm.task.OutputCollector; 6 | import org.apache.storm.task.TopologyContext; 7 | import org.apache.storm.topology.OutputFieldsDeclarer; 8 | import org.apache.storm.topology.base.BaseRichBolt; 9 | import org.apache.storm.tuple.Fields; 10 | import org.apache.storm.tuple.Tuple; 11 | import org.apache.storm.tuple.Values; 12 | 13 | 14 | 15 | /** 16 | * 订阅sentence spout发射的tuple流,实现分割单词 17 | * @author soul 18 | * 19 | */ 20 | public class SplitSentenceBolt extends BaseRichBolt { 21 | //BaseRichBolt是IComponent和IBolt接口的实现 22 | //继承这个类,就不用去实现本例不关心的方法 23 | 24 | /** 25 | * 26 | */ 27 | private static final long serialVersionUID = 1L; 28 | private OutputCollector collector; 29 | 30 | /** 31 | * prepare()方法类似于ISpout 的open()方法。 32 | * 这个方法在blot初始化时调用,可以用来准备bolt用到的资源,比如数据库连接。 33 | * 本例子和SentenceSpout类一样,SplitSentenceBolt类不需要太多额外的初始化, 34 | * 所以prepare()方法只保存OutputCollector对象的引用。 35 | */ 36 | public void prepare(Map stormConf, TopologyContext context, OutputCollector collector) { 37 | // TODO Auto-generated method stub 38 | this.collector=collector; 39 | 40 | } 41 | 42 | /** 43 | * SplitSentenceBolt核心功能是在类IBolt定义execute()方法,这个方法是IBolt接口中定义。 44 | * 每次Bolt从流接收一个订阅的tuple,都会调用这个方法。 45 | * 本例中,收到的元组中查找“sentence”的值, 46 | * 并将该值拆分成单个的词,然后按单词发出新的tuple。 47 | */ 48 | public void execute(Tuple input) { 49 | // TODO Auto-generated method stub 50 | String sentence = input.getStringByField("sentence"); 51 | String[] words = sentence.split(" "); 52 | for (String word : words) { 53 | this.collector.emit(new Values(word));//向下一个bolt发射数据 54 | } 55 | } 56 | 57 | /** 58 | * plitSentenceBolt类定义一个元组流,每个包含一个字段(“word”)。 59 | */ 60 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 61 | // TODO Auto-generated method stub 62 | declarer.declare(new Fields("word")); 63 | } 64 | 65 | } 66 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo3/NettyDecoder.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo3; 2 | 3 | import java.util.List; 4 | 5 | import io.netty.buffer.ByteBuf; 6 | import io.netty.channel.ChannelHandlerContext; 7 | import io.netty.handler.codec.ByteToMessageCodec; 8 | 9 | /** 10 | * 11 | * Description: Netty自定义解码器 12 | * Version:1.0.0 13 | * @author pancm 14 | * @date 2017年9月21日 15 | */ 16 | public class NettyDecoder extends ByteToMessageCodec { 17 | 18 | //判断传送客户端传送过来的数据是否按照协议传输,头部信息的大小应该是 byte+byte+int = 1+1+4 = 6 19 | private static final int HEADER_SIZE = 6; 20 | 21 | /** 类型 系统编号 0xAB 表示A系统,0xBC 表示B系统 */ 22 | private byte type; 23 | 24 | /** 信息标志 0xAB 表示心跳包 0xBC 表示超时包 0xCD 业务信息包 */ 25 | private byte flag; 26 | 27 | /** 主题信息的长度 */ 28 | private int length; 29 | 30 | /** 主题信息 */ 31 | private String body; 32 | 33 | 34 | @Override 35 | protected void encode(ChannelHandlerContext ctx, NettyMsg msg, ByteBuf out) 36 | throws Exception { 37 | System.out.println("msg:"+msg); 38 | if (out == null) { 39 | return ; 40 | } 41 | if (out.readableBytes() < HEADER_SIZE) { 42 | throw new Exception("可读信息段比头部信息都小,你在逗我?"); 43 | } 44 | //注意在读的过程中,readIndex的指针也在移动 45 | type = out.readByte(); 46 | 47 | flag = out.readByte(); 48 | 49 | length = out.readInt(); 50 | 51 | if (out.readableBytes() < length) { 52 | throw new Exception("body字段你告诉我长度是"+length+",但是真实情况是没有这么多,你又逗我?"); 53 | } 54 | ByteBuf buf = out.readBytes(length); 55 | byte[] req = new byte[buf.readableBytes()]; 56 | buf.readBytes(req); 57 | body = new String(req, "UTF-8"); 58 | NettyMsg customMsg = new NettyMsg(type,flag,length,body); 59 | 60 | } 61 | 62 | @Override 63 | protected void decode(ChannelHandlerContext ctx, ByteBuf in, 64 | List out) throws Exception { 65 | // TODO Auto-generated method stub 66 | 67 | } 68 | 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example/WordNormalizer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.example; 2 | 3 | import java.util.Map; 4 | 5 | import org.apache.storm.task.OutputCollector; 6 | import org.apache.storm.task.TopologyContext; 7 | import org.apache.storm.topology.IRichBolt; 8 | import org.apache.storm.topology.OutputFieldsDeclarer; 9 | import org.apache.storm.tuple.Fields; 10 | import org.apache.storm.tuple.Tuple; 11 | import org.apache.storm.tuple.Values; 12 | 13 | 14 | /** 15 | * 16 | * Title: WordNormalizer 17 | * Description:该类主要用于格式化数据 18 | * Version:1.0.0 19 | * @author pancm 20 | * @date 2017年12月28日 21 | */ 22 | public class WordNormalizer implements IRichBolt { 23 | /** 24 | * 25 | */ 26 | private static final long serialVersionUID = 3644849073824009317L; 27 | private OutputCollector collector; 28 | private static int count=1; 29 | 30 | /** 31 | * *bolt*从单词文件接收到文本行,并标准化它。 文本行会全部转化成小写,并切分它,从中得到所有单词。 32 | */ 33 | public void execute(Tuple input) { 34 | System.out.println("WordNormalizer.execute()执行次数:"+count); 35 | String sentence = input.getString(0); 36 | String[] words = sentence.split(" "); 37 | for (String word : words) { 38 | word = word.trim(); 39 | if (!word.isEmpty()) { 40 | word = word.toLowerCase(); 41 | /* //发布这个单词 */ 42 | collector.emit(input, new Values(word)); 43 | } 44 | } 45 | // 对元组做出应答 46 | collector.ack(input); 47 | count++; 48 | } 49 | 50 | public void prepare(Map stormConf, TopologyContext context, 51 | OutputCollector collector) { 52 | System.out.println("WordNormalizer.prepare()"); 53 | this.collector = collector; 54 | } 55 | 56 | /** 57 | * 这个*bolt*只会发布“word”域 58 | */ 59 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 60 | System.out.println("WordNormalizer.declareOutputFields()"); 61 | declarer.declare(new Fields("word")); 62 | } 63 | 64 | @Override 65 | public Map getComponentConfiguration() { 66 | System.out.println("WordNormalizer.getComponentConfiguration()"); 67 | return null; 68 | } 69 | 70 | public void cleanup() { 71 | System.out.println("WordNormalizer.cleanup()"); 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example1/ReportBolt.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.example1; 2 | 3 | import java.util.ArrayList; 4 | import java.util.Collections; 5 | import java.util.HashMap; 6 | import java.util.Map; 7 | 8 | import org.apache.storm.task.OutputCollector; 9 | import org.apache.storm.task.TopologyContext; 10 | import org.apache.storm.topology.OutputFieldsDeclarer; 11 | import org.apache.storm.topology.base.BaseRichBolt; 12 | import org.apache.storm.tuple.Tuple; 13 | 14 | 15 | 16 | /** 17 | * 生成一份报告 18 | * @author soul 19 | * 20 | */ 21 | public class ReportBolt extends BaseRichBolt { 22 | 23 | private HashMap counts = null;//保存单词和对应的计数 24 | 25 | public void prepare(Map stormConf, TopologyContext context, OutputCollector collector) { 26 | // TODO Auto-generated method stub 27 | 28 | this.counts = new HashMap(); 29 | } 30 | 31 | public void execute(Tuple input) { 32 | // TODO Auto-generated method stub 33 | 34 | String word = input.getStringByField("word"); 35 | Long count = input.getLongByField("count"); 36 | this.counts.put(word, count); 37 | 38 | //实时输出 39 | System.out.println("结果:"+this.counts); 40 | } 41 | 42 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 43 | // TODO Auto-generated method stub 44 | //这里是末端bolt,不需要发射数据流,这里无需定义 45 | } 46 | 47 | /** 48 | * cleanup是IBolt接口中定义 49 | * Storm在终止一个bolt之前会调用这个方法 50 | * 本例我们利用cleanup()方法在topology关闭时输出最终的计数结果 51 | * 通常情况下,cleanup()方法用来释放bolt占用的资源,如打开的文件句柄或数据库连接 52 | * 但是当Storm拓扑在一个集群上运行,IBolt.cleanup()方法不能保证执行(这里是开发模式,生产环境不要这样做)。 53 | */ 54 | public void cleanup(){ 55 | System.out.println("---------- FINAL COUNTS -----------"); 56 | 57 | ArrayList keys = new ArrayList(); 58 | keys.addAll(this.counts.keySet()); 59 | Collections.sort(keys); 60 | for(String key : keys){ 61 | System.out.println(key + " : " + this.counts.get(key)); 62 | } 63 | System.out.println("----------------------------"); 64 | } 65 | 66 | } 67 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/mina/demo1/MinaServerHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.mina.demo1; 2 | 3 | import java.util.Date; 4 | 5 | import org.apache.log4j.Logger; 6 | import org.apache.mina.core.service.IoHandlerAdapter; 7 | import org.apache.mina.core.session.IdleStatus; 8 | import org.apache.mina.core.session.IoSession; 9 | 10 | 11 | /** 12 | * @author ZERO: 13 | * @version 2017-3-27 下午3:59:33 14 | * 业务逻辑实现 15 | */ 16 | public class MinaServerHandler extends IoHandlerAdapter { 17 | public static Logger logger=Logger.getLogger(MinaServerHandler.class); 18 | 19 | @Override 20 | public void sessionCreated(IoSession session) throws Exception{ 21 | logger.info("服务端与客户端创建连接..."); 22 | super.sessionCreated(session); 23 | } 24 | 25 | 26 | @Override 27 | public void sessionOpened(IoSession session) throws Exception{ 28 | logger.info("服务端与客户端连接打开..."); 29 | super.sessionOpened(session); 30 | } 31 | 32 | @Override 33 | public void messageReceived(IoSession session,Object message) throws Exception{ 34 | String msg=message.toString(); 35 | logger.info("服务端收到的数据为:"+msg); 36 | if("bye".equals(msg)){ //服务端断开的条件 37 | session.close(); 38 | } 39 | Date date=new Date(); 40 | String mg="Come on:"+date; 41 | logger.info("服务端返回给客户端的数据:"+mg); 42 | session.write(mg); //返回给服务端数据 43 | } 44 | 45 | @Override 46 | public void messageSent(IoSession session, Object message) throws Exception { 47 | logger.info("服务端发送数据 = "+message); 48 | // session.close(); //发送成功后主动断开与客户端的连接 实现短连接 49 | logger.info("服务端发送信息成功..."); 50 | } 51 | 52 | @Override 53 | public void sessionClosed(IoSession session) throws Exception { 54 | logger.info("断开连接"); 55 | super.sessionClosed(session); 56 | } 57 | 58 | @Override 59 | public void sessionIdle(IoSession session, IdleStatus status) 60 | throws Exception { 61 | logger.info("服务端进入空闲状态..."); 62 | super.sessionIdle(session, status); 63 | } 64 | 65 | @Override 66 | public void exceptionCaught(IoSession session, Throwable cause) 67 | throws Exception { 68 | logger.error("服务端发送异常...", cause); 69 | super.exceptionCaught(session, cause); 70 | } 71 | 72 | 73 | } 74 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/adapter/AdapterTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.adapter; 2 | 3 | /** 4 | * @Title: AdapterTest 5 | * @Description: 6 | * 适配器模式 7 | * 将一个类的接口转换成客户希望的另外一个接口。适配器模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。 8 | * 9 | * 有两种种模式 10 | * 1.类适配器模式 11 | * 2.对象适配器模式 12 | * @Version:1.0.0 13 | * @author pancm 14 | * @date 2018年8月8日 15 | */ 16 | public class AdapterTest { 17 | 18 | public static void main(String[] args) { 19 | /* 20 | * 1.类适配器模式 21 | * 通过继承来实现适配器功能。 22 | * 有一个视频播放器,但是只能播放MP4格式的视频 23 | * 有一个AVI格式的视频需要播放,这时便可以使用格式工厂软件进行转换(适配器)进行转换成MP4格式,然后就可以播放了 24 | */ 25 | Mp4 mp4=new VideoPlayer(); 26 | mp4.playMp4(); 27 | Avi avi=new FormatFactory(); 28 | avi.playAvi(); 29 | 30 | /* 31 | * 2.对象适配器模式 32 | * 通过组合来实现适配器功能。 33 | * 推荐使用对象适配器模式,设计原则的合成复用原则中描述,尽量使用合成/聚合的方式,而不是使用继承。 34 | * 35 | */ 36 | Rvmb rvmb=new FormatFactory2(new VideoPlayer()); 37 | rvmb.playRvmb(); 38 | 39 | 40 | } 41 | } 42 | 43 | 44 | interface Mp4{ 45 | void playMp4(); 46 | } 47 | 48 | interface Avi{ 49 | void playAvi(); 50 | } 51 | 52 | 53 | interface Rvmb{ 54 | void playRvmb(); 55 | } 56 | 57 | /** 58 | * 59 | * @Title: VideoPlayer 60 | * @Description: 视频播放器 61 | * @Version:1.0.0 62 | * @author pancm 63 | * @date 2018年8月21日 64 | */ 65 | class VideoPlayer implements Mp4{ 66 | 67 | @Override 68 | public void playMp4() { 69 | System.out.println("播放Mp4格式的视频文件."); 70 | } 71 | } 72 | 73 | 74 | /** 75 | * 76 | * @Title: FormatFactory 77 | * @Description: 格式工厂 78 | * @Version:1.0.0 79 | * @author pancm 80 | * @date 2018年8月21日 81 | */ 82 | class FormatFactory extends VideoPlayer implements Avi{ 83 | 84 | @Override 85 | public void playAvi() { 86 | //转换成MP4格式的视频 87 | playMp4(); 88 | } 89 | } 90 | 91 | 92 | /** 93 | * 94 | * @Title: FormatFactory2 95 | * @Description: 格式工厂 96 | * @Version:1.0.0 97 | * @author pancm 98 | * @date 2018年8月21日 99 | */ 100 | class FormatFactory2 implements Rvmb{ 101 | private Mp4 mp4; 102 | 103 | public FormatFactory2(Mp4 mp4) { 104 | this.mp4=mp4; 105 | } 106 | 107 | @Override 108 | public void playRvmb() { 109 | mp4.playMp4(); 110 | } 111 | 112 | } 113 | 114 | 115 | 116 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/threadPrinter.java: -------------------------------------------------------------------------------- 1 | package com.pancm.thread.test; 2 | /** 3 | * @author ZERO 4 | * @Data 2017-5-27 下午4:27:21 5 | * @Description 6 | * 测试Object notify和wait方法 7 | */ 8 | public class threadPrinter implements Runnable { 9 | 10 | private String name; 11 | private Object prev; 12 | private Object self; 13 | 14 | private threadPrinter(String name, Object prev, Object self) { 15 | this.name = name; 16 | this.prev = prev; 17 | this.self = self; 18 | } 19 | 20 | @Override 21 | public void run() { 22 | int count = 10; 23 | while (count > 0) { 24 | synchronized (prev) { 25 | synchronized (self) { 26 | System.out.print(name); 27 | count--; 28 | self.notify(); 29 | } 30 | try { 31 | prev.wait(); 32 | } catch (InterruptedException e) { 33 | e.printStackTrace(); 34 | } 35 | } 36 | 37 | } 38 | } 39 | 40 | /** 41 | * 建立三个线程,A线程打印10次A,B线程打印10次B,C线程打印10次C,要求线程同时运行,交替打印10次ABC。 42 | * 思路: 43 | * 同时运行这三个线程,打印A、B、C,确保线程的执行顺序是ABC,可以加上Thread.sleep()进行简单的控制 44 | * 在运行A线程的时候,确保上一个线程不在运行,那么先唤醒本线程,然后 使上一个线程进行等待 45 | * 46 | * @param args 47 | * @throws Exception 48 | */ 49 | public static void main(String[] args) throws Exception { 50 | Object a = new Object(); 51 | Object b = new Object(); 52 | Object c = new Object(); 53 | threadPrinter pa = new threadPrinter("A", c, a); 54 | threadPrinter pb = new threadPrinter("B", a, b); 55 | threadPrinter pc = new threadPrinter("C", b, c); 56 | 57 | 58 | new Thread(pa).start(); 59 | Thread.sleep(100); //确保按顺序A、B、C执行 60 | new Thread(pb).start(); 61 | Thread.sleep(100); 62 | new Thread(pc).start(); 63 | Thread.sleep(100); 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/one/WordCounter.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.one; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import org.apache.storm.task.OutputCollector; 7 | import org.apache.storm.task.TopologyContext; 8 | import org.apache.storm.topology.IRichBolt; 9 | import org.apache.storm.topology.OutputFieldsDeclarer; 10 | import org.apache.storm.tuple.Tuple; 11 | 12 | /** 13 | * 14 | * Title: WordCounter 15 | * Description: 该类主要用于统计 16 | * Version:1.0.0 17 | * @author pancm 18 | * @date 2017年12月28日 19 | */ 20 | public class WordCounter implements IRichBolt { 21 | /** 22 | * 23 | */ 24 | private static final long serialVersionUID = 1L; 25 | Integer id; 26 | String name; 27 | Map counters; 28 | private OutputCollector collector; 29 | 30 | /** 31 | * 当Bolt销毁时,我们会显示单词数量 32 | */ 33 | @Override 34 | public void cleanup() { 35 | System.out.println("开始显示单词数量..."); 36 | for (Map.Entry entry : counters.entrySet()) { 37 | System.out.println(entry.getKey() + ": " + entry.getValue()); 38 | } 39 | System.out.println("WordCounter.cleanup()"); 40 | } 41 | 42 | /** 43 | * 为每个单词计数 44 | */ 45 | @Override 46 | public void execute(Tuple input) { 47 | System.out.println("WordCounter.execute()"); 48 | String str = input.getString(0); 49 | /** 50 | * 如果单词尚不存在于map,我们就创建一个,如果已在,我们就为它加1 51 | */ 52 | if (!counters.containsKey(str)) { 53 | counters.put(str, 1); 54 | } else { 55 | Integer c = counters.get(str) + 1; 56 | counters.put(str, c); 57 | } 58 | // 对元组作为应答 59 | collector.ack(input); 60 | } 61 | 62 | /** 63 | * 初始化 64 | */ 65 | @Override 66 | public void prepare(Map stormConf, TopologyContext context, 67 | OutputCollector collector) { 68 | this.counters = new HashMap(); 69 | this.collector = collector; 70 | this.name = context.getThisComponentId(); 71 | this.id = context.getThisTaskId(); 72 | } 73 | 74 | @Override 75 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 76 | System.out.println("WordCounter.declareOutputFields()"); 77 | } 78 | 79 | @Override 80 | public Map getComponentConfiguration() { 81 | System.out.println("WordCounter.getComponentConfiguration()"); 82 | return null; 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example/WordCounter.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.example; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import org.apache.storm.task.OutputCollector; 7 | import org.apache.storm.task.TopologyContext; 8 | import org.apache.storm.topology.IRichBolt; 9 | import org.apache.storm.topology.OutputFieldsDeclarer; 10 | import org.apache.storm.tuple.Tuple; 11 | 12 | /** 13 | * 14 | * Title: WordCounter 15 | * Description: 该类主要用于统计 16 | * Version:1.0.0 17 | * @author pancm 18 | * @date 2017年12月28日 19 | */ 20 | public class WordCounter implements IRichBolt { 21 | /** 22 | * 23 | */ 24 | private static final long serialVersionUID = 1L; 25 | Integer id; 26 | String name; 27 | Map counters; 28 | private OutputCollector collector; 29 | 30 | /** 31 | * 当Bolt销毁时,我们会显示单词数量 32 | */ 33 | @Override 34 | public void cleanup() { 35 | System.out.println("开始显示单词数量..."); 36 | for (Map.Entry entry : counters.entrySet()) { 37 | System.out.println(entry.getKey() + ": " + entry.getValue()); 38 | } 39 | System.out.println("WordCounter.cleanup()"); 40 | } 41 | 42 | /** 43 | * 为每个单词计数 44 | */ 45 | @Override 46 | public void execute(Tuple input) { 47 | System.out.println("WordCounter.execute()"); 48 | String str = input.getString(0); 49 | /** 50 | * 如果单词尚不存在于map,我们就创建一个,如果已在,我们就为它加1 51 | */ 52 | if (!counters.containsKey(str)) { 53 | counters.put(str, 1); 54 | } else { 55 | Integer c = counters.get(str) + 1; 56 | counters.put(str, c); 57 | } 58 | // 对元组作为应答 59 | collector.ack(input); 60 | } 61 | 62 | /** 63 | * 初始化 64 | */ 65 | @Override 66 | public void prepare(Map stormConf, TopologyContext context, 67 | OutputCollector collector) { 68 | this.counters = new HashMap(); 69 | this.collector = collector; 70 | this.name = context.getThisComponentId(); 71 | this.id = context.getThisTaskId(); 72 | } 73 | 74 | @Override 75 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 76 | System.out.println("WordCounter.declareOutputFields()"); 77 | } 78 | 79 | @Override 80 | public Map getComponentConfiguration() { 81 | System.out.println("WordCounter.getComponentConfiguration()"); 82 | return null; 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/ffmpeg/FFmpegUtil.java: -------------------------------------------------------------------------------- 1 | package com.pancm.ffmpeg; 2 | 3 | import java.io.BufferedReader; 4 | import java.io.IOException; 5 | import java.io.InputStreamReader; 6 | import java.util.ArrayList; 7 | import java.util.List; 8 | 9 | /** 10 | * @author pancm 11 | * @Title: gb28181_platform 12 | * @Description: FFmpeg相关的工具类 13 | * @Version:1.0.0 14 | * @Since:jdk1.8 15 | * @date 2021/4/15 16 | */ 17 | public class FFmpegUtil { 18 | 19 | 20 | /** 21 | * 执行ffmpeg的项目命令 22 | * @param cmdList 23 | * @throws IOException 24 | */ 25 | public static void exec(List cmdList) throws IOException { 26 | BufferedReader br = null; 27 | try { 28 | ProcessBuilder builder = new ProcessBuilder(); 29 | builder.command(cmdList); 30 | //正常信息和错误信息合并输出 31 | builder.redirectErrorStream(true); 32 | //开始执行命令 33 | Process process = builder.start(); 34 | StringBuffer sbf = new StringBuffer(); 35 | String line = null; 36 | br = new BufferedReader(new InputStreamReader(process.getInputStream())); 37 | while ((line = br.readLine()) != null) { 38 | sbf.append(line); 39 | sbf.append(" "); 40 | } 41 | String resultInfo = sbf.toString(); 42 | System.out.println(resultInfo); 43 | } finally { 44 | if (br != null) { 45 | br.close(); 46 | } 47 | } 48 | } 49 | 50 | public static void main(String[] args) throws IOException { 51 | String ffmpegExePath = "C:\\ffmpeg\\bin\\ffmpeg.exe"; 52 | String inputFilePath = "D:\\video\\ts\\25-16_940.ts"; 53 | String outputFilePath = "D:\\video\\ts\\t3.jpg"; 54 | List command = new ArrayList(); 55 | command.add(ffmpegExePath); 56 | command.add("-i"); 57 | command.add(inputFilePath); 58 | command.add("-f"); 59 | command.add("image2"); 60 | command.add("-ss"); 61 | command.add("1"); 62 | command.add("-t"); 63 | command.add("0.001"); 64 | command.add("-s"); 65 | command.add("640*480"); 66 | command.add(outputFilePath); 67 | exec(command); 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test2/Test2Bolt.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.test2; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | import org.apache.storm.task.OutputCollector; 7 | import org.apache.storm.task.TopologyContext; 8 | import org.apache.storm.topology.OutputFieldsDeclarer; 9 | import org.apache.storm.topology.base.BaseRichBolt; 10 | import org.apache.storm.tuple.Tuple; 11 | 12 | /** 13 | * 14 | * Title: Test2Bolt 15 | * Description: 16 | * 统计单词出现的次数 17 | * Version:1.0.0 18 | * @author pancm 19 | * @date 2018年3月16日 20 | */ 21 | public class Test2Bolt extends BaseRichBolt{ 22 | 23 | /** 24 | * 25 | */ 26 | private static final long serialVersionUID = 4743224635827696343L; 27 | 28 | 29 | /** 30 | * 保存单词和对应的计数 31 | */ 32 | private HashMap counts = null; 33 | 34 | private long count=1; 35 | /** 36 | * 在Bolt启动前执行,提供Bolt启动环境配置的入口 37 | * 一般对于不可序列化的对象进行实例化。 38 | * 注:如果是可以序列化的对象,那么最好是使用构造函数。 39 | */ 40 | @Override 41 | public void prepare(Map map, TopologyContext arg1, OutputCollector collector) { 42 | System.out.println("prepare:"+map.get("test")); 43 | this.counts=new HashMap(); 44 | } 45 | 46 | /** 47 | * execute()方法是Bolt实现的核心。 48 | * 也就是执行方法,每次Bolt从流接收一个订阅的tuple,都会调用这个方法。 49 | * 50 | */ 51 | @Override 52 | public void execute(Tuple tuple) { 53 | String msg=tuple.getStringByField("count"); 54 | System.out.println("第"+count+"次统计单词出现的次数"); 55 | /** 56 | * 如果不包含该单词,说明在该map是第一次出现 57 | * 否则进行加1 58 | */ 59 | if (!counts.containsKey(msg)) { 60 | counts.put(msg, 1); 61 | } else { 62 | counts.put(msg, counts.get(msg)+1); 63 | } 64 | count++; 65 | } 66 | 67 | 68 | /** 69 | * cleanup是IBolt接口中定义,用于释放bolt占用的资源。 70 | * Storm在终止一个bolt之前会调用这个方法。 71 | */ 72 | @Override 73 | public void cleanup() { 74 | System.out.println("===========开始显示单词数量============"); 75 | for (Map.Entry entry : counts.entrySet()) { 76 | System.out.println(entry.getKey() + ": " + entry.getValue()); 77 | } 78 | System.out.println("===========结束============"); 79 | System.out.println("Test2Bolt的资源释放"); 80 | } 81 | 82 | /** 83 | * 声明数据格式 84 | */ 85 | @Override 86 | public void declareOutputFields(OutputFieldsDeclarer arg0) { 87 | 88 | } 89 | } 90 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/test1/KafkaProducerTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.test1; 2 | 3 | import java.util.Properties; 4 | 5 | import org.apache.kafka.clients.producer.KafkaProducer; 6 | import org.apache.kafka.clients.producer.ProducerRecord; 7 | import org.apache.kafka.common.serialization.StringSerializer; 8 | 9 | 10 | /** 11 | * 12 | * Title: KafkaProducerTest 13 | * Description: 14 | * kafka 生产者demo 15 | * Version:1.0.0 16 | * @author pancm 17 | * @date 2018年1月26日 18 | */ 19 | public class KafkaProducerTest implements Runnable { 20 | 21 | private final KafkaProducer producer; 22 | private final String topic; 23 | 24 | 25 | public KafkaProducerTest(String topicName) { 26 | Properties props = new Properties(); 27 | props.put("bootstrap.servers", "master:9092,slave1:9092,slave2:9092"); 28 | //acks=0:如果设置为0,生产者不会等待kafka的响应。 29 | //acks=1:这个配置意味着kafka会把这条消息写到本地日志文件中,但是不会等待集群中其他机器的成功响应。 30 | //acks=all:这个配置意味着leader会等待所有的follower同步完成。这个确保消息不会丢失,除非kafka集群中所有机器挂掉。这是最强的可用性保证。 31 | props.put("acks", "all"); 32 | //配置为大于0的值的话,客户端会在消息发送失败时重新发送。 33 | props.put("retries", 0); 34 | //当多条消息需要发送到同一个分区时,生产者会尝试合并网络请求。这会提高client和生产者的效率 35 | props.put("batch.size", 16384); 36 | props.put("key.serializer", StringSerializer.class.getName()); 37 | props.put("value.serializer", StringSerializer.class.getName()); 38 | this.producer = new KafkaProducer(props); 39 | this.topic = topicName; 40 | } 41 | 42 | @Override 43 | public void run() { 44 | int messageNo = 1; 45 | try { 46 | for(;;) { 47 | String messageStr="你好,这是第"+messageNo+"条数据"; 48 | producer.send(new ProducerRecord(topic, "Message", messageStr)); 49 | //生产了100条就打印 50 | if(messageNo%100==0){ 51 | System.out.println("发送的信息:" + messageStr); 52 | } 53 | //生产1000条就退出 54 | if(messageNo%1000==0){ 55 | System.out.println("成功发送了"+messageNo+"条"); 56 | break; 57 | } 58 | messageNo++; 59 | // Utils.sleep(1); 60 | } 61 | } catch (Exception e) { 62 | e.printStackTrace(); 63 | } finally { 64 | producer.close(); 65 | } 66 | } 67 | 68 | public static void main(String args[]) { 69 | KafkaProducerTest test = new KafkaProducerTest("KAFKA_TEST"); 70 | Thread thread = new Thread(test); 71 | thread.start(); 72 | } 73 | 74 | 75 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/test2/KafkaProducerTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.test2; 2 | 3 | import java.util.Properties; 4 | 5 | import org.apache.kafka.clients.producer.KafkaProducer; 6 | import org.apache.kafka.clients.producer.ProducerRecord; 7 | import org.apache.kafka.common.serialization.StringSerializer; 8 | 9 | 10 | /** 11 | * 12 | * Title: KafkaProducerTest 13 | * Description: 14 | * kafka 生产者demo 15 | * Version:1.0.0 16 | * @author pancm 17 | * @date 2018年1月26日 18 | */ 19 | public class KafkaProducerTest implements Runnable { 20 | 21 | private final KafkaProducer producer; 22 | private final String topic; 23 | 24 | 25 | public KafkaProducerTest(String topicName) { 26 | Properties props = new Properties(); 27 | props.put("bootstrap.servers", "master:9092,slave1:9092,slave2:9092"); 28 | //acks=0:如果设置为0,生产者不会等待kafka的响应。 29 | //acks=1:这个配置意味着kafka会把这条消息写到本地日志文件中,但是不会等待集群中其他机器的成功响应。 30 | //acks=all:这个配置意味着leader会等待所有的follower同步完成。这个确保消息不会丢失,除非kafka集群中所有机器挂掉。这是最强的可用性保证。 31 | props.put("acks", "all"); 32 | //配置为大于0的值的话,客户端会在消息发送失败时重新发送。 33 | props.put("retries", 0); 34 | //当多条消息需要发送到同一个分区时,生产者会尝试合并网络请求。这会提高client和生产者的效率 35 | props.put("batch.size", 16384); 36 | props.put("key.serializer", StringSerializer.class.getName()); 37 | props.put("value.serializer", StringSerializer.class.getName()); 38 | this.producer = new KafkaProducer(props); 39 | this.topic = topicName; 40 | } 41 | 42 | @Override 43 | public void run() { 44 | int messageNo = 1; 45 | try { 46 | for(;;) { 47 | String messageStr="你好,这是第"+messageNo+"条数据"; 48 | producer.send(new ProducerRecord(topic, "Message", messageStr)); 49 | //生产了10条就打印 50 | if(messageNo%10==0){ 51 | System.out.println("发送的信息:" + messageStr); 52 | } 53 | //生产100条就退出 54 | if(messageNo%100==0){ 55 | System.out.println("成功发送了"+messageNo+"条"); 56 | break; 57 | } 58 | messageNo++; 59 | // Utils.sleep(1); 60 | } 61 | } catch (Exception e) { 62 | e.printStackTrace(); 63 | } finally { 64 | producer.close(); 65 | } 66 | } 67 | 68 | public static void main(String args[]) { 69 | KafkaProducerTest test = new KafkaProducerTest("KAFKA_TEST2"); 70 | Thread thread = new Thread(test); 71 | thread.start(); 72 | } 73 | 74 | 75 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo1/NettyServerHandler.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo1; 2 | 3 | import java.net.InetAddress; 4 | 5 | import io.netty.channel.ChannelHandlerContext; 6 | import io.netty.channel.SimpleChannelInboundHandler; 7 | 8 | /** 9 | * 10 | * Title: NettyServerHandler 11 | * Description:Netty服务端业务逻辑实现 12 | * Version:1.0.0 13 | * @author Administrator 14 | * @date 2017-8-31 15 | */ 16 | 17 | 18 | public class NettyServerHandler extends SimpleChannelInboundHandler { 19 | 20 | @Override 21 | protected void channelRead0(ChannelHandlerContext ctx, String msg) 22 | throws Exception { 23 | // 收到消息直接打印输出 24 | System.out.println(ctx.channel().remoteAddress() + " Say : " + msg); 25 | 26 | // 返回客户端消息 - 我已经接收到了你的消息 27 | ctx.writeAndFlush("Received your message !\n"); 28 | } 29 | 30 | /* 31 | * 32 | * 覆盖 channelActive 方法 在channel被启用的时候触发 (在建立连接的时候) 33 | * 34 | * channelActive 和 channelInActive 在后面的内容中讲述,这里先不做详细的描述 35 | */ 36 | @Override 37 | public void channelActive(ChannelHandlerContext ctx) throws Exception { 38 | 39 | System.out.println("连接的客户端地址:" + ctx.channel().remoteAddress()); 40 | ctx.writeAndFlush("客户端"+ InetAddress.getLocalHost().getHostName() + "成功与服务端建立连接! \n"); 41 | super.channelActive(ctx); 42 | } 43 | 44 | } 45 | 46 | 47 | 48 | /** 49 | * Sharable表示此对象在channel间共享 50 | * handler类是我们的具体业务类 51 | * */ 52 | /*@Sharable//注解@Sharable可以让它在channels间共享 53 | public class NettyServerHandler extends ChannelInboundHandlerAdapter { 54 | public void channelRead(ChannelHandlerContext ctx, Object msg) { 55 | System.out.println("服务端接受的数据为:" + msg); 56 | if("quit".equals(msg)){ //服务端断开的条件 57 | ctx.close(); 58 | } 59 | Date date=new Date(); 60 | ctx.write(date);//回写数据 61 | } 62 | public void channelReadComplete(ChannelHandlerContext ctx) { 63 | System.out.println("1111"); 64 | ctx.writeAndFlush(Unpooled.EMPTY_BUFFER) //flush掉所有写回的数据 65 | .addListener(ChannelFutureListener.CLOSE); //当flush完成后关闭channel 66 | } 67 | public void exceptionCaught(ChannelHandlerContext ctx,Throwable cause) { 68 | System.out.println("2222"); 69 | cause.printStackTrace();//捕捉异常信息 70 | ctx.close();//出现异常时关闭channel 71 | } 72 | }*/ 73 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/thread/test/Test.java: -------------------------------------------------------------------------------- 1 | /** 2 | * 3 | */ 4 | package com.pancm.thread.test; 5 | 6 | import java.util.concurrent.Callable; 7 | import java.util.concurrent.ExecutionException; 8 | import java.util.concurrent.FutureTask; 9 | 10 | /** 11 | * @Title: Test 12 | * @Description: 13 | * @Version:1.0.0 14 | * @author pancm 15 | * @date 2018年5月17日 16 | */ 17 | public class Test { 18 | 19 | public static void main(String[] args) { 20 | ThreadTest threadTest=new ThreadTest(); 21 | threadTest.setPriority(1); 22 | threadTest.start(); 23 | 24 | RunalbeTest runalbeTest=new RunalbeTest(); 25 | Thread thread=new Thread(runalbeTest); 26 | thread.setPriority(10); 27 | thread.start(); 28 | 29 | CallableTest callableTest=new CallableTest(); 30 | FutureTask ft = new FutureTask(callableTest); 31 | Thread thread2=new Thread(ft); 32 | thread2.setPriority(5); 33 | thread2.start(); 34 | try { 35 | System.out.println("返回值:"+ft.get()); 36 | } catch (InterruptedException e) { 37 | e.printStackTrace(); 38 | } catch (ExecutionException e) { 39 | e.printStackTrace(); 40 | } 41 | } 42 | 43 | } 44 | 45 | 46 | class ThreadTest extends Thread{ 47 | @Override 48 | public void run() { 49 | for(int i=1;i<5;i++){ 50 | System.out.println("这是一个Thread的线程!"+i); 51 | try { 52 | sleep(50); 53 | } catch (InterruptedException e) { 54 | e.printStackTrace(); 55 | } 56 | } 57 | System.out.println("Thread的线程执行完了!"); 58 | 59 | } 60 | } 61 | 62 | 63 | class RunalbeTest implements Runnable{ 64 | @Override 65 | public void run() { 66 | for(int i=1;i<5;i++){ 67 | System.out.println("这是一个Runnable的线程!"+i); 68 | try { 69 | Thread.sleep(50); 70 | } catch (InterruptedException e) { 71 | e.printStackTrace(); 72 | } 73 | } 74 | System.out.println("Runnable的线程执行完了!"); 75 | 76 | } 77 | } 78 | 79 | 80 | class CallableTest implements Callable{ 81 | 82 | @Override 83 | public Integer call() throws Exception { 84 | for(int i=1;i<5;i++){ 85 | System.out.println("这是一个Callable的线程!"+i); 86 | try { 87 | Thread.sleep(50); 88 | } catch (InterruptedException e) { 89 | e.printStackTrace(); 90 | } 91 | } 92 | System.out.println("Callable的线程执行完了!"); 93 | return 2; 94 | } 95 | } 96 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/one/WordCountApp.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.one; 2 | 3 | import org.apache.storm.Config; 4 | import org.apache.storm.LocalCluster; 5 | import org.apache.storm.StormSubmitter; 6 | import org.apache.storm.generated.AlreadyAliveException; 7 | import org.apache.storm.generated.AuthorizationException; 8 | import org.apache.storm.generated.InvalidTopologyException; 9 | import org.apache.storm.generated.StormTopology; 10 | import org.apache.storm.topology.TopologyBuilder; 11 | import org.apache.storm.tuple.Fields; 12 | 13 | 14 | 15 | /** 16 | * 17 | * Title: WordCountApp 18 | * Description: 测试storm本地模式 统计words单次个数 19 | * 源代码地址:http://www.tianshouzhi.com/api/tutorials/storm/54 20 | * Version:1.0.0 21 | * @author pancm 22 | * @date 2017年12月28日 23 | */ 24 | public class WordCountApp { 25 | public static void main(String[] args) throws InterruptedException, AlreadyAliveException, InvalidTopologyException { 26 | //定义拓扑 27 | TopologyBuilder builder = new TopologyBuilder(); 28 | builder.setSpout("word-reader" , new WordReader()); 29 | builder.setBolt("word-normalizer" , new WordNormalizer()).shuffleGrouping("word-reader" ); 30 | builder.setBolt("word-counter" , new WordCounter()).fieldsGrouping("word-normalizer" , new Fields("word")); 31 | StormTopology topology = builder.createTopology(); 32 | //配置 33 | 34 | Config conf = new Config(); 35 | String fileName ="words.txt" ; 36 | conf.put("fileName" , fileName ); 37 | conf.setDebug(false); 38 | 39 | //运行拓扑 40 | System.out.println("开始..."); 41 | if(args !=null&&args.length>0){ //有参数时,表示向集群提交作业,并把第一个参数当做topology名称 42 | System.out.println("远程模式"); 43 | try { 44 | StormSubmitter.submitTopology(args[0], conf, topology); 45 | } catch (AuthorizationException e) { 46 | e.printStackTrace(); 47 | } 48 | } else{//没有参数时,本地提交 49 | //启动本地模式 50 | System.out.println("本地模式"); 51 | LocalCluster cluster = new LocalCluster(); 52 | cluster.submitTopology("Getting-Started-Topologie" , conf , topology ); 53 | Thread.sleep(5000); 54 | //关闭本地集群 55 | cluster.shutdown(); 56 | } 57 | System.out.println("结束"); 58 | 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/example/WordCountApp.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.example; 2 | 3 | import org.apache.storm.Config; 4 | import org.apache.storm.LocalCluster; 5 | import org.apache.storm.StormSubmitter; 6 | import org.apache.storm.generated.AlreadyAliveException; 7 | import org.apache.storm.generated.AuthorizationException; 8 | import org.apache.storm.generated.InvalidTopologyException; 9 | import org.apache.storm.generated.StormTopology; 10 | import org.apache.storm.topology.TopologyBuilder; 11 | import org.apache.storm.tuple.Fields; 12 | 13 | 14 | 15 | /** 16 | * 17 | * Title: WordCountApp 18 | * Description: 测试storm本地模式 统计words单次个数 19 | * 源代码地址:http://www.tianshouzhi.com/api/tutorials/storm/54 20 | * Version:1.0.0 21 | * @author pancm 22 | * @date 2017年12月28日 23 | */ 24 | public class WordCountApp { 25 | public static void main(String[] args) throws InterruptedException, AlreadyAliveException, InvalidTopologyException { 26 | //定义拓扑 27 | TopologyBuilder builder = new TopologyBuilder(); 28 | builder.setSpout("word-reader" , new WordReader()); 29 | builder.setBolt("word-normalizer" , new WordNormalizer()).shuffleGrouping("word-reader" ); 30 | builder.setBolt("word-counter" , new WordCounter()).fieldsGrouping("word-normalizer" , new Fields("word")); 31 | StormTopology topology = builder.createTopology(); 32 | //配置 33 | 34 | Config conf = new Config(); 35 | String fileName ="words.txt" ; 36 | conf.put("fileName" , fileName ); 37 | conf.setDebug(false); 38 | 39 | //运行拓扑 40 | System.out.println("开始..."); 41 | if(args !=null&&args.length>0){ //有参数时,表示向集群提交作业,并把第一个参数当做topology名称 42 | System.out.println("远程模式"); 43 | try { 44 | StormSubmitter.submitTopology(args[0], conf, topology); 45 | } catch (AuthorizationException e) { 46 | e.printStackTrace(); 47 | } 48 | } else{//没有参数时,本地提交 49 | //启动本地模式 50 | System.out.println("本地模式"); 51 | LocalCluster cluster = new LocalCluster(); 52 | cluster.submitTopology("Getting-Started-Topologie" , conf , topology ); 53 | Thread.sleep(5000); 54 | //关闭本地集群 55 | cluster.shutdown(); 56 | } 57 | System.out.println("结束"); 58 | 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/bigdata/storm/test/TestSpout.java: -------------------------------------------------------------------------------- 1 | package com.pancm.bigdata.storm.test; 2 | 3 | import java.util.Map; 4 | 5 | import org.apache.storm.spout.SpoutOutputCollector; 6 | import org.apache.storm.task.TopologyContext; 7 | import org.apache.storm.topology.OutputFieldsDeclarer; 8 | import org.apache.storm.topology.base.BaseRichSpout; 9 | import org.apache.storm.tuple.Fields; 10 | import org.apache.storm.tuple.Values; 11 | 12 | /** 13 | * 14 | * Title: TestSpout 15 | * Description: 16 | * Spout 发射器 17 | * 用于向Bolt发送消息 18 | * Version:1.0.0 19 | * @author pancm 20 | * @date 2018年3月6日 21 | */ 22 | public class TestSpout extends BaseRichSpout{ 23 | 24 | private static final long serialVersionUID = 225243592780939490L; 25 | 26 | private SpoutOutputCollector collector; 27 | private String message="这是个测试消息!"; 28 | private static final String field="test"; 29 | private long count=1; 30 | 31 | 32 | /** 33 | * open()方法中是在ISpout接口中定义,在Spout组件初始化时被调用。 34 | * 有三个参数: 35 | * 1.Storm配置的Map; 36 | * 2.topology中组件的信息; 37 | * 3.发射tuple的方法; 38 | */ 39 | @Override 40 | public void open(Map map, TopologyContext arg1, SpoutOutputCollector collector) { 41 | System.out.println("open:"+map.get("test")); 42 | this.collector = collector; 43 | } 44 | 45 | /** 46 | * nextTuple()方法是Spout实现的核心。 47 | * 也就是主要执行方法,用于输出信息,通过collector.emit方法发射。 48 | */ 49 | @Override 50 | public void nextTuple() { 51 | if(count<=2){ 52 | System.out.println("第"+count+"次开始发送数据..."); 53 | this.collector.emit(new Values(message)); 54 | } 55 | count++; 56 | } 57 | 58 | 59 | /** 60 | * declareOutputFields是在IComponent接口中定义,用于声明数据格式。 61 | * 即输出的一个Tuple中,包含几个字段。 62 | */ 63 | @Override 64 | public void declareOutputFields(OutputFieldsDeclarer declarer) { 65 | System.out.println("定义格式..."); 66 | declarer.declare(new Fields(field)); 67 | } 68 | 69 | /** 70 | * 当一个Tuple处理成功时,会调用这个方法 71 | */ 72 | @Override 73 | public void ack(Object obj) { 74 | System.out.println("ack:"+obj); 75 | } 76 | 77 | /** 78 | * 当Topology停止时,会调用这个方法 79 | */ 80 | @Override 81 | public void close() { 82 | System.out.println("关闭..."); 83 | } 84 | 85 | /** 86 | * 当一个Tuple处理失败时,会调用这个方法 87 | */ 88 | @Override 89 | public void fail(Object obj) { 90 | System.out.println("失败:"+obj); 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo3/NettyClientDemo3.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo3; 2 | 3 | import java.io.IOException; 4 | 5 | import io.netty.bootstrap.Bootstrap; 6 | import io.netty.channel.Channel; 7 | import io.netty.channel.ChannelInitializer; 8 | import io.netty.channel.ChannelOption; 9 | import io.netty.channel.ChannelPipeline; 10 | import io.netty.channel.EventLoopGroup; 11 | import io.netty.channel.nio.NioEventLoopGroup; 12 | import io.netty.channel.socket.SocketChannel; 13 | import io.netty.channel.socket.nio.NioSocketChannel; 14 | 15 | /** 16 | * 17 | * Title: NettyClientDemo3 18 | * Description: Netty客户端 测试自定义解码器 19 | * Version:1.0.0 20 | * @author pancm 21 | * @date 2017年9月21日 22 | */ 23 | public class NettyClientDemo3 { 24 | public static String host = "127.0.0.1"; //ip地址 25 | public static int port = 3456; //端口 26 | /// 通过nio方式来接收连接和处理连接 27 | private static EventLoopGroup group = new NioEventLoopGroup(); 28 | private static Bootstrap b = new Bootstrap(); 29 | private static Channel ch=null; 30 | 31 | /** 32 | * Netty创建全部都是实现自AbstractBootstrap。 33 | * 客户端的是Bootstrap,服务端的则是ServerBootstrap。 34 | **/ 35 | public static void main(String[] args) throws InterruptedException, IOException { 36 | b.group(group) 37 | .channel(NioSocketChannel.class) 38 | .option(ChannelOption.TCP_NODELAY,true) 39 | .handler(new ChannelInitializer() { 40 | @Override 41 | public void initChannel(SocketChannel ch) throws Exception { 42 | ChannelPipeline p = ch.pipeline(); 43 | p.addLast(new NettyEncoder()); //绑定自定义编码器 44 | p.addLast(new NettyClientHandlerDemo3()); //绑定自定义业务 45 | } 46 | }); 47 | // 连接服务端 48 | ch = b.connect(host, port).sync().channel(); 49 | System.out.println("客户端成功启动..."); 50 | star(); 51 | } 52 | 53 | public static void star() throws IOException{ 54 | String str="你好,Netty"; 55 | NettyMsg customMsg = new NettyMsg((byte)0xAB, (byte)0xCD, str.length(), str); 56 | ch.writeAndFlush(customMsg); 57 | System.out.println("客户端发送数据:"+customMsg); 58 | } 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/examples/DataProducer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.examples; 2 | 3 | import java.util.Properties; 4 | import java.util.Random; 5 | 6 | import org.apache.kafka.clients.producer.KafkaProducer; 7 | import org.apache.kafka.clients.producer.Producer; 8 | import org.apache.kafka.clients.producer.ProducerRecord; 9 | 10 | public class DataProducer { 11 | private static Random random = new Random(93285); 12 | private static Producer producer; 13 | 14 | public static void main(String args[]) { 15 | Properties props = new Properties(); 16 | props.put("bootstrap.servers", "192.168.125.172:9092"); 17 | props.put("acks", "all"); 18 | props.put("retries", 0); 19 | props.put("batch.size", 16384); 20 | props.put("linger.ms", 1); 21 | props.put("buffer.memory", 33554432); 22 | props.put("key.serializer", "org.apache.kafka.common.serialization.StringSerializer"); 23 | props.put("value.serializer", "org.apache.kafka.common.serialization.StringSerializer"); 24 | producer = new KafkaProducer<>(props); 25 | int count = 0; 26 | long startTime = System.nanoTime(); // 获取开始时间 27 | int tdata = 0; 28 | double hdata = 0.0; 29 | while (true) { 30 | int choise = 0 + random.nextInt(10000); 31 | switch (choise) { 32 | case 0: 33 | tdata = createRandom(-30, -20); 34 | hdata = createRandom(0.0, 4.9); 35 | break; 36 | case 9999: 37 | tdata = createRandom(60, 70); 38 | hdata = createRandom(96.0, 100.0); 39 | break; 40 | default: 41 | tdata = createRandom(-19, 59); 42 | hdata = createRandom(5.0, 95.9); 43 | break; 44 | } 45 | producer.send(new ProducerRecord(args[0], "temper:" + tdata + "," + "humi:" + hdata)); 46 | long endTime = System.nanoTime(); 47 | count++; 48 | int a = (int) ((endTime - startTime) * Math.pow(10, -9)); 49 | if (a == 1) { 50 | System.out.println(args[0] + "每秒发送:" + count + "条数据"); 51 | count = 0; 52 | startTime = System.nanoTime(); 53 | } 54 | } 55 | 56 | } 57 | 58 | private static int createRandom(int min, int max) { 59 | return min + random.nextInt(max - min); 60 | } 61 | 62 | private static double createRandom(double min, double max) { 63 | if (min == 0) { 64 | return max - random.nextDouble(); 65 | } 66 | return max - random.nextDouble() * min; 67 | 68 | } 69 | 70 | } 71 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/interpreter/InterpreterTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.interpreter; 2 | 3 | /** 4 | * @Title: InterpreterTest 5 | * @Description: 解释器模式 6 | 解释器模式(Interpreter Pattern)是类的行为模式。给定一个语言之后,解释器模式可以定义出其文法的一种表示,并同时提供一个解释器。客户端可以使用这个解释器来解释这个语言中的句子。 7 | * 比如正则表达式 8 | * @Version:1.0.0 9 | * @author pancm 10 | * @date 2018年8月8日 11 | */ 12 | public class InterpreterTest { 13 | 14 | /** 15 | * @param args 16 | */ 17 | public static void main(String[] args) { 18 | 19 | 20 | 21 | String word = "好好学习,天天向上!"; 22 | Expreeion expreeion =new BaiduExpreeion(); 23 | Expreeion expreeion2 =new YouDaoExpreeion(); 24 | Expreeion expreeion3 =new XuWuJingExpreeion(); 25 | expreeion.interpert(word); 26 | expreeion2.interpert(word); 27 | expreeion3.interpert(word); 28 | 29 | 30 | /* 31 | 输出结果: 32 | 百度翻译:好好学习,天天向上! 的英文是 Study hard and keep up! 33 | 有道翻译:好好学习,天天向上! 的英文是 study hard and make progress every day! 34 | xuwujing翻译:好好学习,天天向上! 的英文是 Good good study, day day up! 35 | 36 | */ 37 | 38 | /* 39 | 40 | 应用实例:编译器、运算表达式计算。 41 | 42 | 优点: 1、可扩展性比较好,灵活。 2、增加了新的解释表达式的方式。 3、易于实现简单文法。 43 | 44 | 缺点: 1、可利用场景比较少。 2、对于复杂的文法比较难维护。 3、解释器模式会引起类膨胀。 4、解释器模式采用递归调用方法。 45 | 46 | 使用场景: 1、可以将一个需要解释执行的语言中的句子表示为一个抽象语法树。 2、一些重复出现的问题可以用一种简单的语言来进行表达。 3、一个简单语法需要解释的场景。 47 | 48 | */ 49 | 50 | } 51 | 52 | } 53 | 54 | 55 | 56 | /* 57 | * 定义一个表达式,有一个解释的方法 58 | */ 59 | interface Expreeion{ 60 | void interpert(String word); 61 | } 62 | 63 | class BaiduExpreeion implements Expreeion{ 64 | String str ="好好学习,天天向上!"; 65 | @Override 66 | public void interpert(String word) { 67 | //如果是这句就翻译 68 | if(str.equals(word)) { 69 | System.out.println("百度翻译:"+word+" 的英文是 Study hard and keep up!"); 70 | } 71 | } 72 | } 73 | 74 | class YouDaoExpreeion implements Expreeion{ 75 | String str ="好好学习,天天向上!"; 76 | @Override 77 | public void interpert(String word) { 78 | //如果是这句就翻译 79 | if(str.equals(word)) { 80 | System.out.println("有道翻译:"+word+" 的英文是 study hard and make progress every day!"); 81 | } 82 | } 83 | } 84 | 85 | class XuWuJingExpreeion implements Expreeion{ 86 | String str ="好好学习,天天向上!"; 87 | @Override 88 | public void interpert(String word) { 89 | //如果是这句就翻译 90 | if(str.equals(word)) { 91 | System.out.println("xuwujing翻译:"+word+" 的英文是 Good good study, day day up!"); 92 | } 93 | } 94 | } 95 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/design/nullobject/NullObjectTest.java: -------------------------------------------------------------------------------- 1 | package com.pancm.design.nullobject; 2 | 3 | /** 4 | * @Title: NullObjectTest 5 | * @Description: 空对象模式 一个空对象取代 NULL 对象实例的检查。Null 对象不是检查空值,而是反应一个不做任何动作的关系。 这样的 6 | * Null 对象也可以在数据不可用的时候提供默认的行为。 7 | * 核心: 其主要目的是在进行调用是不返回Null,而是返回一个空对象,防止空指针异常。 8 | * 9 | * @Version:1.0.0 10 | * @author pancm 11 | * @date 2018年8月8日 12 | */ 13 | public class NullObjectTest { 14 | 15 | /** 16 | * @param args 17 | */ 18 | public static void main(String[] args) { 19 | 20 | /* 21 | * 22 | */ 23 | 24 | AbstractUser au1 = UserFactory.getUser("wangwu"); 25 | AbstractUser au2 = UserFactory.getUser("xuwujing"); 26 | 27 | System.out.println(au1.isNull()); 28 | System.out.println(au1.getName()); 29 | System.out.println(au2.isNull()); 30 | System.out.println(au2.getName()); 31 | 32 | /* 33 | * 34 | * 优点: 35 | 1 .可以加强系统的稳固性,能有效防止空指针报错对整个系统的影响。 36 | 2 .不依赖客户端便可以保证系统的稳定性。 37 | 38 | 缺点: 39 | 1.需要编写较多的代码来实现空值的判断,从某种方面来说不划算。 40 | 41 | 使用场景: 42 | 需要大量对空值进行判断的时候。 43 | 44 | * 45 | */ 46 | } 47 | 48 | } 49 | 50 | //定义一个抽象类 51 | interface AbstractUser { 52 | String getName(); 53 | 54 | boolean isNull(); 55 | } 56 | 57 | //实际用户 58 | class RealUser implements AbstractUser { 59 | private String name; 60 | 61 | public RealUser(String name) { 62 | this.name = name; 63 | } 64 | 65 | @Override 66 | public String getName() { 67 | return name; 68 | } 69 | 70 | @Override 71 | public boolean isNull() { 72 | return false; 73 | } 74 | } 75 | 76 | class NullUser implements AbstractUser { 77 | 78 | @Override 79 | public String getName() { 80 | return "user is not exist"; 81 | } 82 | 83 | @Override 84 | public boolean isNull() { 85 | return true; 86 | } 87 | } 88 | 89 | //定义一个工厂 90 | class UserFactory { 91 | 92 | public static final String[] names = { "zhangsan", "lisi", "xuwujing" }; 93 | 94 | public static AbstractUser getUser(String name) { 95 | for (int i = 0; i < names.length; i++) { 96 | if (names[i].equalsIgnoreCase(name)) { 97 | return new RealUser(name); 98 | } 99 | } 100 | return new NullUser(); 101 | } 102 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/basics/ReflectTest2.java: -------------------------------------------------------------------------------- 1 | package com.pancm.basics; 2 | 3 | import java.lang.reflect.Method; 4 | 5 | /** 6 | * 7 | * Title: ReflectTest2 8 | * Description: 9 | * 反射测试 10 | *  反射的基本步骤: 11 | 1、获得class对象,就是获取到指定的名称的字节码文件对象。 12 | 2、实例化对象,获得类的属性、方法或构造函数。 13 | 3、访问属性、调用方法、调用构造函数创建对象。 14 | * Version:1.0.0 15 | * @author pancm 16 | * @date 2018年2月28日 17 | */ 18 | public class ReflectTest2 { 19 | 20 | public static void main(String[] args) throws ReflectiveOperationException { 21 | method_1(); 22 | method_2(); 23 | method_3(); 24 | method_4(); 25 | } 26 | 27 | /** 28 | * 获取该类中的所有方法 29 | */ 30 | private static void method_1() throws ReflectiveOperationException { 31 | //指定类和路径 32 | Class clazz=Class.forName("com.pancm.test.reflectTest.User"); 33 | // Class clazz=User.class; 34 | //获取的是该类中的公有方法和父类中的公有方法。 35 | Method[] methods=clazz.getMethods(); 36 | //获取本类中的方法,包含私有方法。 37 | methods=clazz.getDeclaredMethods(); 38 | for(Method me:methods){ 39 | System.out.println("方法:"+me); 40 | } 41 | } 42 | 43 | /** 44 | * 获取指定方法 45 | */ 46 | @SuppressWarnings({ "unchecked", "rawtypes" }) 47 | private static void method_2() throws ReflectiveOperationException { 48 | //指定类和路径 49 | Class clazz=Class.forName("com.pancm.test.reflectTest.User"); 50 | //获取的指定名称的方法 51 | //如果带有入参,则指定入参类型 52 | Method method=clazz.getMethod("getMessage2",int.class); 53 | //初始化 54 | Object obj=clazz.newInstance(); 55 | //执行该方法 56 | method.invoke(obj, 11); 57 | } 58 | 59 | 60 | /** 61 | * 获取私有的方法 62 | */ 63 | @SuppressWarnings({ "unchecked", "rawtypes" }) 64 | private static void method_3() throws ReflectiveOperationException { 65 | //指定类和路径 66 | Class clazz=Class.forName("com.pancm.test.reflectTest.User"); 67 | //获取私有的方法,必须要使用getDeclaredMethod 68 | Method method=clazz.getDeclaredMethod("getMessage3", null); 69 | //私有方法不能直接访问,因为权限不够。非要访问,可以通过暴力的方式。 70 | method.setAccessible(true); 71 | } 72 | 73 | 74 | /** 75 | * 获取静态方法 76 | */ 77 | @SuppressWarnings({ "unchecked", "rawtypes" }) 78 | private static void method_4() throws ReflectiveOperationException { 79 | //指定类和路径 80 | Class clazz=Class.forName("com.pancm.test.reflectTest.User"); 81 | //获取私有的方法,必须要使用getDeclaredMethod 82 | Method method=clazz.getMethod("getMessage4",String.class); 83 | System.out.println(); 84 | method.invoke(null, "测试"); 85 | } 86 | 87 | } 88 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo4/NettyServerDemo4.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo4; 2 | 3 | import java.net.InetSocketAddress; 4 | 5 | import io.netty.bootstrap.ServerBootstrap; 6 | import io.netty.channel.ChannelFuture; 7 | import io.netty.channel.ChannelInitializer; 8 | import io.netty.channel.ChannelOption; 9 | import io.netty.channel.ChannelPipeline; 10 | import io.netty.channel.EventLoopGroup; 11 | import io.netty.channel.nio.NioEventLoopGroup; 12 | import io.netty.channel.socket.SocketChannel; 13 | import io.netty.channel.socket.nio.NioServerSocketChannel; 14 | import io.netty.handler.codec.string.StringDecoder; 15 | 16 | /** 17 | * 18 | * Description: Netty 服务端 测试自定义解码器 19 | * Version:1.0.0 20 | * @author pancm 21 | * @date 2017年9月21日 22 | */ 23 | public class NettyServerDemo4 { 24 | 25 | private final static int port=4567; 26 | 27 | 28 | public void start(){ 29 | EventLoopGroup bossGroup = new NioEventLoopGroup(1); 30 | EventLoopGroup workerGroup = new NioEventLoopGroup(); 31 | try { 32 | ServerBootstrap sbs = new ServerBootstrap().group(bossGroup,workerGroup).channel(NioServerSocketChannel.class).localAddress(new InetSocketAddress(port)) 33 | .childHandler(new ChannelInitializer() { 34 | 35 | protected void initChannel(SocketChannel ch) throws Exception { 36 | ChannelPipeline p = ch.pipeline(); 37 | p.addLast(new StringDecoder()); 38 | p.addLast(new NettyServerHandlerDemo4()); //绑定自定义业务逻辑 39 | }; 40 | 41 | }).option(ChannelOption.SO_BACKLOG, 128) 42 | .childOption(ChannelOption.SO_KEEPALIVE, true); 43 | // 绑定端口,开始接收进来的连接 44 | ChannelFuture future = sbs.bind(port).sync(); 45 | 46 | System.out.println("Netty服务端启动成功,端口为: " + port ); 47 | future.channel().closeFuture().sync(); //释放监听 48 | } catch (Exception e) { 49 | bossGroup.shutdownGracefully(); //释放资源 50 | workerGroup.shutdownGracefully(); 51 | } 52 | } 53 | 54 | public static void main(String[] args) throws Exception { 55 | new NettyServerDemo4().start(); 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /src/main/java/com/pancm/mq/kafka/others/TestProducer.java: -------------------------------------------------------------------------------- 1 | package com.pancm.mq.kafka.others; 2 | 3 | import java.util.Properties; 4 | 5 | import org.apache.kafka.clients.producer.KafkaProducer; 6 | import org.apache.kafka.clients.producer.Producer; 7 | import org.apache.kafka.clients.producer.ProducerRecord; 8 | 9 | public class TestProducer { 10 | public static void main(String[] args) { 11 | System.out.println("开始..."); 12 | Properties props = new Properties(); 13 | props.put("bootstrap.servers", "192.169.0.23:9092"); 14 | //The "all" setting we have specified will result in blocking on the full commit of the record, the slowest but most durable setting. 15 | //“所有”设置将导致记录的完整提交阻塞,最慢的,但最持久的设置。 16 | props.put("acks", "all"); 17 | //如果请求失败,生产者也会自动重试,即使设置成0 the producer can automatically retry. 18 | props.put("retries", 0); 19 | 20 | //The producer maintains buffers of unsent records for each partition. 21 | props.put("batch.size", 16384); 22 | //默认立即发送,这里这是延时毫秒数 23 | props.put("linger.ms", 1); 24 | //生产者缓冲大小,当缓冲区耗尽后,额外的发送调用将被阻塞。时间超过max.block.ms将抛出TimeoutException 25 | props.put("buffer.memory", 33554432); 26 | //The key.serializer and value.serializer instruct how to turn the key and value objects the user provides with their ProducerRecord into bytes. 27 | props.put("key.serializer", "org.apache.kafka.common.serialization.StringSerializer"); 28 | props.put("value.serializer", "org.apache.kafka.common.serialization.StringSerializer"); 29 | 30 | //创建kafka的生产者类 31 | Producer producer = new KafkaProducer(props); 32 | long startTime=System.currentTimeMillis(); 33 | producer.send(new ProducerRecord("test1",1,startTime,"a","b")); 34 | producer.close(); 35 | //生产者的主要方法 36 | // close();//Close this producer. 37 | // close(long timeout, TimeUnit timeUnit); //This method waits up to timeout for the producer to complete the sending of all incomplete requests. 38 | // flush() ;所有缓存记录被立刻发送 39 | // for(int i = 0; i < 100; i++){ 40 | // //这里平均写入4个分区 41 | // producer.send(new ProducerRecord("foo",i%4, Integer.toString(i), Integer.toString(i))); 42 | // producer.close(); 43 | // } 44 | System.out.println("结束"); 45 | } 46 | } -------------------------------------------------------------------------------- /src/main/java/com/pancm/nio/netty/demo4/NettyClientDemo4.java: -------------------------------------------------------------------------------- 1 | package com.pancm.nio.netty.demo4; 2 | 3 | import java.io.IOException; 4 | 5 | import io.netty.bootstrap.Bootstrap; 6 | import io.netty.channel.Channel; 7 | import io.netty.channel.ChannelInitializer; 8 | import io.netty.channel.ChannelOption; 9 | import io.netty.channel.ChannelPipeline; 10 | import io.netty.channel.EventLoopGroup; 11 | import io.netty.channel.nio.NioEventLoopGroup; 12 | import io.netty.channel.socket.SocketChannel; 13 | import io.netty.channel.socket.nio.NioSocketChannel; 14 | import io.netty.handler.codec.string.StringDecoder; 15 | 16 | /** 17 | * 18 | * Title: NettyClientDemo4 19 | * Description: Netty客户端 20 | * Version:1.0.0 21 | * @author pancm 22 | * @date 2017年9月21日 23 | */ 24 | public class NettyClientDemo4 { 25 | public static String host = "127.0.0.1"; //ip地址 26 | public static int port = 4567; //端口 27 | /// 通过nio方式来接收连接和处理连接 28 | private static EventLoopGroup group = new NioEventLoopGroup(); 29 | private static Bootstrap b = new Bootstrap(); 30 | private static Channel ch=null; 31 | 32 | /** 33 | * Netty创建全部都是实现自AbstractBootstrap。 34 | * 客户端的是Bootstrap,服务端的则是ServerBootstrap。 35 | **/ 36 | public static void main(String[] args) throws InterruptedException, IOException { 37 | b.group(group) 38 | .channel(NioSocketChannel.class) 39 | .option(ChannelOption.TCP_NODELAY,true) 40 | .handler(new ChannelInitializer() { 41 | @Override 42 | public void initChannel(SocketChannel ch) throws Exception { 43 | ChannelPipeline p = ch.pipeline(); 44 | p.addLast(new StringDecoder()); //绑定自定义编码器 45 | p.addLast(new NettyClientHandlerDemo4()); //绑定自定义业务 46 | } 47 | }); 48 | // 连接服务端 49 | ch = b.connect(host, port).sync().channel(); 50 | System.out.println("客户端成功启动..."); 51 | //发送消息 52 | star(); 53 | } 54 | 55 | public static void star() throws IOException{ 56 | NettySendBody nsb=new NettySendBody(); 57 | nsb.put("Netty","Hello"); 58 | nsb.put("JAVA","从入门到入土"); 59 | nsb.put("SQL","从删库到跑路"); 60 | ch.writeAndFlush(nsb); 61 | System.out.println("客户端发送数据:"+nsb.toString()); 62 | } 63 | } 64 | --------------------------------------------------------------------------------