さて、
今回ふれますのは
インクルードの色々な使い方です。
普通にヘッダをインクルード
するだけなら、多分たくさんの人がやったことあるんじゃないかなと思います。
Visual Studioに登録されているヘッダなら
#include<~~.h>
自作のヘッダなら
#include"~~.h"
みたいな感じです。
インライン関数を使っている方なら
#include "~~.inl"
みたいなのを書いてる方も多いかもしれません
本来このinlファイルは、コンパイル上、
hファイルと何ら変わりありません
インライン関数の実体をまとめて置いておく際に
hファイルだと、命名の重複の可能性があったり、
クラスヘッダ等との、見分けが難しいためです。
このinlファイルを使ったテクニックとして、
「クラスのメンバ関数の隠ぺいをする」という物があります。
(※Visual Studio 2008でのみ確認)
中村君のオブジェクト指向セミナーが以前ありましたが、
カプセル化の概念上、
1つのクラスには
プライベートなメンバが多く存在する場合があります。
内部的には使用していますが、外部からすると、まったく関係のない個所です。
なのに、Visual Studioは予測表示等で、外部からこいつらを閲覧させちゃってくれます。
これは邪魔なので隠しちゃいましょう。
main.cpp
class Test{
#Include "PriveInl.inl"
public:
int PublicMember0;
int PublicMember1;
int PublicMember2;
};
int main(){
Test a;
}
|
ソース内に
#include "PrivInl.inl"
と書いてやります。
PriveInl.inl
private:
int PrivateMember0;
int PrivateMember1;
int PrivateMember2;
|
PrivInl.inlの中に、プライベートメンバを書いてやります。
すると…
なんと、予測リストから消えました!
ある程度、完成したクラスなら、
このようにしてプライベートメンバを、隠ぺいし、使いやすくしてやるのもいいかもしれません。
また、
インクルードをうまく使い、
テンプレート関数をもったクラスのメンバをcppに書く
という方法があります。
テンプレート関数は、インラインでなければ、定義することができません。
そのために、inlファイルがあるわけですが、
これをcppに書いてやりましょう。
Test.h
#pragma once //これがないとcppの中身が無効なソースになる
#ifndef TEST_INC
#define TEST_INC
class Test{
public:
template< class T >
T Func ( T Val );
};
#include "Test.cpp"
#endif
|
Test.cpp
#ifdef TEST_INC //インクルードされていなければ無視する
template < class T >
T Test::Func( T Val ){
return Val;
}
#endif
|
ヘッダ側でcppをインクルードしています。
また、cppが、
ヘッダより先にコンパイルにかけられる可能性があるので
ヘッダ側のインクルードガードを流用し、コンパイルガードをしています。
このようにすることで、テンプレートなどのインライン関数の実体をcpp側に書くことができます。
どうでしょう
たかがインクルードといえども、
他にも色々な使い方があるかもしれません。
何か、いいアイディアがありましたら、教えてください!!
そ~れ~で~は~(*´∀`)ノ
追記:
メンバの隠ぺいはVisual Studio 2010ではできないようです。
インテリセンスに大幅な変更があったためだそうです。
PR
COMMENT
No Title
すべての.cppをコンパイルしないで
すべての.cppをインクルードしたファイルを一つだけ用意
してそれをコンパイルすると、最小限のincludeで済むので
コンパイルがはやーくなるらしい
元ネタ「http://d.hatena.ne.jp/melpon/20101022/1287705842」