有代码如下,问输出的是多少:

class Program
{
static void Main(string[] args)
{
B b = new B();
Console.ReadKey();
}
class A
{
public A()
{
PrintFields();
}
public virtual void PrintFields() { }
}
class B : A
{
int x = ;
int y;
public B()
{
y = -;
}
public override void PrintFields()
{
Console.WriteLine("x={0},y={1}", x, y);
}
}
}

结果:x=1;y=0;

刚开始有点不理解,觉得输出是x=1;y=-1;然后反编译看了下IL代码,然而。。还是没看出来,IL代码如下:

.class private auto ansi beforefieldinit Program
extends [mscorlib]System.Object
{
.method public hidebysig specialname rtspecialname instance void .ctor() cil managed
{
.maxstack
L_0000: ldarg.0
L_0001: call instance void [mscorlib]System.Object::.ctor()
L_0006: nop
L_0007: ret
} .method private hidebysig static void Main(string[] args) cil managed
{
.entrypoint
.maxstack
.locals init (
[] class ConsoleApplication1.Program/B b)
L_0000: nop
L_0001: newobj instance void ConsoleApplication1.Program/B::.ctor()
L_0006: stloc.0
L_0007: call valuetype [mscorlib]System.ConsoleKeyInfo [mscorlib]System.Console::ReadKey()
L_000c: pop
L_000d: ret
} .class auto ansi nested private beforefieldinit A
extends [mscorlib]System.Object
{
.method public hidebysig specialname rtspecialname instance void .ctor() cil managed
{
.maxstack
L_0000: ldarg.0
L_0001: call instance void [mscorlib]System.Object::.ctor()
L_0006: nop
L_0007: nop
L_0008: ldarg.0
L_0009: callvirt instance void ConsoleApplication1.Program/A::PrintFields()
L_000e: nop
L_000f: ret
} .method public hidebysig newslot virtual instance void PrintFields() cil managed
{
.maxstack
L_0000: nop
L_0001: ret
} } .class auto ansi nested private beforefieldinit B
extends ConsoleApplication1.Program/A
{
.method public hidebysig specialname rtspecialname instance void .ctor() cil managed
{
.maxstack
L_0000: ldarg.0
L_0001: ldc.i4.1
L_0002: stfld int32 ConsoleApplication1.Program/B::x
L_0007: ldarg.0
L_0008: call instance void ConsoleApplication1.Program/A::.ctor()
L_000d: nop
L_000e: nop
L_000f: ldarg.0
L_0010: ldc.i4.m1
L_0011: stfld int32 ConsoleApplication1.Program/B::y
L_0016: ret
} .method public hidebysig virtual instance void PrintFields() cil managed
{
.maxstack
L_0000: nop
L_0001: ldstr "x={0},y={1}"
L_0006: ldarg.0
L_0007: ldfld int32 ConsoleApplication1.Program/B::x
L_000c: box int32
L_0011: ldarg.0
L_0012: ldfld int32 ConsoleApplication1.Program/B::y
L_0017: box int32
L_001c: call void [mscorlib]System.Console::WriteLine(string, object, object)
L_0021: nop
L_0022: ret
} .field private int32 x .field private int32 y }
}

IL代码

最后打断点,找到了原因

原因分析:

B b = new B();

执行顺序:

1、int x = 1;int y;给x赋值1,给y赋值默认为0(int类型)

2、public B(),然后关键点来了

3、public A(),执行A里面的PrintFields();但是A里面的这个方法是个虚方法,会调用B里面重写的方法

4、public override void PrintFields()这个是B里面的然后Console.WriteLine("x={0},y={1}", x, y);结果当然就是x=1;y=0;

5、然后才回到了B的public B(),接着给y赋值y = -1;这个时候y才变了,如果这个时候打印y的值才是-1,这个时候B的实例化就完成了

关键点:实例化类的时候,会先执行继承的父类的构造函数,如果父类构造函数含有虚方法又会回调子类的重写方法,之后才回到初始类的构造函数

C#基础 继承和实例化的更多相关文章

  1. python基础——继承和多态

    python基础——继承和多态 在OOP程序设计中,当我们定义一个class的时候,可以从某个现有的class继承,新的class称为子类(Subclass),而被继承的class称为基类.父类或超类 ...

  2. python基础——继承实现的原理

    python基础--继承实现的原理 1 继承顺序 class A(object): def test(self): print('from A') class B(A): def test(self) ...

  3. python基础——继承与派生、组合

    python基础--继承与派生 1 什么是继承: 继承是一种创建新的类的方式,在python中,新建的类可以继承自一个或者多个父类,原始类成为基类或超累,新建的类成为派生类或子类 1.1 继承分为:单 ...

  4. api的使用机制:继承、实例化、实现(继承)配置、实例(参数化)配置、机制管理模块

    api的使用机制:继承.实例化.实现(继承)配置.实例(参数化)配置.机制管理模块 facade模式.管理模块

  5. 《Java基础——继承》

    Java基础--继承     一.类的继承: 规则: 1.一个子类只能有一个父类,但一个父类可以有多个子类,每个子类都可以作为父类使用. 2.若一个类没有声明父类,则默认其父类为Object. 3.父 ...

  6. JAVA基础-子类继承父类实例化对象过程

    之前在项目中碰到这样一个问题: 类B继承了类A,B在实例化的时候,A的构造方法中调用了B的某个方法,并且B的方法中对B的成员属性进行了初始化,然后最后得到的B对象的成员属性为空. 代码场景如下: 这里 ...

  7. python基础----继承与派生、组合、接口与归一化设计、抽象类、子类中调用父类方法

    一.什么是继承                                                                          继承是一种创建新的类的方式,在pyth ...

  8. 03Java基础——继承

    1.继承 例如一个员工类,包括开发员工和经理. package cn.jxufe.java.chapter2.demo12; public class Employee { String name; ...

  9. Java 基础 - 继承

    子类继承父类的private字段么? Oracle的Java Documentation对Inheritance的定义: 很直白,定义里面就告诉你了这不叫继承.继承的意思是你可以对其进行直接的调用和修 ...

随机推荐

  1. POJ 2339

    #include <iostream> #include <algorithm> #define MAXN 205 using namespace std; char _m[M ...

  2. (转)Python中集合(set)的基本操作以及一些常见的用法

    原文:http://blog.51cto.com/10616534/1944841 Python除了List.Tuple.Dict等常用数据类型外,还有一种数据类型叫做集合(set),集合的最大特点是 ...

  3. android瓦片地图技术研究

    最近根据公司项目需求,需要制作场馆的室内图并且实现根据rfid信号的自动定位功能,研究了好久找到了一个目前为止还算好用的瓦片地图工具——TileView. github连接:https://githu ...

  4. 二叉树的LCA(最近公共祖先)算法

    1.如果是二叉搜索树 2.如果是普通树

  5. tomcat与jboss等容器的区别

    1.JBoss 是 J2EE 应用服务器,而 Tomcat 只是一个 Servlet 容器,或者说是一个简单的 J2EE 应用服务器. JBoss 中的 Servlet 容器还是 Tomcat. 与  ...

  6. hadoop的RPC机制 -源码分析

    这些天一直奔波于长沙和武汉之间,忙着腾讯的笔试.面试,以至于对hadoop RPC(Remote Procedure Call Protocol ,远程过程调用协议,它是一种通过网络从远程计算机程序上 ...

  7. OpenStack Identity(Keystone)概述及示例

    OpenStack 的验证服务有两个主要功能: 1. 用户管理(租户.用户.权限) 2. Service catalog,管理服务的目录和它们的endpoint. 相关概念 1. User User即 ...

  8. Ionic APP 热更新 之 产品发布状态下的热更新搭建,去local-dev-addon插件

    上一篇,我们介绍了在本地开发环境下的ionic项目热更新测试, 本文,我们将详细说明如何在去掉cordova-hot-code-push-local-dev-addon插件的情况下,实现热更新. 使用 ...

  9. [转]javascript之Object.assign()痛点

    本文转自:http://blog.csdn.net/waiterwaiter/article/details/50267787 最近也一直会用javascript,然后中间使用的一些组件,如Echar ...

  10. MVC页面缓存

    1.OutputCache 属性 contact.cshtml    [OutputCache(Duration=10)] public ActionResult Contact()   {      ...