从继承类进行浅复制

3

好的,我可以帮您翻译这段与IT技术相关的内容。这段文字提到了一个抽象基类Product,一个继承自Product的KitItem类和一个继承自KitItem的PackageKitItem类。

Product
KitItem : Product
PackageKitItem : KitItem

我已经加载了我的 KitItems,现在需要加载一组 PackageKitItems,它们实际上是 KitItems 的浅拷贝。

目前我们在 Product 构造函数中执行的是一种感觉很 hacky 的浅拷贝,如下所示:

public Product(Product product)
        {
            FieldInfo[] fields = product.GetType().GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);

            // copy each value over to 'this'
            foreach (FieldInfo fi in fields)
                fi.SetValue(this, fi.GetValue(product));
        }

我尝试在KitItem上设置一个副本,方法如下:

public KitItem ShallowCopy()
        {
            return (KitItem)this.MemberwiseClone();
        }

并将其称为这样:
PackageKitItem tempPackKitItem = (PackageKitItem)packKitItem.ShallowCopy();

但是我得到了一个无效的转换。我正在寻找实现这一目标最好的方法。


如果 packKitItem 是一个 KitItem,那么使用 MemberwiseClone 仍然会返回一个 KitItem。 - undefined
不,克隆在KitItem上,我正在尝试初始化packagekititem,这是问题的关键所在,它无法正常工作。 - undefined
2
你不应该把小猫咪当作产品来包装,那是残忍的! - undefined
3个回答

4

您所遇到的问题是由于ShallowCopy()是KitItem的成员函数,而MemberwiseClone()只复制了KitItem的字段并返回一个KitItem对象,即使原始对象是PackageKitItem。

我认为在这种情况下,您需要在KitItem中添加以下内容:

public virtual KitItem ShallowCopy()        
{            
  return (KitItem) this.MemberwiseClone();        
}

在PackageKitItem中:

public override KitItem ShallowCopy()        
{            
    return (PackageKitItem) this.MemberwiseClone();        
}

因此,根据您尝试进行ShallowCopy()的对象,您将获得适当的MemberwiseClone()调用。
如果您想进一步,可以在Product中定义一个ShallowCopy()(返回Product),然后在KitItem和PackageKitItem中分别覆盖该方法并返回它们各自的浅拷贝。

1

奇怪的是,我在Visual Studio 2008上做这个时没有出错。我将代码发布在这里,以便您可以看到我缺少什么或者我假设错误的地方。我猜测问题可能出现在您没有发布的某个类成员中。

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Reflection;

namespace WindowsFormsApplication1
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            PackageKitItem PKI = new PackageKitItem();
            PKI.ID      = 1;
            PKI.KitName = "2";
            PKI.Name    = "3";
            PKI.Package = 4;

            PackageKitItem tempPackKitItem = (PackageKitItem)PKI.ShallowCopy();

        }
    }

}

public class Product
{
    public int ID;
    public string Name;

    public Product()
    {
    }

    public Product(Product product)
    {
        FieldInfo[] fields = product.GetType().GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);

        // copy each value over to 'this'
        foreach (FieldInfo fi in fields)
            fi.SetValue(this, fi.GetValue(product));
    }


}

public class KitItem:Product
{
    public string KitName;
    public KitItem ShallowCopy()
    {
        return (KitItem)this.MemberwiseClone();
    }

}

public class PackageKitItem : KitItem
{
    public int Package;

}

0
在你的Product构造函数中,你已经在做某种浅拷贝了,对吧?如果你没有重写你的构造函数,那么你应该可以简单地创建一个新的PackageKitItem,它接收一个KitItem作为参数。
PackageKitItem tempPackKitItem = new tempPackKitItem(kitItem);

也许我只是误解了你的问题。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接