上周末回家去享受生活了, 工作是为了更好的生活嘛, 所以我把生活, 工作分的比较开. 这几天不是很忙, 在学习工作技能的同时, 发点博文, 也算是做一个学习笔记

上篇中, 贴出的地址里面那位哥, 也有一篇值类型和引用类型的文章

来源:http://www.cnblogs.com/yingql/archive/2009/03/23/1420026.html

我这个和他的那个稍有不同, 各位看官, 请!

一、示例

public class Person
{
public string Name { get; set; } public int Age { get; set; }
} class Program
{
private Random rand = new Random(DateTime.Now.Millisecond); private Person person = new Person { Name = "Elvin", Age = }; private string pro = "pro"; private double dou = 3.14; static void Main(string[] args)
{
Console.WriteLine("Main");
Console.ReadKey();
}
}

反编译Program的构造函数, 代码如下:

public Program()
{
this.rand = new Random(DateTime.Now.Millisecond);
Person person = new Person {
Name = "Elvin",
Age = 0x1a
};
this.person = person;
this.pro = "pro";
this.dou = 3.14;
} .method public hidebysig specialname rtspecialname instance void .ctor() cil managed
{
.maxstack
.locals init (
[] class ConsoleApplication3.Person person,
[] valuetype [mscorlib]System.DateTime time) L_0000: ldarg. //加载this, 是一个地址, 将this沉底, 为一会的this.rand = new Random()服务
L_0001: call valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::get_Now()
L_0006: stloc. //初始化time, 为当前时间
L_0007: ldloca.s time //加载time的地址, 为什么加载地址呢, 一会详细介绍, 容我卖个关子 (1)
L_0009: call instance int32 [mscorlib]System.DateTime::get_Millisecond() //调用结构体Datetime的方法 L_000e: newobj instance void [mscorlib]System.Random::.ctor(int32) //new Random(), 将对象放入堆中, 然后把指向此对象的地址压栈
L_0013: stfld class [mscorlib]System.Random ConsoleApplication3.Program::rand //把刚刚得到的地址赋给rand, 实现this.rand = new Random()功能 L_0018: ldarg. //加载this地址,将this沉底, 为一会的this.person=person服务
L_0019: newobj instance void ConsoleApplication3.Person::.ctor() //new Person()
L_001e: stloc. //person = new Person(), 这里的person并不是this.person, 注意
L_001f: ldloc. //加载person, 为什么此处是用的ldloc, 而不是ldloca呢? 答案马上揭晓
L_0020: ldstr "Elvin" //加载 "Elvin" 字符串
L_0025: callvirt instance void ConsoleApplication3.Person::set_Name(string) //person.Name = "Elvin"
L_002a: nop L_002b: ldloc.
L_002c: ldc.i4.s 0x1a
L_002e: callvirt instance void ConsoleApplication3.Person::set_Age(int32)
L_0033: nop L_0034: ldloc. //加载person, 不是this.person
L_0035: stfld class ConsoleApplication3.Person ConsoleApplication3.Program::person //给this.person赋值, this.person=person L_003a: ldarg. //加载this, 这里加载this做什么? (2)
L_003b: ldstr "pro" //加载"pro"字符串
L_0040: stfld string ConsoleApplication3.Program::pro //this.pro = "pro" L_0045: ldarg.
L_0046: ldc.r8 3.14
L_004f: stfld float64 ConsoleApplication3.Program::dou
L_0054: ldarg.
L_0055: call instance void [mscorlib]System.Object::.ctor()
L_005a: nop
L_005b: ret
}

例子大家应该都能看得懂, 下面就揭晓上面的包袱

二、注意的点

在揭晓答案之前, 首先得开一扇窗户.

大家应该都知道, 值类型、引用类型是怎么存储的吧, 多的就不解释了, 上一幅图吧

2. stfld -- 好吧, 在讲第1点之前, 我还是想先将第2点

先看stfld的工作原理, 即堆栈转换行为如下:

按照先后顺序:

  1.将一个对象引用或指针压入堆栈

  2.将值压入堆栈

  3.该值和对象的引用/指针从堆栈中弹出,对象的字段更新为替换的值

详细分析 : http://www.cnblogs.com/jackson0714/p/4995948.html

从上面可以看出, 是需要传地址的, 先传地址, 在传值, 接着调用stfld指令, 才能完成赋值操作, 所以这里传了个ldarg.0, 来完成this.pro="pro"功能

1. ldloc 与 ldloca

从上面的例子, 看到在使用Person的时候, 用的ldloc, 而使用DateTime的时候, 却使用了ldloca, 此处就能体现引用类型和值类型的区别了.

在调用方法的时候, 由于引用类型在栈中, 存放的就是地址, 所以可以直接实现调用内部方法的功能,

而值类型并不是直接存放地址的, 所以在调用内部方法的时候, 其实是传地址来实现此功能的.

对象,结构体(值类型本质也是结构体, 如:int, decimal)在调用自身方法/属性/字段的时候, 都是通过传递地址的方式来调用的. time.Year(), 此处的time就是地址, person.Name, 此处的person也是一个地址

这哥们对IL有一个比较详细的介绍:http://www.cnblogs.com/jackson0714/p/DotNET_IL3.html#_label4

Emit学习(2) - IL - 值类型和引用类型(补)的更多相关文章

  1. C#学习笔记之值类型与引用类型

    [TOC] C#学习笔记之值类型与引用类型 1.值类型与引用类型 1.1 深层区别 值类型与引用类型有不同的内存分布,这导致了不同的内存管理机制: 值类型由OS负责内存管理 引用类型由垃圾回收器(GC ...

  2. 学习记录 java 值类型和引用类型的知识

    1. Java中值类型和引用类型的不同? [定义] 引用类型表示你操作的数据是同一个,也就是说当你传一个参数给另一个方法时,你在另一个方法中改变这个变量的值, 那么调用这个方法是传入的变量的值也将改变 ...

  3. 【C#】学习笔记(4) 值类型和引用类型相关(Null相关)

    Reference and Value Types Value Types(值类型): struct(结构体) 独立的实例或者是拷贝 值的改变不会影响其它拷贝 值就是它所代表的信息 没有引用,所以不可 ...

  4. C#学习笔记(基础知识回顾)之值类型和引用类型

    一:C#把数据类型分为值类型和引用类型 1.1:从概念上来看,其区别是值类型直接存储值,而引用类型存储对值的引用. 1.2:这两种类型在内存的不同地方,值类型存储在堆栈中,而引用类型存储在托管对上.存 ...

  5. .net学习之.net和C#关系、运行过程、数据类型、类型转换、值类型和引用类型、数组以及方法参数等

    1..net 和 C# 的关系.net 是一个平台,C#是种语言,C#语言可以通过.net平台来编写.部署.运行.net应用程序,C#通过.net平台开发.net应用程序2..net平台的重要组成FC ...

  6. C#学习笔记(三):值类型、引用类型及参数传递

    值类型和引用类型简介 C#中存在两种数据类型,分别是值类型与引用类型,下面我们来看看这两种类型的区别. 值类型主要包括: 简单类型(如int.float.char等,注意string不是值类型): 枚 ...

  7. c#学习基础(2)存储、值类型和引用类型、变量

    程序运行时,它的数据必须存储在内存中,数据项需要多大的内存.存储在什么地方以及如何存储都依赖该数据项的类型 运行中的程序使用两个区域来存储数据:栈和堆 栈是一个内存数组,是一个LIFO(last in ...

  8. Net基础篇_学习笔记_第十二天_面向对象继承(命名空间 、值类型和引用类型)

    命名空间可以认为类是属于命名空间的. 解决类的重名问题,可以看做类的“文件夹”如果在当前项目中没有这个类的命名空间,需要我们手动的导入这个类所在的命名空间.1).用鼠标去点2).alt+shift+F ...

  9. 从CLR角度来看值类型与引用类型

    前言 本文中大部分示例代码来自于<CLR via C# Edition3>,并在此之上加以总结和简化,文中只是重点介绍几个比较有共性的问题,对一些细节不会做过深入的讲解. 前几天一直忙着翻 ...

随机推荐

  1. Angular实现递归指令 - Tree View

    在层次数据结构展示中,树是一种极其常见的展现方式.比如系统中目录结构.企业组织结构.电子商务产品分类都是常见的树形结构数据. 这里我们采用Angular的方式来实现这类常见的tree view结构. ...

  2. SOA服务设计与实现的几个语言无关的原则速记

    一.SOA定义 SOA即面向服务架构(Service-Oriented Architecture).在SOA中,一切皆服务.一个服务是通过消息交换来调用的程序,一个信息系统是共同完成一个特定任务的一组 ...

  3. IOS Socket 04-利用框架CocoaAsyncSocket实现客户端/服务器端

    这篇文章,我们介绍CocoaAsyncSocket框架的使用,主要介绍实现客户端/服务器端代码,相信在网上已经很多这样的文章了,这里做一下自己的总结.这里介绍使用GCD方式 一.客户端 1.下载地址 ...

  4. ios UIButton设置单选效果,以及同时设置图片和标题

    一,设置单选效果 - (void)selectedBtnPress:(UIButton*)sender { //首先把原来按钮的选中效果消除 for (int i=0;i<num;i++) {/ ...

  5. MVVM架构~Knockoutjs系列之对象与对象组合

    返回目录 在面向对象的程序设计里,对象是核心,一切皆为对象,对象与对象之间的关系可以表现为继承和组合,而在Knockoutjs或者JS里,也存在着对象的概念,今天主要说一下JS里的对象及对象的组合. ...

  6. Atitit 颜色平均值cloor grb hsv模式的区别对比

    Atitit 颜色平均值cloor grb hsv模式的区别对比 使用hsv模式平均后会变得更加的靓丽一些..2 public class imgT { public static void main ...

  7. Atitit Gaussian Blur 高斯模糊 的原理and实现and 用途

    Atitit Gaussian Blur 高斯模糊 的原理and实现and 用途 1.1. 高斯模糊 的原理(周边像素的平均值+正态分布的权重1 1.2. 高斯模糊 的用途(磨皮,毛玻璃效果,背景虚化 ...

  8. Atitit.架构设计趋势 设计模式 ---微服务架构  soa

    Atitit.架构设计趋势 设计模式 ---微服务架构  soa 什么是微服务架构?1 .微服务与SOA的关系 :微服务架架构师面向服务架构(SOA)的一种特定实现1 微服务与康威定律2 微服务的一些 ...

  9. PHP 基础

    var_dump(empty($a));    判断变量是否为空 var_dump(isset($a));      判断变量是否定义 $a=10;unset($a);      删除变量 var_d ...

  10. 投资人谈VR色变,VR好戏却刚刚开始

    去年下半年,资本圈谈O2O色变,以至于创业者们都不敢说自己做O2O:到了今年下半年,资本圈却成为了谈VR色变--在中国的互联网科技创业中,资本市场已经成为了创业的一种风向标.资本走向哪里,创业者就走向 ...