Overrideをしない場合の同じ名前の関数

解決


ペン  2011-01-26 11:35:29  No: 39908  IP: 192.*.*.*

簡単な質問かもしれませんが、教えてください。

派生クラスで宣言したものが同名の関数だった場合、これは通常?(Override)
すると思いますが、しなかった場合は自動でOverrideしたことになるのでしょうか?

よろしくお願いします。

編集 削除
tor  2011-01-26 13:20:00  No: 39909  IP: 192.*.*.*

ヘルプの「オーバーライドと隠蔽」より
> override を指定しなかった場合は,継承されたメソッドが新しいメソッド宣言によって隠蔽されるだけで,オーバーライドはされません。
具体的にどうなるかもコード例を挙げて説明してあるので読んでみてください。

編集 削除
ペン  2011-01-26 13:52:23  No: 39910  IP: 192.*.*.*

すいません、ヘルプにありませんでした。Delphi7です。
なので、教えてください。。。すいません

1.先ほどの質問
親クラスのPrivateで宣言しているfunction Hogeを子クラスでもfunction Hogeとした場合どうなりますか?

2.新しい質問
この部分を自分で検証していて思ったのですが、同じPas内であれば子クラスから親クラスのPrivateにアクセスできるなんてことありますか?
できてしまっているので、なぜ?と思っています。
何か勘違いしているのでしょうか?

よろしくお願いします。

編集 削除
igy  2011-01-26 14:09:13  No: 39911  IP: 192.*.*.*

>すいません、ヘルプにありませんでした。Delphi7です。

Delphi7のヘルプなら、

目次ページの
Delphi言語リファレンス
+クラスとオブジェクト
  +メソッド
    +メソッドの結合
      +オーバーライドと隠蔽

にあるようです。

編集 削除
ぺん  2011-01-26 14:18:27  No: 39912  IP: 192.*.*.*

igyさんありがとうございます。
では1.の質問に関しては、結局子クラスで同じ名前で宣言した関数は無効になり、Overrideされないということですね。

編集 削除
au  2011-01-26 14:49:20  No: 39913  IP: 192.*.*.*

無効というと語弊があるかと。
virtual、overrideされたメソッド(動的メソッドだったかな)は、変数の型じゃなく変数の実態に合わせたメソッドを呼んでくれるけど、そうじゃないメソッドは、変数の型に従ったメソッドを呼ぶという事かな。

  TTestBase = class
  public
    procedure Method1; virtual;
    procedure Method2; virtual;
  end;

  TTest = class(TTestBase)
  public
    procedure Method1;
    procedure Method2; override;
  end;

procedure TForm1.Button1Click(Sender: TObject);
var
  Obj: TTestBase;
  Obj2: TTest;
begin
  Obj := TTest.Create;
  Obj.Method1;//TTestBaseのMethod1が呼ばれる
  Obj.Method2;//TTestのMethod2が呼ばれる

  Obj2 := TTest.Create;
  Obj2.Method1;//TTestのMethod1が呼ばれる
  Obj2.Method2;//TTestのMethod2が呼ばれる
end;

編集 削除
tor  2011-01-26 14:54:25  No: 39914  IP: 192.*.*.*

ちなみに、やってみるとわかりますが、仮想メソッドを隠蔽すると「本当にこれでいいの?」的な警告が出ます。
「分かっててやっているんだからいちいち警告しなくていいよ」という場合はreintroduceを使います。

>同じPas内であれば子クラスから親クラスのPrivateにアクセスできるなんてことありますか?

ヘルプの「トピックの検索」ウィンドウで「キーワード」タブで
「クラスメンバー」「可視性」が入っているトピックを検索してたどってみてください。例えば以下のような記述が見つかります。

・「private 宣言,protected 宣言,public 宣言,published 宣言」
> private 部は,...プライベートメンバーが宣言されているユニットの中でしかアクセスできません。

・「プライベートメンバー,プロテクトメンバー,パブリックメンバー」
> プライベートメンバーは,それが属するクラスが宣言されているユニットまたはプログラムの外からは見えません。

これは裏を読むと「宣言されているユニット」つまり同一ファイル内であれば
(別に同じクラスでなくても)privateやprotectedメンバにアクセスできるということです。
(これを逆手にとって、自Unit内で標準コンポーネントの派生クラスを宣言して
そのprotectedメンバにアクセスするというのはよく使われるテクニックです)

編集 削除
ペン  2011-01-31 17:13:45  No: 39915  IP: 192.*.*.*

やはり同じユニット内ではPrivateにアクセス可能なんですね。
よくわかりました、みなさんありがとうございます。

またなにかありましたら、よろしくお願いします。

編集 削除