- 博客(52)
- 资源 (2)
- 收藏
- 关注
原创 Lucene的Smart CN实现分词、停用词、扩展词
Lucene 中提供了 SmartCN 为中文提供分词功能,实际应用中还会涉及到停用词、扩展词(特殊词、专业词)等,因此本文将聚焦在 SmartCN 而暂时不考虑其他中文分词类库。1 简介analyzers-smartcn 是一个用于简体中文索引词的 Analyzer。但是需要注意的它提供的 API 是试验性的,后续版本中可能进行更改。可以它包含了如下两部分:org.apache.lucene.analysis.cn.smart 用于简体中文的分析器,用来建立索引。org.apache.luce.
2020-05-24 15:22:08 1034
原创 实战 TDD(9):Pair Programming
Pair (结对)已经不是什么新鲜的事情。工作中我们进行 Pair。但是也会经常发现一个问题:“两个人单纯的坐在一起工作或者被领导命令坐到一起工作,并没有什么工作效率提升的“。工作中许多人对 Pair 这个词的理解多于 Pair 应该怎么做的理解。这篇文章将详细描述关于 Pair 的中的详细细节,主要设计内容如下:什么是 Pair Programming?为什么我们要做 Pair Prog...
2020-04-20 21:18:22 434
原创 实战 TDD (2): Tasking to Action
如果给我一个小时来砍树,我会先花 20 分钟来磨刀。 ---- 林肯在上一篇内容 TDD 实战(1) 通过一个案例来展现了 TDD coding 的过程,编码之前首先要做的事情就是确保已经准确理解了需求。TDD 也不例外如果需求不能获取准确后续用什么实践都无法完全交付想要的。工作中有 BA 人员来挖去需求,DEV 将业务需求转化为软件功能,其中 Tas...
2020-04-01 11:02:29 577 1
原创 TDD 实战(1)
工作常见的几种情况:0,想了解 TDD 如何做,但是找到的资料多时十多年前的内容了,甚至里面没有明确说明要怎么做1, 听到身边人的谈论TDD,但是并使轮到工作时却不知道怎么用TDD2,本来要学 TDD 结果显示得到了一大堆的道理,无从下手3,看到那些讲 TDD 自己工作中都不用TDD本文将通过实战的方式来讲解 TDD,以代码为主,“少讲道理,多练习”。当需要的时候才会引入一些理论或...
2020-03-11 16:17:40 666
原创 实战 PostgreSQL 分区表
我们在之前的《实战PostgreSQL》 详细描述的 PostgreSQL 的版本差别、JSON/JSONB、全文检索等相关信息,PostgreSQL 远比上述三点内容,这篇文章将实战 PostgreSQL 分区表。01,什么是分区表?如下图,分区表就是根据分区策略,将数据数据分散到不同的子表中,并通过父表建立关联关系,从而实现数据物理上的分区。02,PostgreSQL 提供的分区表功...
2020-03-04 21:56:16 1253
原创 为架构填坑的正确姿势
看看下面的问题是否经常出现在你的团队中:1,项目中经常出现循环依赖的问题2,开发者日常开发出现问题,总是被管教3,项目架构实际情况和目标差距只能靠拍着脑袋说百分比。4,作为架构师除了开会沟通、画架构图、了解业务,不清楚还做些什么如果你也遇到上述问题并寻找解决方法,这篇文章或许适合你。解决上面的问题可以使用“适应度函数”。什么是适应度函数 ?简单来讲一个适应度函数就是度量某个目标...
2020-03-01 23:16:35 229
原创 架构上“坑”了小伙伴如何填?
软件开发中大小坑遍地,架构设计上同样到处都是坑坑洼洼。随着工作经验积累的增加,自己也开始接触架构,自己做架构设计,也参考别人的架构设计。由于自己的经验和精力有限坑过小伙伴,也被小伙伴坑过。言归正传,本文不是吐槽架构上的坑,而是整理一些 5 种常见的坑给出填坑思路。(1) 架构产出不足(2) 架构的技能不足(3) 延迟决策坑队友(4) 年久失修的架构坑 01: 架构产出不足表...
2020-02-26 19:19:33 264
原创 PostgreSQL 初探
PostgreSQL 使我们经常选择的数据库之一。它不仅仅是关系型数据库,同时也添加了对JSON数据的支持、全文检索功能,以及其他扩展。2020 年 2月的总排名为第四名,关系型数据库中排名第四名。排名信息参考:DB-Engines为了更好地应用的工作中,针对 PostgreSQL 给我造成的疑惑整理了如下内容:(1) PostgreSQL 版本之间的主要区别(2) Postgre...
2020-02-24 22:17:41 531
原创 实战 Git 分支策略
项目上总有那么多不尽人意的地方,导致各方面出现问题。分支管理策略就是其中一个经常遇到的问题。例如:(1) 主干开发,发现代码质量不强,导致代码提交后阻塞,等待修复问题。(2)QA 进入了在 Dev 环境对应 Master 分支,由于 Dev 环境一直在合并代码,QA不得不停下来,因为服务有一段时间可能持续在部署。上述问题就会让我们思考应该如何让我们的分支管理对团队更加有效。在常见的分...
2020-02-16 21:52:47 327
原创 实战Arch Unit
在以前的文章中介绍了通过 《实战PMD》、《实战Checkstyle》在代码级守护我们的代码,比通过《实战Jacoco》来了解当前项目的测试覆盖情况。通过得到数据了解我们的项目质量,进行定向的改进。使用这些简单方面的自动化工具比凭空猜想或者全靠人力来接发现代码上的问题,效率高多了。这篇文章将聚焦在Arch Unit上,Arch Unit能通过为我们提供架构的守护。开发前的准备项目...
2020-02-15 22:43:33 635 1
原创 拼接“1亿行字符串”你会遇到什么问题?
本文将涉及到的三方面的内容,如下:1,一个10万次的for循环,4种实现的性能对比2,直接将For循环改为1亿次,遇到的问题3,拓展00. 需求原计划是生成1亿条模拟数据,详细的需求如下:创建1亿条Insert SQL语句,例如: INSERT INTO products (`id`,`code`) value (1, '000000000');其中, id ...
2020-01-17 14:31:37 231
原创 价值观和落地之间的距离
经常听到周边的同事是“敏捷是价值观”,“敏捷是价值观”,自己也说“敏捷是价值观”,今天偶然间看到群中又有人指出是对方价值观的问题。那么到底价值观是什么?价值观能给我什么?又是怎么影响我们的呢?01 什么是价值观 ?价值观就指导自己思考方式的一种思考方式。例如:小A的价值观是追求技术卓越,那么当小A做事时,不管遇到有利条件,还是不利的条件都会想到技术卓越。小B的价值观是追求商业价...
2020-01-08 18:47:32 212
原创 DDD提升我的开发效率
2019年参加了"领域驱动设计峰会2019"看到了国内、国外、不同行业在基于DDD的实践分享。成年热学习的一个特点就是带着自己的经验来思考接收到的内容,那么回顾自己接触DDD有一段时间,将自己的经验和思考作用在项目上,真真切切替换了DDD带给我的提升。本片内容将不会聚焦在哪些理论上,而是看看那些些提升我开发效率的技术部分(非具体代码的粒度)。充血模型 代替 贫血模型Domain + D...
2019-12-29 18:10:36 590 1
原创 重构分析21: 被拒绝的遗赠(Refused Bequest)
子类和父类的关系开始很简单,但是随着时间的推移有可能会变的越来越复杂。一个子类通常需要紧密的依赖其父类,但是有时会矫枉过正。这就是继承的两面性,下面我们看看继承可能代码的Code Smell。01 场景复现需求描述这是关于活动(Activity)和票(Ticket)的业务需求:活动的主题(ActityType): session | workshop | read | TDD活动(A...
2019-12-22 13:51:17 1364
翻译 如何写出好的测试
如何写出好的测试我们知道编写测试能够带来很多好处。那么除了只是停留在编写测试上,我们应该如何编写好的测试呢?这里翻译了一篇2012年Eric Lewis的一篇文章《How to write good tests》。提交历史显示,这篇内容还在一直维护。##正文开始01 保持测试代码的短小可读要实现这一点就必须产品代码进行重构。否则测试端就会因遗留代码而变得腐败。如果测试代码不能很容易的...
2019-12-20 19:00:30 160
原创 Java几种常用的断言风格你怎么选?
日常工作中,不管你是写Unit Test,还是采用TDD的编程方式进行开发,都会遇到断言。而断言的风格常见的会有Assert、BDD风格,对于这些常见的断言风格你怎么选择呢?01 Assert风格JUnit中提供了这样的assert断言风格,例如:@Test void should_be_unlocked_when_insert_coin_given_a_entrance_machi...
2019-12-15 14:08:03 249
原创 单纯的使用Optional并不能很好的解决业务中的NPE问题
工作中经常会遇到NPE(NullPointException)问题怎么处理,得到最多的回答就是Optional来处理,但是单纯的使用Optional并不能很好的解决业务中的NP问题。所以整理出日常工作中处理NPE问题的思路,供参考。先看一下思路:01 避免的操作01.01 避免入参使用 Optional日常工作中有是看到如下代码。public void execute(Optional...
2019-12-14 17:03:38 431
原创 H2 Database 实战(1):简介
H2 是一个使用 Java 编写的数据库,支持内存、文件等多种模式,经常用于项目的测试环境。除此之外,通过 H2 的官网了解到,H2 还提供了丰富的特性。1 关于 H2 的简介H2 提供了丰富的特性,这里罗列了一些引入注意的特性:性能:与 SQLit 相比较,读操作更快,但是在连接、写操作性能都不如 SQLite。功能:支持全文检索,提供了内置全文检索和使用 Apache Luncene 的全文索引对数据类型和SQL有很好的支持,兼容性好,便于移植支持嵌入式数据库、内
2020-05-22 16:04:34 440
原创 将H2应用在测试环境中
上面篇文章中介绍了 H2 的一些特性。H2 因其提供了内存数据库的模式,经常应用在测试当中,快速验证某些SQL 操作的结果。本文将 H2 应用于测试中的原因,并使用一个简单的实例说明 H2 在测试中的使用。对 H2 提供的全文索引感兴趣可参考:《H2 提供全文索引功能》1, 为什么将 H2 适合应用在测环境中?代码中的测试需要满足 FIRST 原则: Fast 快的 Independent 独立的 Repeatable 可重复的 Self-validating 自验证的
2020-05-22 16:03:46 370
原创 H2 的全文检索功能
在前面的文章中,我们介绍了 H2 的一些特性以及 为什么H2 适合应用在测试环境中。H2 不但可以作为嵌入式数据库、内存数据库使用。在适当的场景下可以选择使用 H2 替换掉 SQLite,还可利用 H2 内存数据库的特点,将它还提供了全文检索的功能。H2 内置了两个全文检索(FullText Search)的实现:**Native FullText Search。**使用 H2 中内置的全文检索,将索引存储在数据库指定的表中。Apache Lucene FullText Search。 H2 使用
2020-05-22 16:02:49 901
原创 识别代码的坏味道(四)
要想重构就需要先识别代码中存在的问题,然而问题有多种也分轻重缓急,所以Code Smell(代码坏味道)可以看作是应该首先动手解决的问题,因此重构过程可以抽象成如下简单的过程。在之前的文章中介绍了常见的 22 种代码坏味道:《识别代码中的坏味道(一)》《识别代码中的坏味道(二)》《识别代码中的坏味道(三)》本本将介绍其他 3 个代码坏味道:反复使用单个临时变量无业务意义的临时变量方法结果返回 null多层条件嵌套有副作用的查询方法假设条件符合01 反复使用单个临时变量使用单.
2020-05-20 16:18:36 350
原创 识别代码中的坏味道(三)
前两篇文章 《识别代码中的坏味道(一)》 和 《识别代码中的坏味道(二)》 中已经介绍了 18 个代码坏味道。《重构》中还涉及到另外 4 个代码坏味道,本文将将详细介绍剩余的 4 个代码坏味道。这四个代码坏味道是:中间人(Middle Man)狎昵关系不完美的库类被拒绝的遗赠01 中间人(Middle Man)在上一篇文章中 《识别代码中的坏味道(二)》 中在“过度耦合的消息链”这种代码坏味道曾经提及过中间人(Middle Man)这种代码坏味道,那么中间人到底是一类什么代码呢?中间人
2020-05-19 11:45:59 431
原创 识别代码中的坏味道(二)
在上一篇文章中,介绍了通过名字就能理解的 8 个坏味道,感兴趣可以查看识别代码中的坏味道(一)。本篇文章将识别代码中的另外 10 个代码坏味道:10个晦涩但是通过简单的即可识别的坏味道。如上图,这 10 个代码坏味道是:发散式变化霰弹式修改依恋情结数据泥球基本类型偏执平行继承体系冗赘类过度耦合信息链异曲同工的类纯数据类01 发散式变化简而言之就是一个类总是因为不同类型的原因发生变化。例如:需要修改数据源时要修改该类,需要修改缓存时还需要修改这个类,甚至当修改某个策略的计算公.
2020-05-18 16:41:25 640
原创 识别代码中的坏味道(一)
在前面的文章中,我们介绍了 《提升编程效率:重构》 以及 《何时开始重构?》。了解了那些能够更好的辅助团队或者个人进行重构,但是要让重构真正产生作用是需要能够代码中的坏味道,并消除代码中的坏味道。如下图是工作中常见的代码的坏味道:上图中的坏味道出自《重构》这本书,虽然并不是全部,但是涵盖了日常中最常见的一些代码坏味道。接触这些坏代码可以分为三类:见名知意的代码坏味道:稍微解释即可掌握的代码坏味道;通过一些例子即可掌握的代码的坏味道;本文主要聚焦在“见名知意的代码坏味道”,后.
2020-05-16 18:55:29 1015
原创 何时开始重构?
“任何时候都可以重构”,如果这样回答太过于宽泛,因为总有那么一些时候重构的 ROI (投入产出比)并不高,设置与对重构还不那么熟悉的开发者相当于什么都没有说。所以整理了下日常开发中进行重构的时间点,从而来帮助提升开发效率和重构效率。如上图:日常重构的时间点可以分为上述三个时间点。Tasking 之后,开发之前进行重构;开发过程中,进行小步重构;修复 Bug 时进行重构;01 Tasking 之后,开发之前进行重构Tasking 指的是任务拆解(如果不熟悉,可以看这个视频 或者 看这篇文章
2020-05-15 17:15:05 296
原创 提升编程效率:重构
提升编程效率的大致可以分三类:任务拆解(Tasking To Action)、使用高效的开发工具/框架、关注高效的工程实践。其中任务拆解,我们在【实战TDD(2):Tasking To Action】(视频版) 中介绍了过了。开发效率的工具/框架也才不但涌现,例如:Spring Boot、Spring Cloud、Elasticsearch 、Intellij IDEA 等为开发提供了不同领域的高效工具。工程实践的也涉及到很多,比如:TDD、重构、Clean Code 等。在过往的工作经历中,发现.
2020-05-15 15:09:52 456
原创 善用技术债
01 技术债是什么?白话的解释就是技术上的债务。比如:(1)功能已经实现,但是需要手动做很多配置的事情,不可复用;(2)某个功能为热点功能业务上更重要,因此单位时间内对该功能的技术支持更完善,其他功能凑合能用。(3)由于思路不严谨,导致某个功能状态为开发完成,但是其中功能并不完整。以上 3 个是常见的技术债,类似的技术债还有很多。技术债具有两面性:(1)技术债带来的好处: 技术有杠杆,加杠杆,有可能带来高的ROI(投资回报率); 有限时间内将精力用到最关注的地方;(2)技术债.
2020-05-14 23:27:54 233
原创 ArrayList需要了解的事情
ArrayList 是日常开发经常使用到的容器类。它能够方便的进行数据的查询、替换。但是因为其低层实现的原因在数据容量、性能、线程安全上都存在问题,主要涉及到下面的内容:(1)默认初始容量为 0,如果未指定容量则首次初始的容量为 10;同时其也是有容量限制的;(2)添加元素会涉及到数组扩容和数组元素拷贝,删除数组元素时同样也会涉及到数组的拷贝,这都会影响性能;(3)线程不安全,因为整个Ar...
2020-04-28 16:42:22 192
原创 Java多线程:使用 CompletionService 接口避免 Future 的阻塞
01 CompletionService 简介在上一篇内容中,介绍了 Future 的使用,其中也涉及到了 Future 的不足,就是当通过 get() 方法获取线程的返回值的时候,会导致阻塞,由于阻塞很多时候这回倒置性能问题。而 JDK 中提供的另外一个工具类能够帮助我们缓解或是解决阻塞的问题。CompletionService 的作用:CompletionService 接口解决 Fu...
2020-04-21 15:32:10 771
原创 从刻意练习到高效工作
2020 年过年回来在家办公的同时组织了一个能力学习小组—刻意练习小组。到目前为止时间已经过去 2 个多月,通过这个活动也是收获良多。主要收获包括以下两个方面:(1)活动运营能力(2)工作效率改进01 活动运行能力刻意练习活动的从想法到成型主要是基于三部分信息的整合。(1)服务设计原则(2)直觉(3)过往活动的经历。服务设计原则。服务设计常用的有 5 个原则,如下:完整性...
2020-04-19 15:56:57 216
原创 Java中线程池实现的两种方式
01 线程池的应用场景(1)应用比如现在收集上的修图软件。一张 1920 x1080 的图片有 200多万个像素点,对整个图片的每个像素点处理一遍也是需要不少的计算量。(2)服务器端服务器端处理大数据、大量请求时如果只是单个线程来进行,也是无法满足需求的。此外,不管是处理应用还是服务器,即使使用了多线程,如果频繁进行创建和销毁线程,最终创建和销毁的时间有可能大于真正执行的时间。将对象复...
2020-04-16 18:21:17 335
原创 使用 Phaser 更加灵活的控制阻塞节点的停留
01 PhaserPhaser 与 CountDownLatch、CyclicBarrier 做的事情类似,只是Phaser 提供了更加丰富的API,左右处理同样一个场景时,使用一个 Phaser 对象,并通过调用不同的 API 即可用更简单的方式实现相同的功能。Phaser 主要有以下功能:(1)提供了多个阻塞节点,因此可以组织一个流程中可以组织多个阻塞节点。(2)控制线程直接通过阻塞...
2020-04-16 11:22:55 268
原创 CyclicBarrier 实现阶段性同步
01 CyclicBarrierCyclicBarrier 提供了如下功能:(1)向上增加计数的功能(2)阻塞等待功能(3)阶段性同步功能(线程数大于 parties 数量时)(4)支持多次循环实现多个线程一起执行的目的。02 与 CountDownLatch 的比较(1)CountDownLatch 时计数器做减法,而 CyclicBarrier 时通过累加来实现。(2)Co...
2020-04-15 16:27:47 120
原创 CountDownLatch实现多线程等待后共同执行
01 CountDownLatchCountDownLatch 通过 count 计数实现屏障设定(阻塞),当满足设定的条件后一个或者多个线程时候一起执行。这里的屏障指的就是一个线程会被阻塞,不再继续向下执行。CountDownLatch 中的计数器会做减法。当执行到它的 await()方法之后,如果计数器不为 0,则阻塞,知道其他线程调用 countDown()之后扣减计数为 0 之后,原...
2020-04-15 15:01:35 496
原创 用 Exchanger两个线程之间的通信
01 Exchanger 作用使两个线程之间进行数据传递。(对是两个之间而不是三个或者更多个线程之间)02 常用方法exchange() 阻塞当前线程并等待其他线程来取得数据,若没有其他线程来取数据则一直等待。exchange() 传递数据exchange(V v, long timeout, TimeUnit unit) 在指定的时间内没收到消息,则抛出超时的异常。03 例子p...
2020-04-14 23:04:03 150
原创 Semaphore 并发控制
01 SemaphoreSemaphore 的作用就是控制某段程序线程并发执行的数量。这比 sychronized 功能更加强大和方便。Semaphore 有个一个参数为 permits 的构造函数。(permist 指的是同一时间内允许多少个线程同时执行 acquire()和 release()之间的代码。...private final Semaphore semaphore = n...
2020-04-14 17:47:55 228
原创 性能调试过程中经常使用的INTELLIJ IDEA 快捷键
最近解决性能测试之后的各种性能问题,解决问题的过程中快捷键能够快速帮助我解决并修复问题,提升解决问题的效率。下面是几种常见常见问题的快捷键01,标记代码位置(1)利用 BookmarksCommand + 2 打开 Favorities 窗口,将光标移动到某个 bookmark 上之后,按下 Enter 键选中,按下 ESC 将光标移动到 Editor 中对应的位置。F3 向 Bookm...
2020-03-31 17:01:56 135
原创 如何做到深度工作
01,了解自己适合的深度工作方式根据可分配的深度工作的时间比例大致分为一下四种:(1)禁欲主义的深度工作。 摒弃、最小化浮浅的职责。适合假期拥有大量的可自由支配的时间。利用“禁欲主义”可以让进将大段大段的时间放在深入工作上。(2)双峰深度工作。 将可支配的时间分为两块,某段时间用于深度工作,剩余时间用于其他事情。(3)节奏深度工作。 将深度工作融合到生活中,将其转为简单的常规习惯,创造一...
2020-03-31 01:49:40 227
原创 帮你扔掉鼠标的前端调试命令
前端调试工具总是鼠标点来点去的?可以看看这些调试命令,瞬间可以省掉很多鼠标点击行为。01,常用 console 的 API(1)console.assert()console.assert(a<400, "a should < 400");(2)console.group() 和 console.groupEnd()console.group();...cons...
2020-03-25 01:38:19 134
原创 Indellij IDEA 快捷键 Top 15
1, Option + Enter 修复问题2, F2 跳转到下一个出现问题的地方(错误,警告,建议)3, Command + 1 打开项目窗口, 可以通过方向键来浏览 项目树, 通过直接键入关键词进行搜索.4, ESC, 通过ESC 让 Editor 重新获取焦点. 当焦点在 其他IDEA的工具窗口时(例如:project, Todo, Run, Debug) 中是可以通过 ESC 回到 ...
2020-03-20 21:39:57 174
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人