クラスのメンバ関数のアドレスの取り方 – プログラミング – Home

クラスのメンバ関数のアドレスの取り方
 
通知
すべてクリア

[解決済] クラスのメンバ関数のアドレスの取り方


C++初心者
 C++初心者
(@C 初心者)
ゲスト
結合: 21年前
投稿: 30
Topic starter  

またメンバ関数へのポインタで疑問がでました。
まずはコードを示します。(VC++6.0 + WinXPです)

#include <iostream>

using namespace std;

class B {
void(B::*pfn)(); // 同じクラスのメンバ関数へのポインタ
public:
void f() { cout << B::f() << endl; }

void SetFunction() { pfn = &B::f; } // 非static版
static void SetFunctionStatic(B &me){ me.pfn = &f; } // static版

void Execute() { (this->*pfn)(); } // 関数実行
};

int main()
{
B ob;

ob.SetFunction();
ob.Execute();

B::SetFunctionStatic(ob);
ob.Execute();

return 0;
}

やってる事はクラスのメンバ変数に同じクラスのメンバ関数のアドレスをセットして
実行するという物です。
アドレスをセットするのにSetFunction()という関数を使ってますが、
片方はstaticな関数です。(thisポインタないので同じクラスの参照を渡してます)
非static版は { pfn = &f; } とすると

error C2276: '&' : 仮想関数のアドレスを取ろうとしました。

と出て(仮想関数じゃないのに)コンパイルエラーとなりますが、
static版はエラーが出ません。
てっきりこれはC++の仕様だと思ってプログラム組んでしまったのですが、
BCCだとエラーになってしまいました。
C++の仕様はstatic版にもクラススコープ指定が必要なのでしょうか?

あと、こういうのってどこで調べたらいいのでしょう?
プログラミング言語C++という本にのっているのでしょうか。


引用未解決
トピックタグ
Jojy
 Jojy
(@Jojy)
ゲスト
結合: 21年前
投稿: 7
 

>非static版は { pfn = &f; } とすると
{ pfn = f; } じゃないの?


返信引用
C++初心者
 C++初心者
(@C 初心者)
ゲスト
結合: 21年前
投稿: 30
Topic starter  

どうも違うみたいです。
このページの下の方に以前私が質問した内容でその事にふれています。
実際、BCCだとエラーがでました。


返信引用
επιστημη
 επιστημη
(@επιστημη)
ゲスト
結合: 22年前
投稿: 600
 

&B::f であれば、BCC5.6.4/VC7.1/GCC3.2 のどれでも受理してくれます。


返信引用
aetos
(@aetos)
Noble Member
結合: 6年前
投稿: 1480
 

>&B::f であれば、BCC5.6.4/VC7.1/GCC3.2 のどれでも受理してくれます。
問題はそれが仕様かどうか、じゃないですか?
まぁ、コンパイラ3つも試して全部受理するんだから仕様だと思われますが。
にしても気になりますので…お得意の”召喚”していただけないでしょうか?


返信引用
tetrapod
 tetrapod
(@tetrapod)
ゲスト
結合: 22年前
投稿: 830
 

ぢゃ小寒、ぢゃなくて召喚。
ISO/IEC 14882:1998 5.3.1 Unary operators 3
A pointer to member is only formed when an explicit & is used and
its operand is a qualified-id not enclosed in parentheses.
つまり、静的関数の中だろうがどこだろうが、メンバ関数へのポインタを取るときには
qualified-id が必要、つまり &B::f としなければならない(括弧でくくってはならない)

誤解があるのは
・各インスタンスごとにメンバ関数が生成されるわけではないから、メンバ関数への
 ポインタを取るときには this は不要
・ポインタ経由でメンバ関数を呼び出す場合には、呼び出す先の this が必要。
 それは必ずしも今の this と一致していなくても良い。
ってあたりかも。


返信引用
aetos
(@aetos)
Noble Member
結合: 6年前
投稿: 1480
 

召喚ありがとうございます。
でも、ということは SetFunctionStatic でも本来はスコープ装飾が必要なんでしょう
か?

#俺もIS欲しいなぁ…


返信引用
C++初心者
 C++初心者
(@C 初心者)
ゲスト
結合: 21年前
投稿: 30
Topic starter  

みなさん、ありがとうございます。

・・・プログラム修正します。
クラス名を引数にとる引数付きマクロ定義しようかと思ってますが、
修正箇所、結構あるので憂鬱です。

結局、複数のコンパイラで試してどれかエラーが出たら最大公約数的にプログラム
組むのが無難なのでしょうね。


返信引用
tetrapod
 tetrapod
(@tetrapod)
ゲスト
結合: 22年前
投稿: 830
 

解決した後であれですが、
> ということは SetFunctionStatic でも本来はスコープ装飾が必要なんでしょう
> か?
必要です。って最初からそう書いているつもりですが。

私が見ている ISO/IEC 14882:1998 は既に obsolete で、
今は 2003 になっています。
んで 14882:2003 は邦訳されていて JIS X 3014:2003 として買えます。
¥16500+TAX

http://www.webstore.jsa.or.jp/webstore/Com/FlowControl.jsp?
lang=jp&bunsyoId=JIS+X+3014%3A2003&dantaiCd=JIS&status=1&pageNo=0

最新規格の邦訳、私も買っちゃお、かな?(高いかも)

あっと、ちなみに JIS X3010:2003 は¥13600+TAXです。
閲覧だけなら http://www.jisc.go.jp/ からも可能です。
X3014 の閲覧はできませんでした、残念。


返信引用

返信する

投稿者名

投稿者メールアドレス

タイトル *

プレビュー 0リビジョン 保存しました
共有:
タイトルとURLをコピーしました