属性参数是否按值传递?

时间:2010-02-22 19:49:38

标签: c#

我有以下活动课程。我有一个与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();
        }
    }

4 个答案:

答案 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中,术语浅层和深层副本通常表示以下内容:

  • 浅拷贝 - 创建一个新实例并将原始实例的字段值复制到新实例(这意味着如果克隆对象引用其他对象,则副本将引用相同的对象)

  • 深层复制 - 克隆对象并克隆对象引用的所有对象(依此类推......)。这意味着将克隆整个对象引用树。