2013-02-26 150 views
0

我试图确定读取配置文件的最佳方式。这种“Parameters.cfg”文件就是定义值,是这种形式的:从配置文件读取变量

origin_uniform_distribution 0 
origin_defined 1 
angles_gaussian 0 
angles_uniform_distribution 0 
angles_defined 0 
startx 0 
starty 0 
gap 500 
nevents 1000 
origin_uniform_distribution_x_min -5 
origin_uniform_distribution_x_max 5 
origin_uniform_distribution_y_min -5 
origin_uniform_distribution_y_max 5 
origin_defined_x 0 
origin_defined_y 0 
angles_gaussian_center 0 
angles_gaussian_sigma 5 
angles_uniform_distribution_x_min -5 
angles_uniform_distribution_x_max 5 
angles_uniform_distribution_y_min -5 
angles_uniform_distribution_y_max 5 
angles_defined_x 10 
angles_defined_y 10 

的名称是有用户知道他们正在定义的变量。我想让我的程序只读取实际的数字并跳过字符串。我知道我可以在我的程序中定义一大堆字符串,然后让它们坐在那里定义但显然未被使用。有没有办法在跳过字符串时轻松读取数字?

+1

没有重新发明轮子的点:http://sourceforge.net/projects/libini/或http://sourceforge.net/projects/libconfig/ – 2013-02-26 21:27:08

+0

这是一个你正在使用的现有配置文件,或者你可以重新设计配置文件? – JBentley 2013-02-26 21:28:01

+0

它可以重新设计。 – ddavis 2013-02-26 21:35:22

回答

1

此方法不串存储在所有(被要求在问题等):

static const std::streamsize max = std::numeric_limits<std::streamsize>::max(); 
std::vector<int> values; 
int value; 

while(file.ignore(max, ' ') >> file >> value) 
{ 
    values.push_back(value); 
} 

它使用ignore而不是读取字符串,也不使用它。

+0

+1正是为了完成问题所说的内容,但我认为代码不如使用临时字符串变量的替代方法更清晰。 – us2012 2013-02-26 21:44:29

+0

@ us2012我同意:) – David 2013-02-26 21:45:39

+0

是的,感谢所有人的所有可用选项:) – ddavis 2013-02-26 21:47:42

4

显而易见的解决方案有什么问题?

string param_name; 
int param_value; 

while (fin >> param_name >> param_value) 
{ 
    .. 
} 

你可以在每次迭代后丢弃param_name同时存储在任何需要它的param_value

3

当你读出的字符串,只是不把它们存储在任何地方:

std::vector<int> values; 
std::string discard; 
int value; 
while (file >> discard >> value) { 
    values.push_back(value); 
} 
0

您可以定义一个结构,然后超载istreamoperator>>吧:

struct ParameterDiscardingName { 
    int value; 
    operator int() const { 
     return value; 
    } 
}; 
istream& operator>>(istream& is, ParameterDiscardingName& param) { 
    std::string discard; 
    return is >> discard >> param.value; 
} 

ifstream file("Parameters.cfg"); 
istream_iterator<ParameterDiscardingName> begin(file), end; 
vector<int> parameters(begin, end); 
2

我想我一定是过期张贴ctype方面忽略字符串和只读,我们关心的数据:

#include <locale> 
#include <fstream> 
#include <vector> 
#include <iostream> 
#include <algorithm> 
#include <iterator> 

struct number_only: std::ctype<char> { 
    number_only() : std::ctype<char>(get_table()) {} 

    static mask const *get_table() { 
     static std::vector<mask> rc(table_size, space); 

     std::fill_n(&rc['0'], 10, digit); 
     rc['-'] = punct; 
     return &rc[0]; 
    } 
}; 

int main() { 
    // open the file 
    std::ifstream x("config.txt"); 

    // have the file use our ctype facet: 
    x.imbue(std::locale(std::locale(), new number_only)); 

    // initialize vector from the numbers in the file: 
    std::vector<int> numbers((std::istream_iterator<int>(x)), 
           std::istream_iterator<int>()); 

    // display what we read: 
    std::copy(numbers.begin(), numbers.end(), 
     std::ostream_iterator<int>(std::cout, "\n")); 

    return 0; 
} 

这样,无关的数据真的被真正地忽略了 - 在用我们的方面注入流之后,就好像字符串根本不存在。

+0

这封装行为,给它一个名称,并且是可重用的,而接受的解决方案需要重复每次你想要做到这一点,必须阅读才能被理解。此外,这适用于任何容器构造函数或迭代器算法。在我看来,这好得多。 – 2013-02-27 08:29:33