2013-05-21 88 views
5

我用C++ 11和工作一個const陣列的STRUCT具有包含下面的結構一類:初始化含有初始化列表

struct Settings{ 
    const std::string name; 

    const std::string* A; 
    const size_t a; 
}; 

class X { 
    static const Settings s; 
    //More stuff 
}; 

.cpp文件I想要定義像這樣

X::s = {"MyName", {"one","two","three"}, 3}; 

但這不起作用。但是,它會利用工作的一箇中間變量

const std::string inter[] = {"one","two","three"}; 
X::s = {"MyName", inter, 3}; 

有沒有辦法做到這一點沒有中間變量?

+3

你的struct *不包含一個const數組。它包含一個指向常量字符串的指針。考慮到這一點,應該很容易明白爲什麼你需要「中間變量」。 – juanchopanza

+0

@juanchopanza:嗯,我想'A'指向const Array的(開始處)。它也可能是一個指向「const std :: string」的指針,但那不是我想要的。但也許我不明白你指的是什麼... – Haatschii

+1

@Haatschii:你混淆了一個事實,即一個數組衰減成一個指針,其數組和指針是相同的。就語言語義而言,數組不是指針。同樣,初始化器列表不是數組。編譯器可以用這樣的列表初始化一個數組,並且它可以將一個數組衰減爲一個指針,但是在您的示例中它不知道將列表轉換爲數組,然後將其衰減爲指針。因此,需要中介,在賦值給指針之前將初始化器列表轉換爲連續數組。 –

回答

5

指針不能從值列表中初始化。你可以使用std::vector代替:

#include <vector> 

struct Settings{ 
    const std::string name; 
    const std::vector<std::string> A; 
//  ^^^^^^^^^^^^^^^^^^^^^^^^ 
    const size_t a; 
}; 

然後,您可以寫:

class X { 
    static const Settings s; 
    //More stuff 
}; 

const Settings X::s = {"MyName", {"one","two","three"}, 3}; 

這裏是一個live example

As suggested by Praetorian in the comments,您可能需要使用std::array更換std::vector,如果它是可以接受的,你要明確指定容器的大小,如果大小並不需要在運行時改變:

#include <array> 

struct Settings{ 
    const std::string name; 
    const std::array<std::string, 3> A; 
//  ^^^^^^^^^^^^^^^^^^^^^^^^^^ 
    const size_t a; 
}; 

這裏是live example

+1

你能解釋爲什麼使用矢量有所作爲? – taocp

+1

@taocp:因爲指針不能用值列表進行初始化。你想要的是可以從初始化列表 –

+3

或'std :: array '初始化的東西,如果你不需要它可以調整大小的話。 – Praetorian

5

這是因爲你正在存儲一個指向字符串數組的指針,而不是字符串本身;所以你需要一個指向某處的字符串數組。你所擁有的是一個包含指向字符數組的指針的括號初始化程序。

如果您要自己存儲字符串(例如,在vector<string>中),則第一個版本可以工作。