プロパティがおぼろげに分かってきたところで、次はポリモーフィズムを学習したいと思います。
また犬クラス(Dog)を追加しました。動物クラス(Animal)にもあるTalkメソッドを実装しています。
takk@deb9:~/vbtest$ cat -n test.vb
1 Imports System.Console
2
3 Public Class Animal
4 Private _classname As String = "哺乳類"
5 Public ReadOnly Property Classname() As String
6 Get
7 Return _classname
8 End Get
9 End Property
10 Private _name(2) As String
11 Public Property Name(idx As Integer) As String
12 Get
13 Return _name(idx)
14 End Get
15 Set(ByVal value As String)
16 If value <> "" Then
17 _name(idx) = value
18 Else
19 WriteLine("名前をつけてください")
20 End If
21 End Set
22 End Property
23
24 Public Sub Talk()
25 End Sub
26
27 Sub WhatIsThis()
28 WriteLine( _classname & "です" )
29 For Each m As String in _name
30 If m <> Nothing Then
31 WriteLine( "名前は" & m & "と言います" )
32 End If
33 Next
34 End Sub
35 End Class
36
37 Public Class Dog : inherits Animal
38 Public Sub Talk()
39 WriteLine( "『わんわん』" )
40 End Sub
41 End Class
42
43 Public Class TestClass
44 <STAThread()> _
45 Shared Sub Main()
46 Dim dog As New Dog()
47 dog.Name(0) = "シロ"
48 dog.WhatIsThis()
49 dog.Talk()
50 End Sub
51
52 End Class
takk@deb9:~/vbtest$
ビルドして実行すると、
takk@deb9:~/vbtest$ vbnc test.vb ~省略~ takk@deb9:~/vbtest$ mono test.exe 哺乳類です 名前はシロと言います 『わんわん』 takk@deb9:~/vbtest$
問題ないですね。
次は、動物クラスを継承して人間クラスも作りました。
43 Public Class Human : inherits Animal 44 Public Sub Say() 45 WriteLine( "『こんにちは』" ) 46 End Sub 47 End Class
呼び出し部分は、こんな感じ。
49 Public Class TestClass 50 <STAThread()> _ 51 Shared Sub Main() 52 Dim dog As New Dog() 53 dog.Name(0) = "シロ" 54 dog.WhatIsThis() 55 dog.Talk() 56 57 Dim human As New Human() 58 human.Name(0) = "モモ" 59 human.WhatIsThis() 60 human.Talk() 61 End Sub 62 End Class
ビルド、実行。
takk@deb9:~/vbtest$ vbnc test.vb ~省略~ takk@deb9:~/vbtest$ mono test.exe 哺乳類です 名前はシロと言います 『わんわん』 哺乳類です 名前はモモと言います takk@deb9:~/vbtest$
あれ、何かおかしいです。人間が喋ってません。
人間クラスを作るとき、Talkメソッドが、Sayメソッドで実装してしまったのが原因です。Talkメソッドは動物クラスに空のメソッドとして存在するので、何も処理されなかったんですね。
43 Public Class Human : inherits Animal 44 Public Sub Say() 45 WriteLine( "『こんにちは』" ) 46 End Sub 47 End Class
こんな間違いを起こさないために、Talkメソッドを強制的にオーバーライドさせることにします。
動物クラスでTalkメソッドをMustOverrideをつけて抽象化します。End Subは要りません。
23 24 Public MustOverride Sub Talk() 25
サブクラスでは、TalkメソッドにOverridesをつけます。
36 Public Class Dog : inherits Animal 37 Public Overrides Sub Talk() 38 WriteLine( "『わんわん』" ) 39 End Sub 40 End Class 41 42 Public Class Human : inherits Animal 43 Public Overrides Sub Talk() 44 WriteLine( "『こんにちは』" ) 45 End Sub 46 End Class
では、ビルド。
takk@deb9:~/vbtest$ vbnc test.vb Visual Basic.Net Compiler version 0.0.0.5943 (Mono 4.7 - tarball) Copyright (C) 2004-2010 Rolf Bjarne Kvinge. All rights reserved. Assembly 'test, Version=0.0, Culture=neutral, PublicKeyToken=null' saved successfully to '/home/takk/vbtest/test.exe'. Compilation successful Compilation took 00:00:00.5661270 takk@deb9:~/vbtest$
実行します。
takk@deb9:~/vbtest$ mono test.exe Unhandled Exception: System.TypeLoadException: Parent class vtable failed to initialize, due to: Type Animal has invalid vtable method slot 4 with method none assembly:/home/takk/vbtest/test.exe type:Animal member:(null) [ERROR] FATAL UNHANDLED EXCEPTION: System.TypeLoadException: Parent class vtable failed to initialize, due to: Type Animal has invalid vtable method slot 4 with method none assembly:/home/takk/vbtest/test.exe type:Animal member:(null) takk@deb9:~/vbtest$
なんてことでしょう。実行エラー。
そういえば、動物クラスに、MustInheritをつけるのを忘れてました。
3 Public MustInherit Class Animal
4 Private _classname As String = "哺乳類"
5 Public ReadOnly Property Classname() As String
6 Get
7 Return _classname
8
~省略~
これでOKのハズです。
ビルド、実行。
takk@deb9:~/vbtest$ vbnc test.vb ~省略~ takk@deb9:~/vbtest$ mono test.exe 哺乳類です 名前はシロと言います 『わんわん』 哺乳類です 名前はモモと言います 『こんにちは』 takk@deb9:~/vbtest$
動きました。



コメント