2012-01-16 12 views
1

私は私が必要とCの状況++にありますデフォルト/名前空間内の変数のためのカスタム値

1)名前空間の静的定数変数の「デフォルト」値を定義する宣言/オブジェクトモジュール

で定義されているが

2)各「メイン」プログラムは、独自のビルドフォルダとオブジェクトモジュールの独自のコピーを持っているので、「メイン」プログラム

に「カスタム」の値を使用して、いくつかの「メイン」プログラムは、これらの値を「上書き」することができます互いに完全に独立しています:

例えば、

/mainProgramA/build/mainProgramA.o 
/mainProgramA/build/Module.o 
/mainProgramB/build/mainProgramB.o 
/mainProgramB/build/Module.o 

また、いつでも、デフォルト値またはカスタム値のいずれかが定義/宣言されますが、両方ではありません。コンパイラーがカスタム値を「検出」すると、それらが使用されます。そうでない場合は、デフォルト値が使用されます。

名前の衝突を避けるために名前空間が必要なので、私は弱い記号を名前空間に使用できません。私は "エラー:弱い宣言が...公開されていなければならない"ため、名前空間に弱い記号を使用できません。私はおそらくクラスを使用することができますが、すべての値はコンパイル時に認識され、変数ではありません。これを行うための最も単純で最もエレガントな方法は何ですか?明確にする

、私はこのような何かをしようとしている:

DefaultValues.h:

namespace ConfigParams { 
    static const int param1 = 1; 
    static const int param2 = 2; 
} 

CustomValues.h:

namespace ConfigParams { 
    static const int param1 = 100; 
    static const int param2 = 200; 
} 

Module.h:

#include "DefaultValues.h" 
class Module { 
public: 
    static void printParam1(); 
} 

Module.cpp:

#include "Module.h" 

void Module::printParam1() 
{ 
    printf("%d\n", param1); 
} 

mainUsingDefaultValues.cpp(module.oのコピーにリンクする場所PARAM1 == 1):

#include "Module.h" 

... 
Module::printParam1(); // Should print "1" 

mainUsingCustomValues.cpp(module.oここでのコピーにリンクしますPARAM1 == 100):あなたがそれを必要とする場合

#include "CustomValues.h" 
#include "Module.h" 

... 
Module::printParam1(); // Should print "100" 
+0

は 'DefaultValues.h'または' CustomValues.h'、どちらか一方だけを含める:だから、おそらく、それはModule.h#ifdefスイッチを作成し、任意のModule.hが含まれる前に、どこかのユーザー#define MY_CUSTOM_VALUESを作る方が良いでしょう。あなたは違うことができますが、 'CustomValues.h'に' #define'を使って 'Module.h'で定義されているかどうかを確認し、それに基づいて' DefaultValues.h'をインクルードします。 – lapk

+0

@AzzA私はそれをする方法がないと思う。定数をコンパイルし、その絶対アドレスでリンクする必要があります。異なる定数を使用してクラスを2回定義すると、実際のアプリケーションで1つになるはずです。 – Vyktor

+0

@Vyktor私は、カスタム値を指定したときにデフォルト値を除外する方法が問題だと思います。あなたはプリプロセッサでそれを行うことができます...または多分私は誤解しました。あなたがどちらかを選択し、OP作成者がそれを選択する方法を必要とするので、私はそれを理解します。両方を使うことはできません。もちろん、どちらかを含めることができます。 – lapk

答えて

2
// File: CustomValues.h 
#define MY_CUSTOM_VALUES 
namespace ConfigParams 
{ 
static const int param1 = 100; 
static const int param2 = 200; 
} 


// File: DefaultValues.h 
#ifndef MY_CUSTOM_VALUES 
namespace ConfigParams 
{ 
static const int param1 = 1; 
static const int param2 = 2; 
} 
#endif 

あなたはそれをより柔軟にすることができます。

EDIT:質問に誤解されました。この方法では、ライブラリのユーザーは、CustomValues.hの前にModule.hが含まれていない限り、デフォルトでDefaultValues.hになります。あなたはどちらか一方を持つことができますが、両方を持つことはできません。

#include "Module.h" 
#include "CustomValues.h" 

は、定数を再定義するため、コンパイルされません。

さらに、CustomValues.hModule.cppに含める必要があります。

// File: Module.h 
#include "My_Constants.h" // #define MY_CUSTOM_VALUES can go here 
#ifdef MY_CUSTOM_VALUES 
#include "CustomValues.h" 
#elif 
#include "DefaultValues.h" 
#endif 

class Module 
{ 
public: 
    static void printParam1(); 
} 
// End of Module.h 

// File: Module.cpp 
#include "Module.h" 

void Module::printParam1() 
{ 
printf("%d\n", ConfigParams::param1); 
} 
// End of Module.cpp 
+0

私はさまよいます... Staticは、コンパイラとリンカーに、この変数はプログラムの始めに初期化されなければならず、ずっとそこにあるべきだと伝えます。それじゃない?リンカが同じ名前の2つの変数を見ると、静的でも...同じ "絶対アドレスのメモリ"を使うのではないでしょうか? – Vyktor

+0

@Vyktor '#define'は、カスタムが提供されている場合、プリプロセッサがデフォルト定義をバイパスするためのものです。デフォルトのプリプロセッサはプリプロセッサによって取り除かれ、コンパイルされません。 – lapk

+0

私はそれを理解していますが、静的constはグローバルスコープ(リンク後)を持っているため、リンカはそれらをすべて同じ "メモリスポット"に入れようとします。あるいは、externが使われない限り、それらはすべてローカルスコープにありますか? – Vyktor

関連する問題