Java - HuTool 使用 ReflectUtil、ClassUtil等工具类(二)
本篇主要介绍 HuTool工具, 其是 java工具类,对于一些静态方法进行封装,虽然很小,但很全,里面拥有平时我们会用到的工具类,就无需我们自己去封装了
以前我还自己去封装,emmm,我真的太傻了~,但是自己封装也不是不好,但是学会站在巨人的肩膀上,也非常有必要
下面就简单介绍一下 HuTool工具 与 其简单使用
相关链接:
HuTool 工具介绍
Hutool 是一个小而全的 Java工具类库,通过静态方法封装,降低相关API的学习成本,提高工作效率,涵盖了Java开发开发中的方方面面
使用 Hutool 可节省开发人员对项目中公用类和公用工具方法的封装时间,使开发专注于业务,同时可以最大限度的避免封装不完善带来的bug
该工具类主要对 文件、流、加密解密、转码、正则、线程、XML等 JDK方法进行封装,组成各种Util工具类,同时提供以下组件:
模块 | 介绍 |
---|---|
hutool-aop | JDK动态代理封装,提供非IOC下的切面支持 |
hutool-bloomFilter | 布隆过滤,提供一些Hash算法的布隆过滤 |
hutool-cache | 简单缓存实现 |
hutool-core | 核心,包括Bean操作、日期、各种Util等 |
hutool-cron | 定时任务模块,提供类Crontab表达式的定时任务 |
hutool-crypto | 加密解密模块,提供对称、非对称和摘要算法封装 |
hutool-db | JDBC封装后的数据操作,基于ActiveRecord思想 |
hutool-dfa | 基于DFA模型的多关键字查找 |
hutool-extra | 扩展模块,对第三方封装(模板引擎、邮件、Servlet、二维码、Emoji、FTP、分词等) |
hutool-http | 基于HttpUrlConnection的Http客户端封装 |
hutool-log | 自动识别日志实现的日志门面 |
hutool-script | 脚本执行封装,例如Javascript |
hutool-setting | 功能更强大的Setting配置文件和Properties封装 |
hutool-system | 系统参数调用封装(JVM信息等) |
hutool-json | JSON实现 |
hutool-captcha | 图片验证码实现 |
hutool-poi | 针对POI中Excel和Word的封装 |
hutool-socket | 基于Java的NIO和AIO的Socket封装 |
hutool-jwt | JSON Web Token (JWT)封装实现 |
可根据需求对每个模块 单独引入,也可以通过引入hutool-all
方式引入所有模块
HuTool工具使用
HuTool 工具 的API文档与官网把其能干的事情说的很详细了,下面主要是列举出工具类能干什么,方法有哪些,顺带可以提一下原理是啥,会用并且懂原理是最好的学习方式
1、导包
使用首先导包,在项目的 pom.xml 中加入以下内容:【Hutool 5.x 支持 JDK8+,JDK7 使用 Hutool 4.x版本】Maven中央库
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.8.0</version>
</dependency>
若使用jar包,可去该 下载jar 网址下载hutool-all-X.X.X.jar
即可
2、使用
本小节主要围绕着 hutool 提供的工具类/功能为小点进行说明,一部分的说明来自官方文档,一部分来自看的源码,这里的源码版本为对应5.8.0(若与您看的源码有所不同,请查看版本是否相同)
本篇博客主要对 对象、类、类加载、类的类型判断、反射 等相关功能进行了封装( API 文档 )
- ClassLoaderUtil:ClassLoader 工具类
- ClassUtil:类工具类
- ObjectUtil:对象工具类
- TypeUtil:针对Type的工具类封装
- ReflectUtil:反射工具类
- ReferenceUtil: 引用工具类
- JAXBUtil:JAXB(Java Architecture for XML Binding),根据XML Schema产生Java对象
- SerializeUtil:类序列化工具类
- ModifierUtil:类修饰符工具类
2.1 ClassLoaderUtil:ClassLoader 工具类( API 文档 )
ClassLoader 工具类主要完成对类的加载,具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 原理 |
---|---|---|
getContextClassLoader | 获取当前线程的 ClassLoader | Thread.currentThread().getContextClassLoader() |
getSystemClassLoader | 获取系统 ClassLoader | ClassLoader.getSystemClassLoader() |
getClassLoader | 获取 ClassLoader,获取顺序如下: 获取当前线程的ContextClassLoader 获取当前类对应的ClassLoader 获取系统ClassLoader | |
loadClass | 通过传入类的字符串加载类: 使用加载器ClassLoader(默认采用getClassLoader获取到的)加载,并初始化类(默认进行初始化,可指定是否初始化) | Class.forName() / Array.newInstance |
loadPrimitiveClass | 通过传入类的字符串加载原始类型的类 包括原始类型、原始类型数组和void | |
getJarClassLoader | 创建新的 JarClassLoader,并使用此Classloader加载目录下的class文件和jar文件 | |
isPresent | 指定类是否被提供,通过loadClass 来加载,若加载到即为提供 |
2.2 ClassUtil:类相关工具类( API 文档 )
其里面主要针对类的一些功能进行实现
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
getClasses getClass | 安全的获取对象类型 获得对象数组的类数组 | T / Object | obj.getClass() |
getClassName getShortClassName | 获取类名,类名并不包含“.class”这个扩展名,可选择返回不带包名的类名 获取完整类名的短格式,如 cn.hutool.core.util.StrUtil -》c.h.c.u.StrUtil | Object | clazz.getEnclosingClass |
getEnclosingClass isTopLevelClass | 是否为顶层类,即定义在包中的类,而非定义在类中的内部类 返回定义此类或匿名类所在的类,如果类本身是在包中定义的,返回 null | Class | |
scanPackageByAnnotation scanPackageBySuper scanPackage | 扫描指定包路径下所有包含指定注解的类 扫描指定包路径下所有指定类或接口的子类或实现类 扫描该包路径下所有class文件 | clazz.isAnnotationPresent | |
getPublicMethodNames getPublicMethods | 获得指定类中的Public方法名 获得本类及其父类所有Public方法 / 过滤后的Public方法列表 | Class | clazz.getMethods |
getDeclaredMethodNames getDeclaredMethods | 获得声明的所有方法,包括本类及其父类和接口的所有方法和Object类的方法名称 获得声明的所有方法,包括本类及其父类和接口的所有方法和Object类的方法 | Class | clazz.getDeclaredMethods |
getClassPathResources getClassPaths getClassPathURL getJavaClassPaths | 获得ClassPath,默认不解码路径中的特殊字符(例如空格和中文) 获得ClassPath,默认不解码路径中的特殊字符(例如空格和中文) 获得ClassPath URL 获得Java ClassPath路径 | Class | clazz.getResource |
getResources getResourceURL getResourceUrl | 获取指定路径下的资源列表 获得资源相对路径对应的URL 获得资源相对路径对应的URL | clazz.getResource | |
getContextClassLoader getClassLoader loadClass | 获取当前线程的ClassLoader 获取 ClassLoader 加载类并初始化(默认进行初始化,可设置不进行初始化) | Thread.currentThread().getContextClassLoader() Class.forName() / Array.newInstance | |
invoke | 执行方法 | method.invoke | |
isSimpleValueType isAssignable isPrimitiveWrapper isSimpleTypeOrArray isBasicType isPublic isNotPublic isAbstract isNormalClass isEnum | 是否为简单值类型 检查目标类是否可以从原类转化 类是否为包装类型 是否简单值类型或简单值类型的数组 类是否为简单类型 指定类是否为Public 指定类是否为非public 指定类是否为抽象类 指定类是否为标准的类 指定类是否为枚举类型 | Class | clazz.isXXX |
isStatic setAccessible | 方法是否为静态方法 方法是否设置为可访问 | Method | |
getTypeArgument getPackage getPackagePath getDefaultValue getDefaultValues getPrimitiveDefaultValue getLocation、getLocationPath isJdkClass | 获得给定类的第一个泛型参数 获得给定类所在包的名称 获得给定类所在包的路径 获取指定类型分的默认值(原始类型为0,其他为null) 获取指定类型分的默认值(数组) 获取指定原始类型分的默认值 获取class类路径URL / String path 是否为JDK中定义的类或接口(以java.、javax.开头的包名 或者 ClassLoader为null的类/接口为JDK中定义的类/接口) | Class |
2.3 ObjectUtil:对象相关工具类( API 文档 )
其里面主要针对对象Object的一些功能进行实现
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
equals、equal notEqual | 比较两个对象是否相等 比较两个对象是否不相等 | Object | Objects.equals |
isNull isNotNull isEmpty isNotEmpty isAllEmpty、isAllNotEmpty | 检查对象是否为null 检查对象是否不为null 判断指定对象是否为空 判断指定对象是否不为空 所有对象是否全都为空 / 不为空 | Object | Objects.equals 长度 / size 是否为0 |
defaultIfNull defaultIfEmpty defaultIfBlank | 如果给定对象为 null 返回默认值 如果给定对象为 null 或者 “” 返回默认值 | T | |
clone cloneIfPossible cloneByStream | 克隆对象,如果对象实现Cloneable接口,调用其clone方法,如果实现Serializable接口,执行深度克隆,否则返回 null 返回克隆后的对象,如果克隆失败,返回原对象 序列化后拷贝流的方式克隆(必须实现Serializable接口) | T | 反射执行 clone 方法 ValidateObjectInputStream.readObject() |
length contains hasNull hasEmpty emptyCount | 计算对象长度 对象中是否包含指定元素 多个对象中是否存在 null 对象 多个对象是否存在 null 或 空对象 多个对象存在多少个 null 或 空对象 | Object | |
serialize deserialize | 序列化 与 反序列化(必须实现Serializable接口) | T / byte[] | io操作 |
isBasicType isValidIfNumber | 对象是否为基本类型,包括包装类型和非包装类型 对象是否为有效的数字 | Object | clazz.isPrimitive() |
toString | 将Object转为String | Object | obj.toString() |
compare | 安全的对象比较 | T | compareTo |
getTypeArgument | 获得给定类的第一个泛型参数 | Object |
2.4 TypeUtil:类的类型相关工具类( API 文档 )
其里面主要针对 Type 的一些功能进行封装
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
getClass | 获得原始类 | Type / Field | |
getType getFieldType | 获取字段Field对应的Type类型 根据字段名称获得字段的泛型类型 | Object | |
getFirstParamType getFirstParamClass getParamType getParamClass getParamTypes getParamClasses getReturnType getReturnClass | 获取方法的第一个参数类型 获取方法的第一个参数类 获取方法指定位置的参数类型 获取方法指定位置的参数类 获取方法的参数类型列表 获取方法的参数类列表 获取方法的返回值类型 获取方法的返回值类 | Method | method.getxxxx() |
toParameterizedType | 将 Type 转换为ParameterizedType,一般用于获取泛型参数具体的参数类型 | Type | |
getTypeArgument | 获得给定类的第一个泛型参数 | Type | |
getActualType getActualTypes | 获得泛型字段对应的泛型实际类型,如果此变量没有对应的实际类型,返回null 获得泛型变量对应的泛型实际类型数组 | Type | |
getTypeMap | 获取泛型变量和泛型实际类型的对应关系Map | Class | |
hasTypeVariable | 指定泛型数组中是否含有泛型变量 | Type… | obj.toString() |
isUnknown | 指定类型是否是未知类型(type为null或者 TypeVariable 都视为未知类型) | Type |
2.5 ReflectUtil:反射相关工具类( API 文档 )
其里面主要针对 反射的一些功能进行封装
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
getConstructor、getConstructors getConstructorsDirectly | 查找类中的指定参数的构造方法,如果找到构造方法,会自动设置可访问为true 获得一个类中所有构造列表,直接反射获取,无缓存 | Class | clazz.getDeclaredConstructors() |
hasField getFieldName getField getFieldMap getFields getFieldsDirectly getFieldValue getFieldsValue getStaticFieldValue setFieldValue | 找指定类中是否包含指定名称对应的字段,包括所有字段(包括非public字段),也包括父类和Object类的字段 获取字段名 查找指定类中的指定name的字段(包括非public字段),也包括父类和Object类的字段, 字段不存在则返回 null 获取指定类中字段名和字段对应的有序Map,包括其父类中的字段 获得一个类中所有字段列表,包括其父类中的字段 获得一个类中所有字段列表,直接反射获取,无缓存 获取字段值 获取所有字段的值 获取静态字段值 设置字段值 | Class | clazz.getDeclaredFields(); |
getPublicMethodNames getPublicMethods getPublicMethod getMethodOfObj getMethodIgnoreCase getMethod getMethodByName getMethodByNameIgnoreCase getMethodNames getMethods getMethodsDirectly | 获得指定类本类及其父类中的Public方法名(去除重载的方法) 获得本类及其父类所有Public方法 根据方法名称查找指定Public方法 如果找不到对应的方法或方法不为public的则返回 根据方法名称查找指定对象中的所有方法(包括非public方法),也包括父对象和Object类的方法型 根据方法名称查找指定方法(忽略大小写),如果找不到对应的方法则返回null 根据方法名称查找指定方法 如果找不到对应的方法则返回null 根据方法名称查找指定方法(忽略大小写),如果找不到对应的方法则返回null(忽略方法的参数) 获得指定类中的Public方法名 获得指定类过滤后的Public方法列表 获得一个类中所有方法列表,直接反射获取,无缓存 | Class | clazz.getMethods() |
isOuterClassField | 字段是否为父类引用字段(字段所在类是对象子类时(对象中定义的非static的class),会自动生成一个以"this$0"为名称的字段,指向父类对象) | Type | equals |
isEqualsMethod isHashCodeMethod isToStringMethod isEmptyParam isGetterOrSetterIgnoreCase isGetterOrSetter | 方法是否为equals方法 、hashCode 方法 、 toString 方法、空参方法、get/set方法 | Method | equals |
newInstance newInstance newInstanceIfPossible | 实例化对象 | String Class | Class.forName Constructor.newInstance(); |
invokeStatic invokeWithCheck invoke invoke | 执行方法 | Method | method.invoke |
setAccessible | 设置方法为可访问(私有方法可以被外部调用) | Class、Method、Field | AccessibleObject.setAccessible(true) |
2.6 ReferenceUtil: 引用相关工具类( API 文档 )
其里面主要针对 类引用 的一些功能进行封装,一般引用会分为三种:
- SoftReference:软引用,在GC报告内存不足时会被GC回收
- WeakReference: 弱引用,在GC时发现弱引用会回收其对象
- PhantomReference:虚引用,在GC时发现虚引用对象,会将加入队列,此时对象未被真正回收,要等到队列被真正处理后才会被回收
其中只有一个 create 方法来创建引用
2.7 SerializeUtil:类序列化工具类( API 文档 )
其里面主要针对 类序列化 的一些功能进行封装
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
clone | 序列化后拷贝流的方式克隆 | Type / Field | deserialize(serialize(obj)) |
serialize | 序列化 对象必须实现Serializable接口 | T | io操作 |
deserialize | 反序列化 对象必须实现Serializable接口 | byte[] | io操作 |
2.8 ModifierUtil:类修饰符相关工具类( API 文档 )
其里面主要针对 类修饰符 的一些功能进行封装
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
isPublic isStatic isAbstract isSynthetic | 是否是Public方法 / 类/ 字段 是否是Static方法 / 类/ 字段 方法是否抽象方法 方法是否是合成方法(由java编译器生成的) | Class / Type / Method Class / Type / Method Method Method | deserialize(serialize(obj)) |
hasModifier | 是否同时存在一个或多个修饰符 | Constructor / Class / Method / Field | method.getModifiers() |
2.9 JAXBUtil:XML Java对象互转工具类( API 文档 )
其里面主要针对 XML Schema产生Java对象 的一些功能进行封装
具体传参与返回值可查看接口文档,这里仅总览出可完成的功能方法
方法 | 功能 | 支持类型 | 原理 |
---|---|---|---|
xmlToBean | XML文件转Bean | Reader 转 Class | XMLReader.parse |
beanToXml | JavaBean转换成xml | Object | 序列化实现 |
总结
我觉得这一类别算是比较常用的,尤其是反射、类的类型判断等相关工具类,例如获取泛型getTypeArgument等相关功能若自己封装,可能考虑的不全,若需反射执行方法传参可能会出现问题