- ベストアンサー
ヘッダオンリーライブラリでプライベートなnamespaceメンバを実現する方法はありますか?
- ヘッダオンリーライブラリでプライベートなnamespaceメンバを実現する方法はありますか?
- 無名名前空間を使用する方法では、Hoge::hogeHelperとしてアクセスできてしまいます。
- ライブラリを書き換えない限り、hogeHelperへのアクセスを禁止する方法はありませんか?
- みんなの回答 (3)
- 専門家の回答
質問者が選んだベストアンサー
まあこの筋だとどうやっても「エラーメッセージがわけわからん」状態になるのは避けられないでしょうねぇ. ソースで #define DO_NOT_USE_AFTERWARD(name) なんか のようなマクロを定義して明確にすれば多少「ごまかし」感は減るけど.... あるいは, いっそあきらめて すべてのメンバーが private かつ static な class を作るとか. たとえば, namespace Hoge { void hoge(); class detail { static void hogeHelper() { } friend void hoge(); }; inline void hoge() { detail::hogeHelper(); } } みたいなイメージ.
その他の回答 (2)
- Tacosan
- ベストアンサー率23% (3656/15482)
手元の g++ で試してみると namespace Hoge{ namespace{ inline void hogeHelper(){} } inline void hoge(){hogeHelper();} namespace{ inline namespace { void hogeHelper(); } } } で (「エラーになる」という意味で) 回避できている感じがします. つまり C++0x ならごまかせるかもしれない. そもそも名前空間が「アクセス制御」を意図しているわけじゃないので, 結局は「ごまかし」の感じが強いですが.
補足
hoge()内では1つめのhogeHelper()を参照しつつ、外からは定義されていない2つめのhogeHelper()を参照させるということですね。 inline namespaceはVC++2010ではエラーになってしまいました。 inlineを外した所、外からも1つめのhogeHelper()を参照してしまったらしく、リンクも通ってしまいました。 ここで、2個目のhogeHelper()をnamespace{namespace{}}から外に出してHoge内にしたところ、hoge()からは無名1つめのhogeHelper()を参照し、外からは2つめのhogeHelper()を参照したようで、みごとにリンクエラーにできました。 これはなかなかスマートな方法です。 さらに、リンクエラーではなくコンパイルエラーにするために、2つめのhogeHelper()を、もはや関数ではなく何でも良いのでnamespaceにしてしまいました。 namespace hogeHelper{} これでHoge::hogeHelperによる関数へのアクセスを完全に禁止できそうです。 ありがとうございました。
- Tacosan
- ベストアンサー率23% (3656/15482)
可能なら #define hogeHelper という技でごまかすとか.
補足
なるほど、そういう手もあるんですね。 回答ありがとうございます。
補足
クラスのprivate staticメンバにしてfriend指定するのは思いつきませんでした。 これならエラーメッセージも理解しやすいです。 namespace Hoge内の他の関数やhoge()内から頻繁に使用される共通処理hogeHelper()を単体で外部から呼び出されたくないだけなので、classのprivate staticメンバで十分目的が果たせます。 namespaceのようにメンバを分割して記述できないことと、class名::を書くことを我慢すれば、namespaceにこだわる必要はないですね。 ありがとうございました。