org.nutz.lang.born.Borns Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of nutz Show documentation
Show all versions of nutz Show documentation
Nutz, which is a collections of lightweight frameworks, each of them can be used independently
package org.nutz.lang.born;
import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
import org.nutz.castor.Castors;
import org.nutz.lang.Lang;
import org.nutz.lang.MatchType;
import org.nutz.lang.Mirror;
/**
* 关于创建对象的一些帮助方法
*
* @author zozoh([email protected])
*/
public abstract class Borns {
/**
* 根据参数类型数组获取一个对象的构建信息
*
* @param
* 对象类型信息
* @param type
* 对象类型
* @param argTypes
* 构造参数类型数组
* @return 构建信息对象
*/
public static BornContext evalByArgTypes(Class type, Class>... argTypes) {
BornContext re;
if (argTypes.length == 0) {
re = evalWithoutArgs(type);
} else {
re = evalWithArgTypes(true, type, argTypes, null);
}
return re;
}
/**
* 根据参数类型数组获取一个对象的构建信息
*
* @param
* 对象类型信息
* @param type
* 对象类型
* @param args
* 构造参数数组
* @return 构建信息对象
*/
public static BornContext eval(Class type, Object... args) {
BornContext re;
if (args.length == 0) {
re = evalWithoutArgs(type);
} else {
re = evalWithArgs(type, args);
}
return re;
}
/**
* 根据一个调用参数数组,获取一个对象的构建信息
*
* @param
* 对象类型信息
* @param type
* 对象类型
* @param args
* 参考构建参数
* @return 构建信息对象
*/
private static BornContext evalWithArgs(Class type, Object[] args) {
// 准备变参数组
Object dynaArg = Mirror.evalArgToSameTypeRealArray(args);
// 准备好参数类型
Class>[] argTypes = Mirror.evalToTypes(args);
BornContext re = evalWithArgTypes(false, type, argTypes, dynaArg);
if (null == re)
return null;
if (MatchType.LACK == re.getMatchType()) {
re.setArgs(Lang.arrayLast(args, re.getLackArg()));
} else {
re.setArgs(args);
}
switch (re.getMatchType()) {
case LACK:
re.setArgs(Lang.arrayLast(args, re.getLackArg()));
break;
case NEED_CAST:
re.setArgs(Lang.array2ObjectArray(args, re.getCastType()));
break;
default:
re.setArgs(args);
}
return re;
}
/**
* 根据一个调用参数类型数组,获取一个对象的构建信息
*
* @param
* 对象类型信息
* @param accurate
* 是否需要精确匹配
* @param type
* 对象类型
* @param argTypes
* 参考参数类型数组
* @param dynaAry
* 参考参数类型信息是否是一个变参数组
* @return 构建信息对象
*/
@SuppressWarnings({"rawtypes", "unchecked"})
private static BornContext evalWithArgTypes( boolean accurate,
Class type,
Class>[] argTypes,
Object dynaArg) {
// 准备好返回对象
BornContext re = new BornContext();
// 先看看有没对应的构造函数
Mirror mirror = Mirror.me(type);
for (Constructor> cc : type.getConstructors()) {
Class>[] pts = cc.getParameterTypes();
MatchType mt = Mirror.matchParamTypes(pts, argTypes);
re.setMatchType(mt);
// 正好合适
if (MatchType.YES == mt) {
return re.setBorning(new ConstructorBorning(cc));
}
// 差一个参数,说明这个构造函数有变参数组
else if (MatchType.LACK == mt) {
re.setLackArg(Mirror.blankArrayArg(pts));
return re.setBorning(new ConstructorBorning(cc));
}
// 看看整个输入的参数是不是变参
else if (null != dynaArg && pts.length == 1 && pts[0] == dynaArg.getClass()) {
return re.setBorning(new DynamicConstructorBorning(cc));
}
}
// 看看有没有对应静态工厂函数
Method[] sms = mirror.getStaticMethods();
for (Method m : sms) {
Class>[] pts = m.getParameterTypes();
MatchType mt = Mirror.matchParamTypes(pts, argTypes);
re.setMatchType(mt);
if (MatchType.YES == mt) {
return re.setBorning(new MethodBorning(m));
} else if (MatchType.LACK == mt) {
re.setLackArg(Mirror.blankArrayArg(pts));
return re.setBorning(new MethodBorning(m));
} else if (null != dynaArg && pts.length == 1) {
if (pts[0] == dynaArg.getClass()) {
return re.setBorning(new DynaMethodBorning(m));
}
}
}
// 如果不是要精确查找的话
if (!accurate) {
// 找到一个长度合适的构造函数,准备转换
try {
for (Constructor> cc : type.getConstructors()) {
Class>[] pts = cc.getParameterTypes();
if (canBeCasted(argTypes, pts)) {
re.setMatchType(MatchType.NEED_CAST);
re.setCastType(pts);
return re.setBorning(new ConstructorCastingBorning(cc));
}
}
}
catch (RuntimeException e) {}
// 有没有变参的静态构造方法
try {
for (Method m : sms) {
Class>[] pts = m.getParameterTypes();
if (canBeCasted(argTypes, pts)) {
re.setMatchType(MatchType.NEED_CAST);
re.setCastType(pts);
return re.setBorning(new MethodCastingBorning(m));
}
}
}
catch (Exception e) {}
}
return null;
}
private static boolean canBeCasted(Class>[] argTypes, Class>[] pts) {
if (pts.length != argTypes.length)
return false;
for (int i = 0; i < pts.length; i++) {
if (!Castors.me().canCast(argTypes[i], pts[i]))
return false;
}
return true;
}
/**
* 为一个给定类,寻找一个不需要参数的构造方法
*
* @param
* 类
* @param type
* 类实例
* @return 构造信息
*/
@SuppressWarnings({"rawtypes", "unchecked"})
private static BornContext evalWithoutArgs(Class type) {
// 准备好返回对象
BornContext re = new BornContext();
Mirror mirror = Mirror.me(type);
// 先看看有没有默认构造函数
try {
re.setBorning(new EmptyArgsConstructorBorning(type.getConstructor()));
return re.setArgs(new Object[0]);
}
// 如果没有默认构造函数 ...
catch (Exception e) {
// 看看有没有默认静态工厂函数
Method[] stMethods = mirror.getStaticMethods();
for (Method m : stMethods) {
if (m.getReturnType() == type && m.getParameterTypes().length == 0) {
return re.setBorning(new EmptyArgsMethodBorning(m)).setArgs(new Object[0]);
}
}
// 看看有没有带一个动态参数的构造函数
for (Constructor> cons : type.getConstructors()) {
Class>[] pts = cons.getParameterTypes();
if (pts.length == 1 && pts[0].isArray()) {
Object[] args = new Object[1];
args[0] = Mirror.blankArrayArg(pts);
return re.setBorning(new ConstructorBorning(cons)).setArgs(args);
}
}
// 看看有没有带一个动态参数的静态工厂函数
for (Method m : stMethods) {
Class>[] pts = m.getParameterTypes();
if (m.getReturnType() == type
&& m.getParameterTypes().length == 1
&& pts[0].isArray()) {
Object[] args = new Object[1];
args[0] = Mirror.blankArrayArg(pts);
return re.setBorning(new MethodBorning(m)).setArgs(args);
}
}
}
return null;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy