我定义了一个基接口IDrivingLicenceB,IDrivingLicenceA 继承自IDrivingLicenceB,两个接口都有GetLicence方法
然后定义一个基类A里面有个虚方法,B类继承A类,重写a方法。
问题来了,MAIN函数里都是用父类去实例化子类,父接口去实例化子实例。虚方法可以理解,override 了,调用的是子类的方法。但为什么接口明明是NEW,调用的却也是子类的GetLicence呢?????!!
using System;
using System.Collections.Generic;
using System.Text;namespace ConsoleApplication1
{
class Program
{
class A
{
public virtual void a()
{
Console.WriteLine("A.a");
}
}
class B : A
{
public override void a()
{
Console.WriteLine("B.a");
}
}
interface IDrivingLicenceB
{
void GetLicence();
}
interface IDrivingLicenceA : IDrivingLicenceB
{
new void GetLicence();
}
class Teacher : IDrivingLicenceA
{
public void GetLicence()
{
Console.WriteLine("老师获得了A类驾驶执照");
}
}
class Stuednt : IDrivingLicenceB
{
public void GetLicence()
{
Console.WriteLine("老师获得了B类驾驶执照");
}
}
class Test
{
static void DriveCar(string name, IDrivingLicenceB o)
{
IDrivingLicenceB dl = o as IDrivingLicenceB;
if (dl != null)
{
Console.WriteLine(name + "开动了卡车");
}
else
{
Console.WriteLine(name + "没有驾驶执照,不能开卡车");
}
}
static void DriveBus(string name, IDrivingLicenceB o)
{
IDrivingLicenceA dl = o as IDrivingLicenceA;
if (dl != null)
{
Console.WriteLine(name + "开动了公交车");
}
else
{
Console.WriteLine(name + "没有驾驶执照,不能开公交车");
}
}
static void Main(string[] args)
{
Teacher t = new Teacher();
Stuednt s = new Stuednt();
A a1 = new B();
a1.a();
IDrivingLicenceB ib = t;
ib.GetLicence();
}
}
}
}
然后定义一个基类A里面有个虚方法,B类继承A类,重写a方法。
问题来了,MAIN函数里都是用父类去实例化子类,父接口去实例化子实例。虚方法可以理解,override 了,调用的是子类的方法。但为什么接口明明是NEW,调用的却也是子类的GetLicence呢?????!!
using System;
using System.Collections.Generic;
using System.Text;namespace ConsoleApplication1
{
class Program
{
class A
{
public virtual void a()
{
Console.WriteLine("A.a");
}
}
class B : A
{
public override void a()
{
Console.WriteLine("B.a");
}
}
interface IDrivingLicenceB
{
void GetLicence();
}
interface IDrivingLicenceA : IDrivingLicenceB
{
new void GetLicence();
}
class Teacher : IDrivingLicenceA
{
public void GetLicence()
{
Console.WriteLine("老师获得了A类驾驶执照");
}
}
class Stuednt : IDrivingLicenceB
{
public void GetLicence()
{
Console.WriteLine("老师获得了B类驾驶执照");
}
}
class Test
{
static void DriveCar(string name, IDrivingLicenceB o)
{
IDrivingLicenceB dl = o as IDrivingLicenceB;
if (dl != null)
{
Console.WriteLine(name + "开动了卡车");
}
else
{
Console.WriteLine(name + "没有驾驶执照,不能开卡车");
}
}
static void DriveBus(string name, IDrivingLicenceB o)
{
IDrivingLicenceA dl = o as IDrivingLicenceA;
if (dl != null)
{
Console.WriteLine(name + "开动了公交车");
}
else
{
Console.WriteLine(name + "没有驾驶执照,不能开公交车");
}
}
static void Main(string[] args)
{
Teacher t = new Teacher();
Stuednt s = new Stuednt();
A a1 = new B();
a1.a();
IDrivingLicenceB ib = t;
ib.GetLicence();
}
}
}
}
前面的关键字是 public abstract virtual。
{
public virtual void a()
{
Console.WriteLine("A.a");
}
}
class B : A
{
public new void a()
{
Console.WriteLine("B.a");
}
}
static void Main(string[] args)
{
A a1 = new B();
a1.a();
IDrivingLicenceA ib =t;
ib.GetLicence();
}
把B转化成A ,A的A1方法调用的还是A(父类)里的方法,因为B里的方法是NEW
那问题是下面这个接口IB也是父接口实例出子对象。调用的却是子类的方法,是怎么回事啊
首先new的意思就是定义一个有相同名称的不同方法、属性、字段等,并不是替换基类方法,也不是隐藏。
而类在实现接口的时候,如果没有显示实现接口的方法,那么会自动匹配类中的方法。也就是说Teacher中的GetLicence()方法同时匹配了IDrivingLicenceA,IDrivingLicenceB中的GetLicence()方法。如果你要为IDrivingLicenceB的GetLicence()方法提供不同的实现,那么可以显示实现IDrivingLicenceB接口:void IDrivingLicenceB.GetLicence()
{
Console.WriteLine("老师获得了B类驾驶执照");
}
看到的只不过是一个现象而已。
IDrivingLicenceA的GetLicence和IDrivingLicenceB的GetLicence是两个不同的方法,而你在定义Teacher的GetLicence方法时,同时实现了这2个接口的GetLicence方法。那么不管你调用IDrivingLicenceA还是IDrivingLicenceB的GetLicence,实际上都是Teacher的GetLicence。
或者,你认为应该得到什么结果?
{
void GetLicence();
}
interface IDrivingLicenceA
{
void GetLicence();
}
class Teacher : IDrivingLicenceA,IDrivingLicenceB
{
public void GetLicence()
{
Console.WriteLine("老师获得了A类驾驶执照");
}
}虽然IDrivingLicenceA和IDrivingLicenceB的GetLicence()方法一点关系都没有,但实际上在Teacher里还是同一个实现。
我明白了点,可是为什么抽象类继承抽象类同名方法只能override,接口只能NEW