Java:如何复制一个对象,使其来自同一个子类?

2024-04-24

我尝试使用一个简单的例子来更好地理解:我有一堂课Tool以及正在延伸班级的子班Tool: Hammer, Saw。两者都定义了一些字段,例如weight两者都是重写方法getCost有自己的实现。

    Tool first_tool = new Hammer();
    Tool second_tool = new Saw();

我需要一个方法Tool类,它将复制任何工具,这样,first_tool_copy来自同一个子类first_tool。我怎样才能使这成为可能?我需要类似的东西:

    /* Copy tool, change parameters of copy, the original won't change */
    /* first_tool_copy will be instance of Hammer class */
    first_tool_copy = first_tool.copy
    first_tool_copy.weight = 100

结论:我想要一些对所有子类通用的简单复制构造函数。


对于这种情况可能有很多解决方案,但我相信最简单的解决方案是使用反射来创建克隆对象并将字段从原始对象复制到副本。该代码的唯一要求是您的子类必须有一个默认构造函数,但这看起来并不是一个真正的问题。

它看起来是这样的:

import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

public class Tool implements Cloneable {

private String name;

public String getName() {
    return name;
}

public void setName(String name) {
    this.name = name;
}

@Override
public Object clone() {

    try {

        Tool instance = this.getClass().newInstance();

        List<Field> fields = new ArrayList<Field>();

        Class<?> kind = this.getClass();

        while ( kind != null ) {
            fields.addAll( Arrays.asList( kind.getDeclaredFields() ) );
            kind = kind.getSuperclass();
        }

        for ( Field field : fields ) {
            field.setAccessible(true);

            int mod = field.getModifiers();

            if ( !Modifier.isStatic( mod ) && !Modifier.isFinal( mod ) && !Modifier.isNative(mod) ) {
                Object value = field.get( this );
                field.set(instance, value);
            }

        }

        return instance;

    } catch (Exception e) {
        throw new UnsupportedOperationException(e);
    }

}

}

这是你的子类,它没有什么特别的:

public class Saw extends Tool {

private int weight;

public int getWeight() {
    return weight;
}

public void setWeight(int weight) {
    this.weight = weight;
}

}

一个 JUnit 测试用例展示了它是如何工作的:

public class SawTest {

@Test
public void testClone() {

    Saw original = new Saw();
    original.setName("Some saw");
    original.setWeight( 10 );

    Saw clone = (Saw) original.clone();

    Assert.assertTrue( original != clone );
    Assert.assertTrue( original.getClass().equals( clone.getClass() ) );
    Assert.assertEquals( original.getName(), clone.getName() );
    Assert.assertEquals( original.getWeight(), clone.getWeight() );

}

}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Java:如何复制一个对象,使其来自同一个子类? 的相关文章

随机推荐

  • 在 post-command-hook 中,这个用于kill-word的命令已经以某种方式变成了kill-region

    In my post command hook回调 当我这样做时kill word the this command var is kill region 并不是kill word正如预期的那样 我想那是因为kill word uses k
  • Swift 3.0 将图像写入目录

    我有一个简单的ImagePicker供用户选择或拍摄个人资料照片 我想保存这个image to the Home Directory方便以后加载 问题是未设置图像类型 Save Image PPimagePicked image let i
  • Spark 2.0 弃用了“DirectParquetOutputCommitter”,没有它如何生活?

    最近 我们从 HDFS 上的 EMR gt S3 上的 EMR 启用了一致视图的 EMRFS 迁移 我们意识到 Spark SaveAsTable 镶木地板格式 写入 S3 的速度比 HDFS 慢约 4 倍 但我们发现使用 DirectPa
  • 在 MySQL 中的分组列中搜索?

    我需要创建一个男人的数据库 男人可以有一个或多个属性 每个男人的属性都有一个特定的值 听起来很简单吧 好吧 继续阅读 因为这个问题有点不可能 5 天处理它 s 所以我创建了这 3 个表 CREATE TABLE guy id int 11
  • Int32 和 UInt32 有什么区别?

    有什么区别Int32 and UInt32 如果它们与容量范围能力相同 问题是出于什么原因UInt32被创造了 我应该什么时候使用UInt32代替Int32 UInt32 不允许负数 从MSDN http msdn microsoft co
  • 修复了滚动 html 文档时的 div

    我正在寻找一个 jquery 插件 可以让我实现这种效果 静态向下滚动 http www bnet com blog drug business it 8217s a trap congress wants to see j j ceo s
  • jQuery hide() div 直到完全加载

    我正在为我的博客使用选项卡式特色帖子 如何实施div latest featured will hide then show 内容完全加载后它会回来吗 document ready function Default Action tab c
  • 从 pod 连接到其他 pod

    基本上 我有一个部署 它创建了 3 个自动扩展的容器 PHP FPM NGINX 和包含应用程序的容器 所有这些都设置了机密 服务和入口 该应用程序还在 PHP FPM 和 NGINX 之间共享项目 因此一切都已设置完毕 由于我想使用 K8
  • M1 Apple Silicon Mac 上的 Dynamodb 本地设置

    我使用 dynamodb 进行了本地设置https docs aws amazon com amazondynamodb latest developerguide DynamoDBLocal DownloadingAndRunning h
  • iOS - iOS 设备和外部配件 (BluetoothWatch) 之间 BLE 数据传输的 MTU 大小

    我正在为使用 BLE CoreBluetooth 的蓝牙手表开发 iOS 应用程序 Objective C 并且我的手表具有 GATT 蓝牙配置文件 iOS 应用程序最低支持来自 iOS7 我想知道如何使用 Core Bluetooth 框
  • 如何从 SDK 插件数据文件夹加载 dll?

    我们使用 Web IDE 来创建插件 我的 test dll 位于数据文件夹中 如何通过js ctypes加载它 使用像 c test dll 这样的绝对路径没有问题 但我无法使用此路径来分发它 var lib ctypes open c
  • Linux 中的机器人框架

    如何借助Robot框架获取Linux中执行的命令的状态 例如如果使用这个 SSHLibrary open Connection server SSHLibrary login xxxxx xxxxx 1111 Write command 2
  • 最近有关于 JVM 的书吗? [关闭]

    就目前情况而言 这个问题不太适合我们的问答形式 我们希望答案得到事实 参考资料或专业知识的支持 但这个问题可能会引发辩论 争论 民意调查或扩展讨论 如果您觉得这个问题可以改进并可能重新开放 访问帮助中心 help reopen questi
  • 如何重命名 iOS 8 Today Widget?

    我刚刚开始尝试将 iOS 8 Today Widget 添加到我的应用程序中 到目前为止一切顺利 但我遵循原始模板并使用 TodayWidget 作为名称创建了我的小部件 在 Xcode 中我的应用程序文件的上下文中 目标 产品名称很好 但
  • Java反射性能——替代方案

    各种问题中讨论的主题 参考文献1 https stackoverflow com questions 19557829 faster alternatives to javas reflection 19563000 19563000 参考
  • boost::shared_mutex 多读取器/单写入器互斥体

    我正在尝试使用 boost shared mutex 来实现多读取器 单写入器互斥体 我的问题相当简单 当另一个线程尝试锁定共享互斥体进行写入时 线程是否有可能获得对共享互斥体的读取器访问权限 例如 我有10个线程 只有其中一个可以写 线程
  • 如何通过脚本使Texture2D可读

    我想让用户能够解码从图库加载的 QR 图像 我找到了一个插件来探索图像并将其加载为texture2D 但是要解码该 QR 代码 Texture2D 必须是可读 可写的 我检查了该插件 对于 Android 它使用 jar 进行探索和加载内容
  • 从 PhoneGap 重新启动设备

    有没有办法用phonegap cordova重启设备 我该怎么做呢 我认为这在 iPad iPhone 上可能不可能 但在 Android 上可以 首先 除非您的设备已root 越狱 否则基本上无法完成 取决于我们谈论的是Android o
  • Visual Studio 2010:如何在解决方案中强制执行项目的构建顺序?

    我在 Visual Studio 2008 中没有遇到任何问题 但 VS 2010 似乎有问题 我敢打赌这可能是我的问题 我有一个包含 ASP NET 网站项目和一些 C 项目 BLL DAL NUnit 中的测试 的解决方案 我已将测试项
  • Java:如何复制一个对象,使其来自同一个子类?

    我尝试使用一个简单的例子来更好地理解 我有一堂课Tool以及正在延伸班级的子班Tool Hammer Saw 两者都定义了一些字段 例如weight两者都是重写方法getCost有自己的实现 Tool first tool new Hamm