当前位置:编程学习 > C#/ASP.NET >>

课程继承要怎么讲

我想把继承讲好一点,希望大家能给点建议。谢谢! 继承 --------------------编程问答-------------------- 继承、封装、多态 是面向对象的三大特性,结合生活中的例子来讲可能跟形象、生动一点。
比如:父亲,儿子继承了父亲的所有优点,同时又有自己的特点。发挥想象吧。 --------------------编程问答-------------------- “儿子继承父亲的优点”跟OOAD的继承是完全不同的。所谓继承,是指概念意义上的继承,也就是一种“is-a”关系。如果是B继承于A,那么一个B它“就是”一个A。例如张柏芝就是一个女人、也是一个演员、对于某会所来说也是一个VIP。谁敢说它自己“就是自己的爸爸”?不敢吧!因此把父子关系说成是OOAD的继承,是不懂OO设计概念的。

你可用这个作为反例,来教会你的学生分辨继承和非继承。 --------------------编程问答-------------------- 例如我们说“我今天上街买了一条外边穿的大裤衩”,那么听到这个话的“正常人”就知道我今天“买了服装”。因为大裤衩“is-a”服装。那么假设这是软件系统,就会把大裤衩“多态地”带入服装处理的中,例如精品店会使用服装销售模块来录入销售信息,而不是使用大裤衩销售模块(可能精品店也没有这个模块)。

事实上,简单的概念,学生反而不能理解其深刻的道理,需要很多年实践来强化这些最简单的概念。但是你仍然要尽量给他们讲明白这个道理。注意不要用什么“儿子继承父亲的财产”之类错误概念来误导他们。 --------------------编程问答-------------------- 在缺乏结构化编程概念的人看来,所谓“大裤衩”就是一个id编号,加上颜色、尺寸、版型等等属性,它以为弄个数据库ER图,弄几条关系数据库增删改查语句,这就是设计。它们只看到最低级的属性,例如只能看到string、int、bool、数组等基本类型,而看不到千姿百态的“用户自定义类型”。因此这些人缺少基本的概念“封装”的能力。

有些人只知道概念,而无法想象出无数“对象”独立地“存在、运行”的状态。例如两个长得一摸一样、味道完全一样的苹果让然是两个独立的苹果,但是他就总觉得这两个苹果有什么神秘的诡异概念复制出来的。因此这些人缺乏“对象都是独立的,可唯一标识的”的认知能力。

有些人学了一定时间的编程,会自定义一些class或者struct了,但是他对继承一直耿耿于怀,他总是心里想不通“子类既可以继承父类的方法,也可以重写(消解)父类的方法”,这样的人难以理解继承。(不过这样的人也许在结构化方面还不错)

有些人滥用继承,把不是继承的东西说成是继承。仅仅为了省得写几行代码,或者别的什么道听途说的原因就去滥用继承。他们产生了各种各样诡异的子类,很快就给产品制造了概念危机。滥用继承的人比丝毫不接受继承的人,不会更好。 --------------------编程问答-------------------- 首先问你的学生一个问题。

User a;

这是什么意思。

你的学生保管都会说,这是定义了一个叫做a的User类型的对象。

当然,这在谭浩强的年代是没有什么问题的。但是在一种支持继承的语言中,这么说就片面了。

User a;表示a可以是一个User类型,或者User的派生类型。

如果能理解了这一点,那就好办了。

我再问一个问题,User的派生类型有哪些?

我也不知道。当然你可以在代码中找一下,但是事实上,你在我写好了这一行之后,可以新定义几个派生自User的类型。因此User的派生类型可以有无数多个。

好了。使用User类型的开发者可以忽视定义User派生类型的程序员的存在而存在了。

比如说,他写这么一个逻辑,判断一个用户是否被授权做一个操作,如果用户有这个权限,就继续下面的逻辑,他可以这么写:
class User
{
    ...
    public virtual bool Authentication(string ActionName) { return false; }
}

void DoSomething(User currentUser)
{
    if (User.Authentication("something")) //判断是否有权限
    {
        ...
    }
    else
    {
        throw new Exception("没有权限");
    }
}


他定义好User类,并且写好通用的逻辑

而定义User派生类的程序员,则可以独立地为User的派生类添加新的代码,具体设计某个特定的用户拥有什么权限,设置他可以从用户的个性设置中加载和判断。

class SuperUser
{
    //超级用户,无论什么操作,都允许他做。
    public override bool Authentication(string ActionName) { return true; }    
}


请注意,编写具体做什么操作的程序员和定义什么用户能做什么操作的程序员是两个人。他们通过定义和继承对象发生联系,但是很明显,前者无需后者就能展开工作。后者呢,他不需要修改前者的代码就可以扩展新的用户类型。

想象下没有继承我们怎么写同样的代码:
void DoSomething(object currentUser)
{
    bool checkresult = false;
    if (currentUser Is AdminUser)
    {
        checkresult = (currentUser As AdminUser).Authentication("something");
    }
    if (currentUser Is SuperUser)
    {
        checkresult = (currentUser As SuperUser).Authentication("something");
    }
    if (currentUser Is GuestUser)
    {
        checkresult = (currentUser As SuperUser).Authentication("something");
    }
    ...
    if (checkresult) //判断是否有权限
    {
        ...
    }
    else
    {
        throw new Exception("没有权限");
    }
}[/code]
我们需要人工去完成类型的判断,并且调用各自的方法——不同的Authentication方法没有联系。那么很显然,每次那个负责编写用户权限的人定义了新的用户类型,就要去找那个编写具体操作的人索要一次代码,并且修改它。

你可以让你的学生几个人编为一组,去体验下,到底是各司其职地协同开发好,还是一个人必须依赖另一个人修改他的代码才能完成自己的工作的方式好。 --------------------编程问答-------------------- 在代码层面,就是把共同的特征提取出来,子类拥有自己的个性。
比如,鸭子的概念。各种鸭子,但是鸭子都有2只脚(属性)、都会游泳(行为),但是颜色可能不同,也可能鸭子的叫声不太一样。
总之发挥想象吧。。。 --------------------编程问答--------------------
引用 6 楼 guwei4037 的回复:
在代码层面,就是把共同的特征提取出来,子类拥有自己的个性。
比如,鸭子的概念。各种鸭子,但是鸭子都有2只脚(属性)、都会游泳(行为),但是颜色可能不同,也可能鸭子的叫声不太一样。
总之发挥想象吧。。。


总之发挥想象吧。。。 --------------------编程问答-------------------- “总之发挥想象吧。。。”这句话说的很好。

为什么要继承,为什么要面向对象,这是你写程序才能体会到的问题。否则只能“发挥想象”。

一些教授,都把想象力放在怎么捞钱学术造假乱搞男女关系上了。至于你让他想象开发中遇到什么问题,不是扯淡吗。 --------------------编程问答--------------------
引用 7 楼 caozhy 的回复:
Quote: 引用 6 楼 guwei4037 的回复:

在代码层面,就是把共同的特征提取出来,子类拥有自己的个性。
比如,鸭子的概念。各种鸭子,但是鸭子都有2只脚(属性)、都会游泳(行为),但是颜色可能不同,也可能鸭子的叫声不太一样。
总之发挥想象吧。。。


总之发挥想象吧。。。


哈哈,看来版主大人看出端倪啦。尽量形象一点,让学生笑笑,印象深了会一直记在脑子里,虽然不一定正确。等学生做了几个项目之后,就会慢慢理解的,这不是一时半会的工夫。。。 --------------------编程问答-------------------- 举些生动的例子,例如玫瑰和花,动物和猫什么的 --------------------编程问答-------------------- 学习继承的目的是培养正确地抽象能力。如果一个中学数学老师给学生讲解各种解方程方法是,只是为了博得学生“一笑”,它可以错误地随便编造函数映射理论吗?那么这个老师教出的学生就无法再学习大学数学和(使用到微积分、方程等数学知识的)物理学课程了。 --------------------编程问答-------------------- 知道继承的概念,对于OOAD知识来说,相当于一个基本概念,从篇幅上看很少。打开一本OOAD(或者具体一些——UML方面的)教科书,假设它有600页,那么继承这个概念占不到一页纸。 --------------------编程问答-------------------- 真心受教了,感谢各位大神!
曾经自学过一段时间C语言,
现在学校学习java和C#,当初转变OOP思想时候看了好多资料才理解什么是面向对象,下面是我的理解

两页纸中间夹张拓印纸,
在第一页纸上画个圆,(父类)
(继承)拓印纸下面一页也会有一个圆,(子类拥有父类所有属性和方法),
但如果在拓印纸的下一页的圆中画条线,

上一页并不能识别,但是上一页可以识别他本身(也就是那个圆)

?不知道这样说对不对
--------------------编程问答--------------------
引用 13 楼 Gozs_cs_dn 的回复:
真心受教了,感谢各位大神!
曾经自学过一段时间C语言,
现在学校学习java和C#,当初转变OOP思想时候看了好多资料才理解什么是面向对象,下面是我的理解

两页纸中间夹张拓印纸,
在第一页纸上画个圆,(父类)
(继承)拓印纸下面一页也会有一个圆,(子类拥有父类所有属性和方法),
但如果在拓印纸的下一页的圆中画条线,

上一页并不能识别,但是上一页可以识别他本身(也就是那个圆)

?不知道这样说对不对


这个例子不太形象,可以看看我那个“鸭子”的例子。。。
补充:.NET技术 ,  C#
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,