我有以下活动课程。我有一个与Property方法有关的问题set {userAccount = value;}
它会复制userAccount对象(深拷贝?)或者它会复制userAccount对象引用(浅拷贝?)我是否需要制作一个UserAccountInfo类中的方法做值复制吗?
class EvEndGetUserAccount
{
private UserAccountInfo userAccount;
/// <summary>
/// An event class for getting user account
/// </summary>
/// <param name="account"></param>
public EvEndGetUserAccount(UserAccountInfo account)
{
userAccount = account;
}
/// <summary>
/// Get/Set userAccount
/// </summary>
public UserAccountInfo UserAccount
{
get { return userAccount; }
set { userAccount = value; }
}
/// <summary>
/// returns the content of this EvEndGetUserAccount event.
/// </summary>
/// <returns>string represent of the EvEndGetUserAccount object</returns>
public override string ToString()
{
return userAccount.ToString();
}
}
答案 0 :(得分:4)
它不会复制UserAccountInfo。它是一个引用类型,因此您的属性被设置为对现有对象的引用 - 而不是新对象。
如果您希望在运行setter时创建一个全新的对象,则需要在UserAccountInfo上实现一个进行深层复制的Clone()方法。
答案 1 :(得分:2)
它会生成一个浅表副本,换句话说它只会复制引用。如果要进行深层复制(或克隆),请将IClonable接口添加到您的班级。它将强制您添加一个实现精确深度复制逻辑的新Clone方法
答案 2 :(得分:0)
首先,一些命名法:除非你使用ref
关键字,否则C#总是按值传递。您正在寻找的区别是UserAccountInfo是值类型还是引用类型。
是的,您的类保留对UserAccountInfo对象的引用。如果你想改变这个,那么当它被传递给setter和构造函数时,你应该让它成为Clone()userAccount对象。您还必须确保UserAccountInfo实现ICloneable。
但是,根据您提供的有限上下文,我的猜测是您希望保留引用,即保持原样。
这是关于在C#中传递参数的一个很好的链接:http://www.yoda.arachsys.com/csharp/parameters.html
答案 3 :(得分:0)
这取决于UserAccountInfo
的类型。如果它是引用类型(通常是C#class
),则=
运算符只是将引用复制到对象的单个实例。
如果类型是值类型(例如使用C#struct
关键字声明或基本类型如int
),则它将复制对象的值。由于值类型通常是不可变的(意味着您无法修改该值),因此您无法通过分析程序的行为来识别这一点(传递引用和值会为不可变数据类型提供相同的结果)。
如果您需要创建副本,可以考虑使用ICloneable
界面。您还可以使用MemberwiseClone
method克隆对象。在.NET中,术语浅层和深层副本通常表示以下内容:
浅拷贝 - 创建一个新实例并将原始实例的字段值复制到新实例(这意味着如果克隆对象引用其他对象,则副本将引用相同的对象)
深层复制 - 克隆对象并克隆对象引用的所有对象(依此类推......)。这意味着将克隆整个对象引用树。