引用类型/值类型,引用传递/值传递

C#中引用类型:继承自System.Object,包括类,数组,接口、委托;

           值类型:继承自System.ValueType,包括简单类型,结构,枚举类型

C#中参数传递方式主要分两种,值传递和引用传递,按引用传递必须以ref或者out关键字来修饰,其规则是:方法定义和方法调用必须同时显示的使用ref或者out,否则将导致编译错误;

测试如下:

      // 值类型按值传递
        private void button1_Click(object sender, EventArgs e)
        {
            int j = 2;
            Change(j);
            MessageBox.Show(j.ToString());  // j=2
        }

        private void Change(int i) // 在栈上建立i,并拷贝j的值
        {
            i += 5;
            MessageBox.Show(i.ToString()); // i=7
        }


        // 值类型按引用传递1
        private void button1_Click(object sender, EventArgs e)
        {
           // ref传递必须对j进行初始化,否则报错
            int j = 2;
            Change(ref j);
            MessageBox.Show(j.ToString());  // j=7
        }

        private void Change(ref int i) // i与j公用同一块栈内存
        {
            i += 5;
            MessageBox.Show(i.ToString()); // i=7
        }


        // 值类型按引用传递2
        private void button1_Click(object sender, EventArgs e)
        {
            // out传递可以不初始化
            int j;
            Change(out j);
            MessageBox.Show(j.ToString());  // j=5
        }

        private void Change(out int i) // i与j公用同一块栈内存
        {
            // 注意这里必须初始化i,否则报错
            i = 0;
            i += 5;
            MessageBox.Show(i.ToString()); // i=5
        }

       // 引用类型按值传递
        private void button1_Click(object sender, EventArgs e)
        {
            StringBuilder build1 = new StringBuilder();
            Change(build1);
            MessageBox.Show(build1.ToString());  // build1值:"John"
        }

        private void Change(StringBuilder build2) // build1与build2均在栈中分配内存,但相互独立,且值相等,指向同一块堆内存
        {
            build2.Append("John"); // build2值:"John"
            MessageBox.Show(build2.ToString());
        }

        // 引用类型按值传递2
        private void button1_Click(object sender, EventArgs e)
        {
            StringBuilder build1 = new StringBuilder();
            Change(build1);
            MessageBox.Show(build1.ToString());  // build1值:null
        }

        private void Change(StringBuilder build2) // build1与build2均在栈中分配内存,但相互独立,且值相等,指向同一块堆内存
        {
            build2 = new StringBuilder("John"); // build2值:"John" ,这里改变build2指向,但build1指向没变
            MessageBox.Show(build2.ToString());
        }

        // 引用类型按引用传递1
        private void button1_Click(object sender, EventArgs e)
        {
            StringBuilder build1 = new StringBuilder();
            Change(ref build1);
            MessageBox.Show(build1.ToString());  // build1值:"John"
        }

        private void Change(ref StringBuilder build2) // build2在栈中不重新分配内存,与build1公用,build1与build2同一
        {
            build2 = new StringBuilder("John"); // build2值:"John" ,这里改变build2指向,也就改变了build1指向
            MessageBox.Show(build2.ToString());
        }

       // 引用类型按引用传递2
        private void button1_Click(object sender, EventArgs e)
        {
            StringBuilder build1 = new StringBuilder();
            Change(out build1);
            MessageBox.Show(build1.ToString());  // build1值:"John"
        }

        private void Change(out StringBuilder build2) 
        {
            build2 = new StringBuilder("John"); // build2值:"John" 
            MessageBox.Show(build2.ToString());
        }

 

总结:值类型按值传递----传递主方法参数中变量值的拷贝

           值类型按引用传递----传递主方法参数中变量的地址

          引用类型按值传递----传递主方法参数中变量值的拷贝(这个值指向堆中一块内存,相当于复制了一个指针?)

          引用类型按引用传递----传递主方法参数中变量的地址

#c#
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值