首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >处理引用类型

处理引用类型
EN

Stack Overflow用户
提问于 2009-11-10 15:11:06
回答 4查看 118关注 0票数 1

当引用变量可以通过引用传递时:

代码语言:javascript
复制
    class Example
    {
        public string str="Demo";

        public int[] intValues={1,3,4,5};

       public static void StrPassing(string someStr)
        {
            string otherStr="Changed!";
            someStr=otherStr;
        }

        public static void NumPassing(int[] a)
        {
            a[2] = 115;
        }

    }


       static void Main(string[] args)
        {
            Example ex = new Example();
            Example.StrPassing(ex.str);
            Example.NumPassing(ex.intValues);

            foreach (int i in ex.intValues)
            {
                Console.WriteLine(i);
            }

            Console.WriteLine(ex.str);
            Console.ReadLine();
        }

当引用被更改时,intValues[2]的值被更改为115。字符串“passed.But”(演示)的值没有更改为" changed !".What是it?.can的原因吗,因为数组是通过引用传递的,而其他引用类型是通过值传递的?

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2009-11-10 15:23:16

你需要区分改变变量引用的对象和改变*对象的内容“。

在此代码中:

代码语言:javascript
复制
public static void StrPassing(string someStr)
{
    string otherStr="Changed!";
    someStr=otherStr;
}

..。您正在更改someStr的值。您不会对someStr最初引用的字符串进行任何更改。实际上,你不能这样做,因为字符串是不可变的。(如果是StringBuilder,可以将长度设置为0,然后附加"Changed!")

更改someStr的值无效,因为参数(ex.str)是通过值传递的。(有问题的值是一个引用,但这并不意味着它是通过引用传递的。)

现在将其与下面的代码进行比较:

代码语言:javascript
复制
public static void NumPassing(int[] a)
{
    a[2] = 115;
}

这里您没有更改a的值-您更改的是a引用的数组的内容。

简而言之,除非使用ref/out,否则参数将通过值传递-但对于引用类型,该值只是一个引用。

我有一个article on parameter passing,它更详细地介绍了这一切。

票数 3
EN

Stack Overflow用户

发布于 2009-11-10 15:15:25

作为参数传递给方法的任何内容都是通过值传递的,对于引用类型,这意味着引用是通过值传递的。因此,您不能将对象更改为另一个对象,但您肯定可以更改其内容(因为这不会更改实际的引用,只是在其他地方更改一些内存)。

正如您的数组示例所示,您需要获取数组引用(但不要更改它)并更改数组中的值。这就像获取某个对象并更改属性值一样。你也可以在一个方法中很好地做到这一点。

如果你想改变一个字符串,它在.NET中是一个不可变的对象,那么你需要求助于ref参数:

代码语言:javascript
复制
public static void StrPassing(ref string someStr)
{
    string otherStr="Changed!";
    someStr=otherStr;
}

然后这样叫它:

代码语言:javascript
复制
string foo = "foo";
StrPassing(ref foo);
Console.WriteLine(foo); // should print "Changed!"

ref关键字确保您的方法获得对字符串的实际引用,并且可以更改它,而不仅仅是引用的副本。这样你就可以用一个全新的对象来替换这个对象。

回到您的数组:您也很难将传递的数组更改为完全不同的数组:

代码语言:javascript
复制
public static void NumPassing(int[] a)
{
    a = new int[15];
}

也不会起作用,因为这样做的效果与将字符串更改为完全不同的字符串完全相同。

票数 5
EN

Stack Overflow用户

发布于 2009-11-10 15:15:27

您需要做的是更改StrPassing的签名,使其如下所示:

代码语言:javascript
复制
public static void StrPassing(ref string someStr)
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1706119

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档