2016-05-16 16 views
2

私はスレッドセーフなシングルトンを実装しています。しかし、この側面(シングルトン&スレッドセーフ)は私の質問の一部ではありません。C++シングルトン、奇妙なエラー

2つのコードを比較してください。コード1:

#include <iostream> 
using namespace std; 
class DataLocation { 
private: 
    DataLocation(std::string) { 
    } 
public: 
    DataLocation& getInstance() { 
    std::string s = " "; 
    static DataLocation instance(s); 
    return instance; 
    } 
}; 
int main() { 
} 

とコード2:

#include <iostream> 
using namespace std; 
class DataLocation { 
private: 
    DataLocation() { 
    } 
public: 
    DataLocation& getInstance() { 
    static DataLocation instance();  
    return instance; 
    } 
}; 
int main() { 
} 

コード1罰金コンパイルします。唯一の違いは、プライベートコンストラクタはそれぞれ、ゼロのパラメータを1持っていることである私の視点から

15_singleton.cpp: In member function ‘DataLocation& DataLocation::getInstance()’: 
15_singleton.cpp:15:34: error: cannot declare static function inside another function 
    static DataLocation instance();  
           ^
15_singleton.cpp:16:12: error: invalid initialization of non-const reference of type ‘DataLocation&’ from an rvalue of type ‘DataLocation (*)()’ 
    return instance; 
      ^

:コード2には、次のエラーが発生します。

コンパイラが私が新しいものを定義していないことを理解するにはどうすればよいですか?コンストラクタを呼び出すだけですか?コンパイラは、1つのパラメータがある場合、それを理解することができます。

+2

または中括弧を使用してください。 – MikeMB

+1

スレッドセーフな部分については、C++で初期化の時間と静的順序を保証します。 – deviantfan

+0

@MikeMB:_use中括弧ではどういう意味ですか? – LiPo

答えて

5

デフォルトコンストラクタでインスタンスを作成するには、ブラケット

static DataLocation instance; 

を削除します。

または、初期設定の中括弧を使用してください。

static DataLocation instance {}; 
+0

@LiPoこれは完全に論理的です。 MVPはよく定義された言語ルールです。 –

+2

が明確に定義されている必要はありません。 1つのパラメータ:foo(param)、パラメータfoo()はありません。それは私の論理です。私たちはすべて異なっており、私たちは異なるロジックを持っています – LiPo

1

getInstance()は静的として宣言する必要があります。

+0

私は静的な定義もしますが、私はこの[モデル](http://stackoverflow.com/a/19907903)を使用し、モデルは+33 ...初心者 – LiPo

+0

@ニオール:あいまいさはありません。いくつかのサプライズ?確かに。しかし定義上、あいまいさはありません。ところで、最も厄介な構文解析は 'A(B());'に関連しています。これは、間違った宣言子構文を使用した後の初心者の驚きと同じ言語ルールによって引き起こされます。 –

+1

@LiPo:私はdownvoteしませんでしたが、Radekは正しいのですが、質問には答えません。 – MikeMB

2
static DataLocation instance = DataLocation(); 

または

static DataLocation instance; 

そして、あなたはおそらくstatic方法としてDataLocation& getInstance();宣言するとよいでしょう。オブジェクトとして作成する

static DataLocation instance(); 

あなたの意図を宣言しながら、

+4

なぜ最初のバージョンが必要かわかりません。特にシングルトンの場合、コピーコンストラクタを無効にして、最初のバージョンをコンパイルしないようにします。 – Galik

2

あなたはカッコ()を使用しています。しかし、単に関数宣言です。また、static以外の機能の中にstatic関数を作成することはできません。それはあなたのエラーが参照しているものです。