add DefaultCloneable

This commit is contained in:
looly 2021-11-16 16:12:23 +08:00
parent 9cac854b3c
commit ff70f92e9c
4 changed files with 42 additions and 81 deletions

View File

@ -16,6 +16,7 @@
* 【core 】 IdCardUtil.isValidCard不再自动trimissue#I4I04O@Gitee
* 【core 】 改进TextFinder支持限制结束位置及反向查找模式
* 【core 】 Opt增加部分方法pr#459@Gitee
* 【core 】 增加DefaultCloneablepr#459@Gitee
*
### 🐞Bug修复
* 【core 】 修复FileResource构造fileName参数无效问题issue#1942@Github

View File

@ -1,29 +0,0 @@
package cn.hutool.core.clone;
import java.lang.reflect.Method;
public interface DefaultClone extends java.lang.Cloneable {
/**
* 浅拷贝
* 功能与 {@link CloneSupport#clone()} 类似, 是一种接口版的实现
* 一个类一般只能继承一个类,但是可以实现多个接口,所以该接口会有一定程度的灵活性
*
* @param <T> T
* @return obj
*/
@SuppressWarnings({"unchecked"})
default <T> T clone0() {
try {
final Class<Object> objectClass = Object.class;
final Method clone = objectClass.getDeclaredMethod("clone");
clone.setAccessible(true);
return (T) clone.invoke(this);
} catch (Exception e) {
throw new CloneRuntimeException(e);
}
}
}

View File

@ -0,0 +1,28 @@
package cn.hutool.core.clone;
import cn.hutool.core.util.ReflectUtil;
/**
* 克隆默认实现接口用于实现返回指定泛型类型的克隆方法
*
* @param <T> 泛型类型
* @since 5.7.17
*/
public interface DefaultCloneable<T> extends java.lang.Cloneable {
/**
* 浅拷贝提供默认的泛型返回值的clone方法
*
* @return obj
*/
default T clone0() {
try {
return ReflectUtil.invoke(this, "clone");
} catch (Exception e) {
throw new CloneRuntimeException(e);
}
}
}

View File

@ -1,6 +1,8 @@
package cn.hutool.core.clone;
import lombok.AllArgsConstructor;
import lombok.Data;
import org.junit.Assert;
import org.junit.Test;
@ -17,70 +19,29 @@ public class DefaultCloneTest {
oldCar.setWheelList(Stream.of(new Wheel("h")).collect(Collectors.toList()));
Car newCar = oldCar.clone0();
Assert.assertEquals(oldCar.getId(),newCar.getId());
Assert.assertEquals(oldCar.getWheelList(),newCar.getWheelList());
Assert.assertEquals(oldCar.getId(), newCar.getId());
Assert.assertEquals(oldCar.getWheelList(), newCar.getWheelList());
newCar.setId(2);
Assert.assertNotEquals(oldCar.getId(),newCar.getId());
Assert.assertNotEquals(oldCar.getId(), newCar.getId());
newCar.getWheelList().add(new Wheel("s"));
Assert.assertNotSame(oldCar, newCar);
}
}
class Car implements DefaultClone {
private Integer id;
private List<Wheel> wheelList;
public Integer getId() {
return id;
@Data
static class Car implements DefaultCloneable<Car> {
private Integer id;
private List<Wheel> wheelList;
}
public void setId(Integer id) {
this.id = id;
@Data
@AllArgsConstructor
static class Wheel {
private String direction;
}
public List<Wheel> getWheelList() {
return wheelList;
}
public void setWheelList(List<Wheel> wheelList) {
this.wheelList = wheelList;
}
@Override
public String toString() {
return "Car{" +
"id=" + id +
", wheelList=" + wheelList +
'}';
}
}
class Wheel {
private String direction;
public Wheel(String direction) {
this.direction = direction;
}
public String getDirection() {
return direction;
}
public void setDirection(String direction) {
this.direction = direction;
}
@Override
public String toString() {
return "Wheel{" +
"direction='" + direction + '\'' +
'}';
}
}