c# 值传递 引用传递
以前一直误以为引用类型,在作为参数传递时,都是引用传递(类似于值传递中的ref),也就是说,把引用类型的变量作为参数传递给方法,在方法中修改该参数,会改变这个变量的值,
后来通过一些事例发现,上面的认识是片面的,引用类型传递实际上也是属于值传递的,只是引用类型传递的是一个堆地址。
先来个例子吧:
- using System;
- public class test{
- public static void Main(){
- testClass a = new testClass();
- ChangeToNull(a);
- Console.WriteLine(string.Format("a不是null,它的属性值为:{0}", a.field));
- ChangeField(a);
- Console.WriteLine(string.Format("a的属性值为:{0}", a.field));
- ChangeToNull(ref a);
- Console.WriteLine(string.Format("a是不是null:{0}", (a == null)));
- }
- static void ChangeToNull(testClass b){
- b = null;
- if(b == null){
- Console.WriteLine("在ChangeToNull方法中,参数已经被修改成null了!");
- }
- }
- static void ChangeField(testClass b){
- b.field = 0;
- Console.WriteLine("在ChangeField方法中,参数的成员已经被修改成0了!");
- }
- static void ChangeToNull(ref testClass b){
- b = null;
- if(b == null){
- Console.WriteLine("在ChangeToNull使用ref的重载方法中,参数已经被修改成null了!");
- }
- }
- }
- class testClass{
- public int field;
- public testClass(){
- field = 123;
- }
- }
上面的代码,执行后的结果是:
在ChangeToNull方法中,参数已经被修改成null了!
a不是null,它的属性值为:123
在ChangeField方法中,参数的成员已经被修改成0了!
a的属性值为:0
在ChangeToNull使用ref的重载方法中,参数已经被修改成null了!
a是不是null:True
由此可见,引用类型作为参数时:
1、在修改变量本身时,结果类似于值传递,即不会改变传递前的变量的值
2、在修改变量的属性或字段时,才是引用传递,会影响到传递前的变量的值
3、参数使用了ref后,才是真正的引用传递,不管修改变量本身还是修改变量的属性或字段,都会影响到传递前的变量的值
究其原因,我们知道,值类型和引用类型,在运行时,它们存放的位置是不同的,值类型是存储在进程的栈上的
而引用类型是存储在进程堆(Heap)上的,在进程的栈上存储了这个引用类型在堆上的地址
而在调用方法时,是把栈上的参数的值复制一份传递给方法,所以值类型作为参数传递时,不会改变原变量值很明显
引用类型传递时,也是一样,把栈上的这个堆地址复制一份传递给方法,
所以在方法里修改这个复制的地址的值,当然不会改变原变量的值,
但是修改这个复制的地址所指向的堆里的内容,那原变量指向的地址的内容当然也跟着改变了。
如果参数加了ref,那传递的就是栈的地址的,此时不管是值类型还是引用类型,都会改变原变量的内容
综上所述,我们可以知道,引用类型作为参数传递,不能单纯的说它就是引用传递,如果直接这么认为,在开发中难免会犯错误的,深入的理解一下值类型和引用类型的传递,还是很有必要的。
c# 值传递 引用传递的更多相关文章
- 对象引用 方法传参 值传递 引用传递 易错点 MD
Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱 MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina ...
- C++之值传递&指针传递&引用传递详解
C++之值传递&指针传递&引用传递详解 目录 C++之值传递&指针传递&引用传递详解 1.函数基础 2.值传递 3.指针传递 4.引用传递 1.函数基础 一个函数由以下 ...
- php函数间的参数传递(值传递/引用传递)
php:函数间的参数传递 1.值传递 代码如下: <?php function exam($var1){ $var1++: echo "In Exam:" . $var1 . ...
- php 数组 类对象 值传递 引用传递 区别
一般的数据类型(int, float, bool)不做这方面的解说了 这里详细介绍一下数组和的类的对象作为参数进行值传递的区别 数组值传递 实例代码: <?php function main() ...
- 值传递 & 引用传递
以下程序的输出结果是? public class Example { String str = new String("good"); char[] ch = { 'a', 'b' ...
- 理解--->Java中的值传递&引用传递
转自:http://url.cn/5tL9F5D 值传递和引用传递 值传递(pass by value)是指在调用函数时将实际参数复制一份传递到函数中,这样在函数中如果对参数进行修改,将不会影响到实际 ...
- [转载]php 数组 类对象 值传递 引用传递 区别
一般的数据类型(int, float, bool)不做这方面的解说了 这里详细介绍一下数组和的类的对象作为参数进行值传递的区别 数组值传递 实例代码: <?php function main() ...
- Java小白进阶之值传递-引用传递
class ClassA{ int value;//成员变量 } public class TestClassA{ public static void main(String args[]){ in ...
- 3.GO-项目结构、包访问权限、闭包和值传递引用传递
3.1.goland中项目结构 (1)在goland中创建标准Go项目 (2)goland配置 创建项目Learn-Go file-settings-go-GOPATH-添加 在项目目录下创建src目 ...
随机推荐
- android系统如何自适应屏幕大小
1.屏幕相关概念 1.1分辨率 是指屏幕上有横竖各有多少个像素 1.2屏幕尺寸 指的是手机实际的物理尺寸,比如常用的2.8英寸,3.2英寸,3.5英寸,3.7英寸 android将屏幕大小分为四个级别 ...
- Android 系统功能设置菜单 LinearLayout与relativeLayout的实现
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android=&quo ...
- 【CF】7 Beta Round D. Palindrome Degree
manacher+dp.其实理解manacher就可以解了,大水题,dp就是dp[i]=dp[i>>1]+1如何满足k-palindrome条件. /* 7D */ #include &l ...
- NOI2005瑰丽华尔兹
1499: [NOI2005]瑰丽华尔兹 Time Limit: 3 Sec Memory Limit: 64 MBSubmit: 893 Solved: 508[Submit][Status] ...
- Hadoop RPC简单实例
1.导入Hadoop-Common-2.6.0.jar导入工程,里面的IPC实现RPC需要的文件. 2.服务器端 (1)服务接口 package com.neu.rpc.server; /** * ...
- 【转】Ubuntu下配置samba服务器--不错
原文网址:http://my.oschina.net/junn/blog/171388 设置虚拟机的网络方式为桥接方式: 一. samba的安装: sudo apt-get insall samba ...
- Linux上使用Qt Creator进行C/C++开发
目录[-] 1.安装Qt Creator和基础构建环境(以Ubuntu为例): 2.把自动完成快捷键"Ctrl+空格"改为"Alt+/"或者"Shif ...
- 使用jenkins + python + selenium一步步搭建web自动化测试“框架”(1) - 各部件简介
原先搭建过一个自动化测试框架,迷迷糊糊不求甚解,算是搭建了一个仅限于能用的.根本算不上框架的玩意儿. 现在回过头来好好看看究竟每一步是怎么联系起来的,是怎么运行起来的. 本次博客先说说各部件都是干什么 ...
- C#中类的默认访问是私有的
如果类前面没有访问修饰符的话,那里面的成员默认是私有private. 下面的代码是从MSDN上拷的,那个d它说明了私有:class Employee{private int i;double d; / ...
- ORM介紹及ORM優點、缺點
主要內容: 1.ORM的概念 2.為什麽要使用ORM 3.ORM的優缺點 4..Net中有那些ORM產品 5.總結 一.ORM的概念 ORM,即Object-Relational Mapping( ...