-
ClassUtils.
getDefaultClassLoader : 获取默认类加载器
forName :初始化类
resolveClassName 和forName只有处理异常的差别
resolvePrimitiveClassName 处理int等原始几个类
isPresent 是否能初始化该类
getUserClass :获取class,处理了 CGLIB_CLASS_SEPARATOR 的类
isCacheSafe :
getShortName : 根据类的完整名获取短名称 java.lang.String --> String 处理了CGLIB_CLASS_SEPARATOR,不会处理开头字母
getShortNameAsProperty : 根据类得到名称,并且会转化成峰坨格式 ,小写字母开头
getClassFileName: 得到有.class文件名称
getPackageName : 获取类的包名,没有类名
getQualifiedName : 获取完整的类名 java.lang.Double[]
getQualifiedMethodName : 完整的方法名
getDescriptiveType : 类签名信息,一般返回完整类名 com.sun.proxy.$Proxy4 implementing com.bydbl.proxy.staticmodel.UserService
matchesTypeName:类是否匹配名称
getConstructorIfAvailable:返回构造器,没有合适的返回空
hasMethod : 是否有方法
getMethod : 查找方法,没找到会报错 IllegalStateException
getMethodIfAvailable :返回方法
getMethodCountForName : 递归返回指定方法名出现的总数,覆写
hasAtLeastOneMethodWithName:
getMostSpecificMethod :获取最适合的方法
getStaticMethod :
isPrimitiveWrapper : 是否是基础类型的包装类
isAssignable: 是否是签名,是否为其子类,处理了基础类型
isAssignableValue : 和isAssignable差不多,这个传入的是Object,参数不一样
convertResourcePathToClassName: / --> .
convertClassNameToResourcePath : . --> /
addResourcePathToPackagePath :
classPackageAsResourcePath: . -->
classNamesToString: 多个类名称的数组格式,以逗号分隔
toClassArray : 顾名思义
getAllInterfaces : 和getAllInterfacesForClass,getAllInterfacesAsSet 一样,就是多了个判空报错
getAllInterfacesForClassAsSet : 递归获取所有的接口
ClassUtils.createCompositeInterface(NaiveWaiter.class.getInterfaces(),ClassUtils.getDefaultClassLoader()) 创建接口的代理对象
determineCommonAncestor : 找到共同的祖先,继承关系
isCglibProxyClass: -->isCglibProxyClassName , 根据是否包含 CGLIB_CLASS_SEPARATOR 标识来判断
-
IdGenerator
其有3个实现类,SimpleIdGenerator ,JdkIdGenerator,AlternativeJdkIdGenerator
IdGenerator idGenerator = new SimpleIdGenerator();
for(int i =0 ;i<500;i++) {
System.out.println(idGenerator.generateId().toString());
}
输出:
00000000-0000-0000-0000-000000000001
00000000-0000-0000-0000-000000000002
00000000-0000-0000-0000-000000000003
00000000-0000-0000-0000-000000000004
System.out.println("------------jdk---------");
idGenerator = new JdkIdGenerator();
for(int i =0 ;i<5;i++) {
System.out.println(idGenerator.generateId().toString());
}
输出:
00d1ca6a-a5aa-40a0-8fef-2b138e3d3634
9466039f-bbfb-480b-bd06-0a50b4df1889
System.out.println("-----------alter---------");
idGenerator = new AlternativeJdkIdGenerator();
for(int i =0;i<5;i++) {
System.out.println(idGenerator.generateId().toString());
}
输出:
dd57c906-7ea5-015c-8a8a-14ed117e5710
c562d92d-f035-6f74-db40-b284148e4c7f
-
CollectionUtils:
arrayToList :参数是Object,传入数组,数组转List
mergeArrayIntoCollection : 数组合并到List,参数是Object,传入数组
mergePropertiesIntoMap : Properties 合并到Map
contains :是否包含,用equal比较
containsInstance : 是否包含,用== 比较,比较实例
containsAny : 第一个参考是否包含后一个参数中的任何一个
findFirstMatch :找到第一个参数包含第二个参数的第一个匹配对象
findValueOfType : 在一个集合中,包含各种类的集合,里面找到指定的类型
hasUniqueObject : 判断给定的集合是否为只包含一个值
findCommonElementType : 有任何一个不同类型就返回空,全部相同就返回对象类型,hasUniqueObject 是用== 比较,这个是用getClass比较
toArray : 转数组,可以是子类的集合转父类的数组
toIterator :
toMultiValueMap : Map> 转 MultiValueMap
unmodifiableMultiValueMap : MultiValueMap 变成线程安全的 MultiValueMap
-
ConcurrencyThrottleSupport:
控制并发,可见 ConcurrencyThrottleInterceptor
public ConcurrencyThrottleInterceptor() {
//设置并发数
setConcurrencyLimit(1);
}
@Override
public Object invoke(MethodInvocation methodInvocation) throws Throwable {
//进入前拿锁,数量加1
beforeAccess();
try {
return methodInvocation.proceed();
}
finally {
//退出后释放,数量减1
afterAccess();
}
}
-
ConcurrentReferenceHashMap
并发Hash Map,其键和值可以是弱引用或者软引用。
在JVM回收时会比硬引用更早回收
http://yuhuiblog6338999322098842.iteye.com/blog/2375746
-
DefaultPropertiesPersister
属性Properties的持久化,可以转成XML
Properties p = new Properties();
p.load(Files.newInputStream(Paths.get(fileName)));
DefaultPropertiesPersister pp = new DefaultPropertiesPersister();
pp.storeToXml(p,Files.newOutputStream(Paths.get(outXml)),"备注信息");
结果如下:
备注信息
"用户UUID"
8093
100
用户信息描述
dev: I'm living in ${home.province} ${home.city}.
ZheJiang
50
也可以读取已经生成的XML到properties
@Test
public void loadFromXml() throws IOException {
DefaultPropertiesPersister pp = new DefaultPropertiesPersister();
Properties p = new Properties();
pp.loadFromXml(p,Files.newInputStream(Paths.get(outXml)));
System.out.println(p);
}
-
DigestUtils 数字签名 MD5
@Test
public void md5Digest() throws UnsupportedEncodingException {
String value = "123";
System.out.println(new String(DigestUtils.md5Digest(value.getBytes("utf-8"))));// ,�b�Y�[�K��-#Kp
System.out.println(DigestUtils.md5DigestAsHex(value.getBytes("utf-8")));//202cb962ac59075b964b07152d234b70
}
-
FileCopyUtils
复制文件的方法,各种复制...
和 commons-io的IOUtil差不多,但是这个只有复制功能,commons-io的IOUtils和FileUtils功能
- FileSystemUtils :复制或删除文件(文件夹)操作,递归
- LinkedCaseInsensitiveMap : 里面存的是一些大小写的key,但是get 和remove的时候可以不区分大小写
- LinkedMultiValueMap : 线程不安全,实现了MultiValueMap数据结构,Map
> - MethodInvoker:方法调用,静态方法也可以反射调用
@Test
public void invoker() throws NoSuchMethodException, ClassNotFoundException, InvocationTargetException, IllegalAccessException {
MethodInvoker methodInvoker = new MethodInvoker();
methodInvoker.setTargetClass(User.class);
methodInvoker.setStaticMethod("com.bydbl.proxy.util.User.hello");
methodInvoker.prepare();
Object o = methodInvoker.invoke();
}
package com.bydbl.proxy.util;
public class User {
public void hi() {
System.out.println("hi...");
}
public static void hello() {
System.out.println("hello...");
}
}
-
MimeType :处理HTTP的Mime类型
MimeTypeUtils
public static final MimeType X_JAVA_OBJECT = MimeType.valueOf("application/x-java-object")
private static final MimeType[] DEFAULT_SMILE_MIME_TYPES = new MimeType[] {
new MimeType("application", "x-jackson-smile", StandardCharsets.UTF_8),
new MimeType("application", "*+x-jackson-smile", StandardCharsets.UTF_8)};
-
NumberUtils
convertNumberToTargetClass : 将数字类型转换成目标类
parseNumber:将字符串转换成目标类型的数字,重载了两个方法,可以指定 NumberFormat
@Test
public void convertNumberToTargetClass() {
BigDecimal b = NumberUtils.convertNumberToTargetClass(11111111111111111111111D, BigDecimal.class);
System.out.println(b);
BigDecimal decimal = NumberUtils.parseNumber("1111111111111111111111111", BigDecimal.class);
System.out.println(decimal);
decimal = NumberUtils.parseNumber("999,999,999", BigDecimal.class, NumberFormat.getInstance());
System.out.println(decimal);
}
-
PathMatcher
AntPathMatcher
extractUriTemplateVariables --> 转换成我们需要的Map
String path = "/hotels/{hotel}";
String pattern = "/hotels/1";
PathMatcher pm = new AntPathMatcher();
Map map = pm.extractUriTemplateVariables(path,pattern );
System.out.println(map.toString());//输出:{hotel=1}
-
PatternMatchUtils
simpleMatch
-
PropertyPlaceholderHelper
将给定的模板替换掉,一般处理我们的属性文件的占位符
Properties p = new Properties();
p.put("name","aaaaa");
p.put("age","23");
p.put("address","china");
PropertyPlaceholderHelper helper = new PropertyPlaceholderHelper("${","}");
System.out.println(helper.replacePlaceholders("${name}", p)); //aaaaa
System.out.println(helper.replacePlaceholders("aaa ${name} bbb=${age} ccc = ${address}",p)); //aaa aaaaa bbb=23 ccc = china
helper = new PropertyPlaceholderHelper("{","}");
System.out.println(helper.replacePlaceholders("${name}", p));//$aaaaa
-
ReflectionUtils
有关反射的优先从此类中找方法,很多实用的,举一个小例子
findField :查找属性
@Test
public void setField() {
User user = new User();
user.setName("aaa");
user.setAge(18);
user.setBirth(new Date());
Field field = ReflectionUtils.findField(User.class, "birth");
ReflectionUtils.makeAccessible(field);
Date birth = (Date)ReflectionUtils.getField(field, user);
System.out.println(birth);
}
-
ResourceUtils
处理了classpath:file,war,jar,file,zip等路径的工具类
@Test
public void getFile() throws FileNotFoundException {
String location = "classpath:application.properties";
//输出:D:\mytest\proxy\target\classes\application.properties
System.out.println(ResourceUtils.getFile(location).getPath());
}
-
InstanceComparator 用法实例
/**
* FileName :InstanceComparatorTest
* Author :zengzhijun
* Date : 2018/5/21 10:58
* Description:
*/
package org.springframework.util.comparator;
import org.aspectj.lang.annotation.*;
import org.junit.Test;
import org.springframework.core.convert.converter.ConvertingComparator;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.util.Arrays;
import java.util.Comparator;
import java.util.List;
/**
*
* 下例先按 输入到 InstanceComparator 的先后顺序排队再根据方法名称排序
* 因为要获取方法的注解,所以要用 ConvertingComparator 先转换到对应的注解
* 参考 ReflectiveAspectJAdvisorFactory 内的方法
*
* @author : zengzhijun
* @date : 2018/5/21 11:25
**/
public class InstanceComparatorTest {
private static final Comparator METHOD_COMPARATOR;
static {
Comparator adviceKindComparator = new ConvertingComparator<>(
new InstanceComparator<>(
Around.class, Before.class, After.class, AfterReturning.class, AfterThrowing.class),
method -> {
Annotation[] annotations = method.getDeclaredAnnotations();
return annotations[0];
});
Comparator methodNameComparator = new ConvertingComparator<>(Method::getName);
METHOD_COMPARATOR = adviceKindComparator.thenComparing(methodNameComparator);
}
@Test
public void comparate() {
Method[] methods = ComparatorService.class.getDeclaredMethods();
List methodList = Arrays.asList(methods);
methodList.sort(METHOD_COMPARATOR);
methodList.stream().map(Method::getName).forEach(System.out::println);
}
class ComparatorService{
@Around("around")
public void around() {
}
@Around("bround")
public void bround() {
}
@AfterThrowing
public void afterThrowing() {
}
@AfterReturning
public void afterReturning() {
}
@Before("before")
public void before() {
}
}
}
-
AnnotationBeanUtils.copyPropertiesToBean
/**
* FileName :AnnotationBeanUtilsTest
* Author :zengzhijun
* Date : 2018/5/21 14:35
* Description:
*/
package org.springframework.beans.annotation;
import org.aspectj.lang.annotation.Before;
import org.junit.Test;
import org.springframework.core.annotation.AnnotationUtils;
/**
*
* AnnotationBeanUtils : 将一个注解的信息对应到一个实体类的属性上
* 本例展示将某一个方法上的注解信息转换到一个实体类上
* 另: AnnotationBeanUtils 支持传入一个 StringValueResolver 和 excludedProperties 两个参数
* 这样可以做更多处理
*
* @author : zengzhijun
* @date : 2018/5/21 14:45
**/
public class AnnotationBeanUtilsTest {
@Test
public void copyPropertiesToBean() throws NoSuchMethodException {
ServiceA serviceA = new ServiceA();
Before annotation = AnnotationUtils.findAnnotation(ServiceA.class.getMethod("before"), Before.class);
BeforeAttribute ba = new BeforeAttribute();
AnnotationBeanUtils.copyPropertiesToBean(annotation,ba);
System.out.println(ba);
}
class ServiceA {
@Before(value = "aaa",argNames = "args")
public void before() {
}
}
class ServiceB {
@Before(value = "bbb",argNames = "argsBBB")
public void before() {
}
}
class BeforeAttribute{
private String value;
private String argNames;
public String getValue() {
return value;
}
public void setValue(String value) {
this.value = value;
}
public String getArgNames() {
return argNames;
}
public void setArgNames(String argNames) {
this.argNames = argNames;
}
@Override
public String toString() {
return "BeforeAttribute{" +
"value='" + value + '\'' +
", args='" + argNames + '\'' +
'}';
}
}
}
-
BeanUtils
/*
* FileName :BeanUtilsTest
* Author :zengzhijun
* Date : 2018/5/21 14:54
* Description:
*/
package org.springframework.beans;
import org.junit.Test;
import org.springframework.util.ClassUtils;
import org.springframework.util.ReflectionUtils;
import java.beans.PropertyDescriptor;
import java.lang.reflect.Method;
import java.util.Date;
public class BeanUtilsTest {
/**
*初始化类,Spring5 考虑到了 Kotlin
**/
@Test
public void instantiateClass() throws NoSuchMethodException {
PropertyValue propertyValue = BeanUtils.instantiateClass(PropertyValue.class.getConstructor(String.class, Object.class),"name","aaa");
propertyValue.setAttribute("attr1","value1");
System.out.println(propertyValue);
}
@Test
public void instantiateClass1() throws ClassNotFoundException {
String className = Person.class.getCanonicalName();
Class> clazz = ClassUtils.forName(className, ClassUtils.getDefaultClassLoader());
Person person = BeanUtils.instantiateClass(clazz, Person.class);
person.setAge(18);
person.setName("name");
System.out.println(person);
}
@Test
public void findMethod() {
//findMethod 不会递归查找父类
Method sing = BeanUtils.findMethod(SuperMan.class, "fly");
//会递归查找方法
Method sing1 = BeanUtils.findDeclaredMethod(SuperMan.class, "sing");
System.out.println(sing);
System.out.println(sing1);
//找到参数最小的同名方法,相当实用
Method fly = BeanUtils.findDeclaredMethodWithMinimalParameters(SuperMan.class, "fly");
SuperMan superMan = new SuperMan();
ReflectionUtils.invokeMethod(fly, superMan);
}
@Test
public void resolveSignature() {
//methodName[([arg_list])
//找到一个参数为空的方法
Method exactlyFly = BeanUtils.resolveSignature("fly()", SuperMan.class);
System.out.println(exactlyFly);
//找到一个方法名为play的,参数最小的会返回
Method play = BeanUtils.resolveSignature("play", SuperMan.class);
System.out.println(play);
//找到一个参数名为指定类型(完整的类型名称)的指定方法
Method fly1 = BeanUtils.resolveSignature("fly(java.lang.String)", SuperMan.class);
System.out.println(fly1);
Method fly2 = BeanUtils.resolveSignature("fly(java.lang.String,java.lang.String)", SuperMan.class);
System.out.println(fly2);
}
@Test
public void getPropertyDescriptors() {
//获取类的 getter 和 setter 方法,神器啊.
PropertyDescriptor[] descriptors = BeanUtils.getPropertyDescriptors(SuperMan.class);
for (PropertyDescriptor descriptor : descriptors) {
Method readMethod = descriptor.getReadMethod();
Method writeMethod = descriptor.getWriteMethod();
if (readMethod == null) {
System.out.println("ignore readMethod : " + descriptor.getName());
continue;
}
if (writeMethod == null) {
System.out.println("ignore writeMethod : " + descriptor.getName());
continue;
}
System.out.println("readMethod Name: " + readMethod.getName());
System.out.println("writeMethod Name: " + writeMethod.getName());
}
}
@Test
public void findPropertyType() {
//获取类中的属性的类型值
Class> age = BeanUtils.findPropertyType("age", Person.class);
System.out.println(age);
}
@Test
public void copyProperties() {
//拷贝属性,最常用的方法
SuperMan superMan = new SuperMan();
superMan.setBirthday(new Date());
superMan.setAge(18);
superMan.setName("superman");
SuperMan cloneMan = new SuperMan();
//匹配上的属性全部复制
BeanUtils.copyProperties(superMan,cloneMan);
System.out.println(cloneMan);
cloneMan = new SuperMan();
//忽略 age 属性
BeanUtils.copyProperties(superMan,cloneMan,"age");
System.out.println(cloneMan);
cloneMan = new SuperMan();
//只复制 Person 里面的属性
BeanUtils.copyProperties(superMan,cloneMan,Person.class);
System.out.println(cloneMan);
}
}
-
PropertyAccessorUtils
@Test
public void getPropertyName() {
//输出:person
System.out.println(PropertyAccessorUtils.getPropertyName("person[1]"));
//是否是数组或者嵌套的属性格式
System.out.println(PropertyAccessorUtils.isNestedOrIndexedProperty("person[1]"));
System.out.println(PropertyAccessorUtils.isNestedOrIndexedProperty("person.age"));
System.out.println(PropertyAccessorUtils.canonicalPropertyName("Asd_Wer"));
System.out.println(PropertyAccessorUtils.canonicalPropertyName("asd_wer"));
System.out.println(PropertyAccessorUtils.canonicalPropertyName("asdWer"));
//输出:map[key]
System.out.println(PropertyAccessorUtils.canonicalPropertyName("map[\"key\"]"));
//true
//true
//Asd_Wer
//asd_wer
//asdWer
//map[key]
}