高段位、不造轮子(善用工具类)

使用大众的语言,交流才会有默契。写代码亦如此!不要乱造轮子,积累轮子,搞懂轮子,最终站在巨人的肩上,才是正途。

字符串操作

org.apache.commons.lang3.StringUtils中几乎有你要的所有字符串操作。
例如:Empty(空判断)、Blank(空白字符判断)、truncate(保留部分长度)、左右保留、左右追加、trim(去掉首位字符ASCII码小于32)、strip(去掉首位空白字符或指定字符)、重复、拼接、分割等等。

如果你需要获取两个字符串的共同前(后)缀nullToEmpty操作,com.google.common.base.Strings中你可以找到想要的。

如果你需要根据组合复杂条件进行字符筛选,过滤,删除等操作,com.google.common.base.CharMatcher是不错的选择,例如:

CharMatcher charMatcher = CharMatcher.inRange('0', '9').or(CharMatcher.inRange('a', 'b'));
System.out.println(charMatcher.retainFrom("abcd123dd")); //ab123
System.out.println(charMatcher.removeFrom("abcd123dd")); //cddd

千万记住,如果能够使用字符操作,尽量不要用字符串正则匹配,因为性能差一个量级,例如:

//三个方法同样的效果,我机器上第一个方法性能差10倍
String uuid = UUID.randomUUID().toString();
System.out.println(StringUtils.removeAll(uuid, "-"));
System.out.println(StringUtils.remove(uuid, '-'));
System.out.println(CharMatcher.is('-').removeFrom(uuid));

如果需要连接成字符串的集合中有元素为null,那你就要小心了,你可能需要com.google.common.base.Joiner。例如:

 //new一个有null元素的ArrayList
List list = Lists.newArrayList(new Integer(1), new Integer(2), null, new Integer(3));  
System.out.println(StringUtils.join(list.iterator(), ',')); //1,2,,3
System.out.println(Joiner.on(',').skipNulls().join(list)); //1,2,3
//System.out.println(Joiner.on(',').join(list)); //空指针

//new一个key或者value是null的Map
Map<String, Integer> map = new HashMap<>();
map.put("a", 1);
map.put("b", null);
map.put(null, 3);
System.out.println(Joiner.on(',').withKeyValueSeparator('-').useForNull("空").join(map)); //空-3,a-1,b-空 

记住一条,对null没有默认处理,不要想当然,需要格外注意,例如:

 //StringBuilder会把null元素转换为值为null的字符串
System.out.println(new StringBuilder().append((String) null).append('-').append("a")); //null-a

注意:字符串+就是 StringBuilder.append()

如果想要对字符串进行分割,最好不要使用StringUtils.split(),因为它的规则不够清晰,而是要用com.google.common.base.Splitter,例如:

String param = ", ,a,b  ,";
System.out.println(Arrays.toString(StringUtils.split(param, ','))); //[ , a, b  ]
System.out.println(Splitter.on(',').omitEmptyStrings().trimResults().splitToList(param)); //[a, b]

字符编码(Charset)常量

不要纠结于选择,来点默契,定个约定:
优先选择com.google.common.base.Charsets
上面没有引入就选org.apache.commons.codec.Charsets
最后jdk1.8才有的java.nio.charset.StandardCharsets

日期处理

日期增、减、字符串解析成Date,可以使用
org.apache.commons.lang3.time.DateUtils
日期格式化成字符串,可以使用
org.apache.commons.lang3.time.DateFormatUtils
如果需要指定瞬间进行日期时间初始化,可以使用org.joda.time.DateTime,例如:

System.out.println(new DateTime(2018, 12, 1, 13, 1, 1).toDate()); //Sat Dec 01 13:01:01 CST 2018

另外,SimpleDateFormat就不要再让它出现了!

数字操作

不能不识:org.apache.commons.lang3.math.NumberUtils
提供了很多常用的基本类型包装类的常量,以及很多便捷操作:

  • 字符串转数字失败返回默认值
    NumberUtils.toInt(java.lang.String, int)
    NumberUtils.toLong(java.lang.String, int)
    ......
    提供所有基本类型数字操作方法,也有参数是一个的方法,默认值则是0,如果你不想转换抛出异常,就不要用原生API。
  • 返回最大或最小
    NumberUtils.max(...)
    NumberUtils.min(...)
    支持所有的基本类型数组,当然如果你只有2个值比较, 下面方式可能会更好:
    java.lang.Math.max(x, y)
    java.lang.Math.min(x, y)

随机生成器

字符串随机生成,可以使用:
org.apache.commons.lang3.RandomStringUtils
注意:如果要生成只包含数字的字符串,
不能使用: RandomStringUtils.randomNumeric(int)
而要使用: RandomStringUtils.random(int, "0123456789")
因为性能有近10倍差距,至于为什么?自行研究。

随机数生成工具
org.apache.commons.lang3.RandomUtils
简单易用,就不多说。

反射

三个常见工具类:

  • org.apache.commons.lang3.ClassUtils
  • org.apache.commons.lang3.reflect.FieldUtils
  • org.apache.commons.lang3.reflect.MethodUtils

通过ClassUtils可以获取所有接口、所有的父类等类定义相关的操作,也可以获取数组每个元素类型,例如:Class<?>[] toClass(final Object... array)
通过FieldUtils可以方便的属性操作:查、读、写;
通过MethodUtils可以方便方法操作:获取、调用。
通过工具类,可以饶过JDK方法、字段反射操作的限制。具体可以参考:JAVA反射,用好就这点东西

如果需要遍历所有字段或方法进行某种操作,可以使用:
org.springframework.util.ReflectionUtils,例如:

doWithMethods(Class<?> clazz, MethodCallback mc)
doWithLocalMethods(Class<?> clazz, MethodCallback mc) 
doWithMethods(Class<?> clazz, MethodCallback mc, MethodFilter mf) 
doWithFields(Class<?> clazz, FieldCallback fc) 
doWithLocalFields(Class<?> clazz, FieldCallback fc)
doWithFields(Class<?> clazz, FieldCallback fc, FieldFilter ff)

ReflectionUtils这个类我在RPC中动态代理中有使用。

判断访问权限,可以使用java.lang.reflect.Modifier,当然你可能永远不会使用。

获取Springbean的目标对象,可以使用:org.springframework.aop.framework.AopProxyUtils.ultimateTargetClass()
主要功能:如果是cglib生成的代理类,则返回父类。

注解操作

获取注解,判断是否有注解等,使用
org.springframework.core.annotation.AnnotationUtils

序列化工具

org.apache.commons.lang3.SerializationUtils,例如:

byte[] bytes = SerializationUtils.serialize(new Integer(1));
System.out.println(SerializationUtils.<Integer>deserialize(bytes)); //1

摘要(签名)工具类

org.apache.commons.codec.digest.DigestUtils
支持常用的md5/sha1/sha256等等单向散列摘要算法,使用:

DigestUtils.md5("abc"); //900150983cd24fb0d6963f7d28e17f72
DigestUtils.sha256("abc"); //ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad

IO操作

主要2个工具类:

  • org.apache.commons.io.IOUtils
  • org.apache.commons.io.FileUtils

IOUtils包括便捷的流操作,包括:优雅关闭流closeQuietly(),当然jdk7后使用try-with-resource自动关闭、复制、转化、读取、写入、常量(换号符、路径分割符等)等等。
FileUtils提供文件便捷操作,文件夹遍历、文件复制读写、转换等等。
例如:

FileUtils.readFileToString(new File("***"), Charsets.UTF_8)
IOUtils.toString(java.io.InputStream,java.nio.charset.Charse)
IOUtils.copy(final Reader input, final Writer output)
......

总之,你几乎以后都不需要自己实例化InputStream、Reader等jdk底层实现了。

集合操作

集合,可谓乱象丛生。各种同质化工具类以及guava,common包等提供的特殊集合。其实你要记住的只是常用操作而已,乱七八糟的东西私下研究研究、涨涨见识就行了。

1. 判空
org.apache.commons.collections.CollectionUtils.isEmpty()
org.apache.commons.collections.MapUtils.isEmpty()

2. 常量
java.util.Collections.EMPTY_LIST
java.util.Collections.EMPTY_MAP
java.util.Collections.EMPTY_SET
注意:正常情况,返回值应该是空集合而不是null。

3. 单元素转集合
java.util.Arrays.asList()返回的集合不支持add、remove操作
com.google.common.collect.Lists.newArrayList(E...)
com.google.common.collect.Sets.newHashSet(E...)

4. 基本类型数组转集合
com.google.common.primitives.Ints.asList(int... )
com.google.common.primitives.Longs.asList(long...)
......
不要用java.util.Arrays.asList,它会认为数组是一个对象。

5. 常用操作
java.util.Collections.sort(java.util.List<T>, java.util.Comparator<? super T>)//排序
org.apache.commons.collections.ListUtils.retainAll(Collection collection, Collection retain)//保留交集
org.apache.commons.collections.ListUtils.removeAll(Collection collection, Collection remove) //去掉相交
com.google.common.collect.Lists.partition() 或者
org.apache.commons.collections4.ListUtils.partition() //分割大集合,并发处理时很常用
com.google.common.collect.Lists.transform()
//懒式数据转换,正真get数据时才会转换。
java.util.Collections.max(java.util.Collection<? extends T>) //最大
java.util.Collections.min(java.util.Collection<? extends T>)//最小

先就写到这里,已经比较多了,以后用到在补充,如果哪位同学给点补充就再好不过了。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,271评论 5 476
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,275评论 2 380
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,151评论 0 336
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,550评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,553评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,559评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,924评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,580评论 0 257
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,826评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,578评论 2 320
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,661评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,363评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,940评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,926评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,156评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,872评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,391评论 2 342