using System;
using System.Collections.Generic;
using System.Text;namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            Food f = new Food();
            f.X = 4;
            Console.WriteLine(f.X.ToString());//输出4
            Program p = new Program();
            p.Change(f);//想新生成一个实例
            Console.WriteLine(f.X.ToString());//输出4,没有改变
            Console.Read();
        }
        void Change(Food f)
        {
            f = new Food();
            f.X = 666;
        }
    }
    class Food
    {
        public int X { get; set; }
    }
}
ref我知道,但是
我觉得new的时候应该产生一个新的实例,然后f的地址也是指向新的,怎么访问到的还是旧的实例呢?

解决方案 »

  1.   

    void Change(Food f)
            {
                f = new Food();这里只是更改了行参f的引用,跟实参f没有关系
      

  2.   

    这里是两个变量f指向了同一个对象
    void Change(Food f) 
    {
    f = new Food();这里的f变量指向了另一个对象,但是原来的f变量并没有改变对象地址
      

  3.   

    ref 关键字使参数按引用传递。其效果是,当控制权传递回调用方法时,在方法中对参数所做的任何更改都将反映在该变量中。若要使用 ref 参数,则方法定义和调用方法都必须显式使用 ref 关键字
      

  4.   

    去掉Change函数里的f=new Food()试试。。
      

  5.   

    同意,change函数这么写意义不大
      

  6.   

    这样说会更迷糊,如果跟实参f没有关系,那么
            void Change(Food f)
            {
                f.X = 666;
            }
      

  7.   

            void Change(Food f)
            {
                f = new Food();<------------此f非彼f,这里的f实际是一个副本
                f.X = 666;
            }
      

  8.   

    可以加 ref 把属性值传出来using System;
    using System.Collections.Generic;
    using System.Text;namespace ConsoleApplication1
    {
        class Program
        {
            static void Main(string[] args)
            {
                Food f = new Food();
                f.X = 4;
                Console.WriteLine(f.X.ToString());//输出4
                Program p = new Program();
                p.Change(ref f);//想新生成一个实例
                Console.WriteLine(f.X.ToString());//输出4,没有改变
                Console.Read();
            }
            void Change(ref Food f)
            {
                f = new Food();
                f.X = 666;
            }
        }
        class Food
        {
            public int X;
        }
    }
      

  9.   

    传入Change方法中的f是一个指向托管堆(暂时称为B1)的一个引用,暂时成为f1
    而Change方法中的f是f1的一个副本,暂时称为f2,它和f1都维持对B1的引用
    然后f=new Food();
    使得在托管堆上创建了新的内存空间,称为B2
    也就是说f2指向B2
    但f1仍然指向B1
      

  10.   


    这样写的话,由于f1与f2都指向B1,所以f2对B1所做的修改,f1也会修改