分享
 
 
 

VB.Net中文教程(3) 继承与封装性

王朝vb·作者佚名  2006-01-08
窄屏简体版  字體: |||超大  

请注意 ......

著作权所有人:物泽计算机事业股份有限公司、

MISOO对象技术顾问团队、对象导向杂志作者、等。

u本文件摘自 对象导向杂志、精通对象观念与技术等书籍著作。

u本文件仅供您的参阅,请遵守著作权法,不得做其它商业用途。

主题: 继承与封装性

?????????? 内容 ??????????

v 1. 继承与封藏性

1. 继承与封装性(Encapsulation)

1.1 公用与私有数据

前面已介绍「封藏性」(Encapsulation) 之观念。即是﹕类别内所定义之资料成员﹐只限于程序成员才能存取之。现在所面临之问题为﹕子类别能否直接存取父类别之资料呢﹖就如同﹕儿女从父母亲继承了财产﹐但能否取用或卖掉继承而来的财产呢﹖如果可以﹐显然违背了「封藏性」之理想。如果不行﹐显然带给程序员莫大之限制。理论上﹐百分之百的封藏性最为完美﹔但应用上﹐若给予子类别若干优待﹐能提高程序之弹性及效率。为了解决此鱼与熊掌不可兼得之困境﹐VB提供三种选择﹕

(1) Public ──指定某些数据为公用的﹐任何程序皆可直接取用之﹔此时并无任何封藏作用。

(2) Protected ──指定某些资料为家族公用﹐亦即只有子孙类别内之程序可取用﹐非子孙类别之程序必须呼叫家族内之程序代为存取。

(3) Private ──指定某资料为类别私有﹐只限于该类别之程序才可取用。子类别之程序也必须呼叫父类别之程序代为存取﹐此时具百分之百封藏性。

先前介绍「封装性」基本概念时,您已经认识了Public和Private的用意了,至于Protected则配合继承来使用,于是在此特别强调它。

由于VB向现实妥协﹐开了方便之门﹐无百分之百封藏性﹔所以有些人认为 VB并非完美的 OOP语言。您认为如何呢﹖请看个程序﹕

'ex01.bas

Imports System.ComponentModel

Imports System.Drawing

Imports System.WinForms

'---------------------------------------------------------

Class Person

Private name As String

Public age As Integer

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

End Class

Class Teacher

Inherits Person

Public salary As Single

Public Sub New(ByVal na As String, ByVal a As Integer, ByVal sa As Single)

MyBase.New(na, a)

salary = sa

End Sub

Public Sub modifyAge(ByVal a As Integer)

age = a

End Sub

End Class

'--------------------------------------------------------

Public Class Form1

Inherits System.WinForms.Form

Public Sub New()

MyBase.New()

Form1 = Me

'This call is required by the Win Form Designer.

InitializeComponent()

'TODO: Add any initialization after the InitializeComponent() call

End Sub

'Form overrides dispose to clean up the component list.

Public Overrides Sub Dispose()

MyBase.Dispose()

components.Dispose()

End Sub

#Region " Windows Form Designer generated code "

.......

#End Region

Protected Sub Form1_Click( ByVal sender As Object,

ByVal e As System.EventArgs)

Dim crag As New Teacher("Crag", 38, 45000)

crag.modifyAge(42)

MessageBox.Show( "AGE: " + str(crag.age) + ", SALARY: "

+ str(crag.salary))

End Sub

End Class

此程序输出如下﹕

AGE: 42 SALARY: 45000

Person之age资料成员定义为 Public﹐表示 age为公用数据﹐任何程序皆可存取之。因之﹐Teacher 之 modifyAge()可使用age这名称。相对地﹐于 Teacher类别中﹐就不得使用name这名称﹐因为name定义为Privatec﹐表示name为Person类别之私有资料。再看Teacher类别之salary资料﹐它定义为Public﹐表示公用之意。所以Form1_Click()可直接使用 crag.salary格式取得salary之值。然而﹐不能写成﹕crag.name ﹐因为name为私有资料。例如,下述程序是不对的:

'ex02.bas

'Some Error Here!

Imports System.ComponentModel

Imports System.Drawing

Imports System.WinForms

'---------------------------------------------------------

Class Person

Private name As String

Public age As Integer

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

End Class

Class Teacher

Inherits Person

Public salary As Single

Public Sub New(ByVal na As String, ByVal a As Integer, ByVal sa As Single)

MyBase.New(na, a)

salary = sa

End Sub

Public Sub modifyName(ByVal na As String)

name = na 'Error Here!

End Sub

End Class

'--------------------------------------------------------

Public Class Form1

Inherits System.WinForms.Form

Public Sub New()

MyBase.New()

Form1 = Me

'This call is required by the Win Form Designer.

InitializeComponent()

'TODO: Add any initialization after the InitializeComponent() call

End Sub

'Form overrides dispose to clean up the component list.

Public Overrides Sub Dispose()

MyBase.Dispose()

components.Dispose()

End Sub

#Region " Windows Form Designer generated code "

.......

#End Region

Protected Sub Form1_Click( ByVal sender As Object,

ByVal e As System.EventArgs)

Dim crag As New Teacher("Crag", 38, 45000)

crag.modifyName("Crag Clinton")

MessageBox.Show( "AGE: " + str(crag.age) + ", SALARY: "

+ str(crag.salary))

End Sub

End Class

因为name是Person类别的私有资料,在子类别Teacher的modifyName()里不能使用此资料名称,所以错了。如果将Person类别定义为﹕

'ex03.bas

Imports System.ComponentModel

Imports System.Drawing

Imports System.WinForms

'---------------------------------------------------------

Class Person

Protected name As String

Public age As Integer

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

Public Function GetName() As String

GetName = name

End Function

End Class

Class Teacher

Inherits Person

Public salary As Single

Public Sub New(ByVal na As String, ByVal a As Integer, ByVal sa As Single)

MyBase.New(na, a)

salary = sa

End Sub

Public Sub modifyName(ByVal na As String)

name = na

End Sub

End Class

'--------------------------------------------------------

Public Class Form1

Inherits System.WinForms.Form

Public Sub New()

MyBase.New()

Form1 = Me

'This call is required by the Win Form Designer.

InitializeComponent()

'TODO: Add any initialization after the InitializeComponent() call

End Sub

'Form overrides dispose to clean up the component list.

Public Overrides Sub Dispose()

MyBase.Dispose()

components.Dispose()

End Sub

#Region " Windows Form Designer generated code "

......

#End Region

Protected Sub Form1_Click( ByVal sender As Object,

ByVal e As System.EventArgs)

Dim crag As New Teacher("Crag", 38, 45000)

crag.modifyName("Crag Clinton")

MessageBox.Show( "AGE: " + str(crag.age) + ", NAME: "

+ crag.GetName())

End Sub

End Class

此程序输出:

AGE: 42, NAME: Crag Clinton

此时﹐name为家族公用之资料﹐凡是Person之子孙类别皆可取用之。但家族外之程序(如 Form1_Click()程序)仍不得直接使用之。如果上述定义改为﹕

Class Person

Protected name As String

Private salary As Decimal

Public age As Integer

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

End Class

此时﹐salary为类别私有﹐其它类别不得使用。name为家族私有﹐家族外之类别不得使用。age为公用﹐任何类别皆可用。

1.2 公用与私有程序

上节介绍过﹕资料成员有 Private、Protected 及Public之分。同样地﹐程序成员也可分为 Private、Protected 及Public。虽然在应用上﹐程序成员大多定义为Public﹐但必要时﹐也能将过程定义为Private 或 Protected。私有程序和私有资料一样﹐只限于该类别之程序才能呼叫它。例如﹕

'ex04.bas

Imports System.ComponentModel

Imports System.Drawing

Imports System.WinForms

'----------------------------------------------------------------------

Class Person

Private name As String

Private age As Integer

Private Sub modifyAge(ByVal a As Integer)

age = a

End Sub

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

Public Sub modify(ByVal na As String, ByVal a As Integer)

name = na

modifyAge(a)

End Sub

Public Sub Show()

Messagebox.Show("Name: " + name + " Age: " + str(age))

End Sub

End Class

'-------------------------------------------------------------------

Public Class Form1

Inherits System.WinForms.Form

Public Sub New()

MyBase.New()

Form1 = Me

'This call is required by the Win Form Designer.

InitializeComponent()

'TODO: Add any initialization after the InitializeComponent() call

End Sub

'Form overrides dispose to clean up the component list.

Public Overrides Sub Dispose()

MyBase.Dispose()

components.Dispose()

End Sub

#Region " Windows Form Designer generated code "

.......

#End Region

Protected Sub Form1_Click( ByVal sender As Object,

ByVal e As System.EventArgs)

Dim p1 As New Person("David", 25)

p1.Show()

p1.modify("David Smith", 28)

p1.Show()

End Sub

End Class

此程序输出:

Name: David Age: 25

Name: David Smith Age: 45

modifyAge()为私有程序﹐New()及modify()为公用程序。modifyAge()为Person类别之程序成员﹐所以modify()能呼叫modifyAge()。Person类别外之函数不能呼叫modifyAge()。例如﹕在Form1_Click()中﹐可写着 p1.modify()﹐因为modify()为公用程序。但于Form1_Click()内﹐就不可写着 p1.modifyAge()﹐因为modifyAge()为 Private函数。如果放宽对modifyAge()之限制﹐使Person之子类别能呼叫modifyAge()﹐就须定义modifyAge()为 Protected函数﹐如下﹕

'ex05.bas

Imports System.ComponentModel

Imports System.Drawing

Imports System.WinForms

'----------------------------------------------------------------------

Class Person

Protected name As String

Private age As Integer

Protected Sub modifyAge(ByVal a As Integer)

age = a

End Sub

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

Public Sub Show()

Messagebox.Show("Name: " + name + " Age: " + str(age))

End Sub

End Class

Class Teacher

Inherits Person

Public Sub New(ByVal na As String, ByVal a As Integer)

MyBase.New(na, a)

End Sub

Public Sub modify(ByVal na As String, ByVal a As Integer)

MyBase.name = na

MyBase.modifyAge(a)

End Sub

End Class

'-------------------------------------------------------------------

Public Class Form1

Inherits System.WinForms.Form

Public Sub New()

MyBase.New()

Form1 = Me

'This call is required by the Win Form Designer.

InitializeComponent()

'TODO: Add any initialization after the InitializeComponent() call

End Sub

'Form overrides dispose to clean up the component list.

Public Overrides Sub Dispose()

MyBase.Dispose()

components.Dispose()

End Sub

#Region " Windows Form Designer generated code "

......

#End Region

Protected Sub Form1_Click( ByVal sender As Object,

ByVal e As System.EventArgs)

Dim p1 As New Teacher("David", 25)

p1.Show()

p1.modify("Kent Smith", 45)

p1.Show()

End Sub

End Class

此程序输出:

Name: David Age: 25

Name: Kent Smith Age: 45

此时﹐子孙类别之函数能呼叫modifyAge()﹐但家族外之类别仍不可呼叫它。总结归纳为简单规则﹕

◎如果允许任何类别使用﹐就宣告为Public。

◎如果允许子类别使用﹐就宣告为Protected 。

◎如果允许本类别使用﹐就宣告为Private 。

请在看个例子:

'ex06.bas

Imports System.ComponentModel

Imports System.Drawing

Imports System.WinForms

'----------------------------------------------------------------------

Class Person

Protected name As String

Private age As Integer

Protected Sub modifyAge(ByVal a As Integer)

age = a

End Sub

Public Sub New(ByVal na As String, ByVal a As Integer)

name = na

age = a

End Sub

Public Sub Show()

Messagebox.Show("Name: " + name + " Age: " + str(age))

End Sub

End Class

Class Teacher

Inherits Person

Public Sub New(ByVal na As String, ByVal a As Integer)

MyBase.New(na, a)

End Sub

Protected Sub modify(ByVal na As String, ByVal a As Integer)

MyBase.name = na

MyBase.modifyAge(a)

End Sub

End Class

Class FullTime_Teacher

Inherits Teacher

Public Sub New(ByVal na As String, ByVal a As Integer)

MyBase.New(na, a)

End Sub

Public Sub modifyValue(ByVal na As String, ByVal a As Integer)

MyBase.modify(na, a)

End Sub

Public Sub modifyData(ByVal na As String, ByVal a As Integer)

MyBase.name = na

MyBase.modifyAge(a)

End Sub

End Class

'-------------------------------------------------------------------

Public Class Form1

Inherits System.WinForms.Form

Public Sub New()

MyBase.New()

Form1 = Me

'This call is required by the Win Form Designer.

InitializeComponent()

'TODO: Add any initialization after the InitializeComponent() call

End Sub

'Form overrides dispose to clean up the component list.

Public Overrides Sub Dispose()

MyBase.Dispose()

components.Dispose()

End Sub

#Region " Windows Form Designer generated code "

.......

#End Region

Protected Sub Form1_Click( ByVal sender As Object,

ByVal e As System.EventArgs)

Dim p1 As New FullTime_Teacher("David", 25)

p1.Show()

p1.modifyValue("Kent Smith", 45)

p1.Show()

End Sub

End Class

此程序输出:

Name: David Age: 25

Name: Kent Smith Age: 45

Show()是Person类别的Public程序,孙子类别FullTime_Teacher继承之,成为FullTime_Teacher类别的Public程序,所以Form1_Click()程序能写着指令:p1.Show()。name和modifyAge()是Person的Protected成员,Teacher的modify()程序里能直接使用它们。而且FullTime_Teacher的modifyData()程序里能直接使用它们。但是Form1_Click()就无法使用它们。modify()是Teacher的Protected成员,FullTime_Teacher的modifyValue()程序里能直接使用它们,但Form1_Click()就不行使用。所以若将上述Form1_Click()的指令改为如下,就不对了:

Protected Sub Form1_Click( ..... )

Dim p1 As New FullTime_Teacher("David", 25)

p1.Show()

p1.modify("Kent Smith", 45) 'Error!

p1.modifyAge(24) 'Error!

p1.Show()

End SubEnd Class

n

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有