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

这些名称是为了让用户知道他们定义了哪些变量。我想让我的程序只读取实际数字并跳过字符串。我知道我可以通过在我的程序中定义大量字符串的方式来做到这一点,然后让它们坐在那里定义但显然未使用。有没有办法在跳过字符串的同时轻松读取数字?

4

5 回答 5

4

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

string param_name;
int param_value;

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

param_name您可以在每次迭代后丢弃它,同时将它存储param_value在您需要的任何地方。

于 2013-02-26T21:27:38.033 回答
3

当您读出字符串时,不要将它们存储在任何地方:

std::vector<int> values;
std::string discard;
int value;
while (file >> discard >> value) {
  values.push_back(value);
}
于 2013-02-26T21:28:26.583 回答
2

我想我一定是逾期发布一个 ctype facet 来忽略字符串并只读取我们关心的数据:

#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;
}

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

于 2013-02-26T23:12:32.267 回答
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);
}

它使用忽略而不是读取字符串而不使用它。

于 2013-02-26T21:39:44.693 回答
0

您可以定义一个结构,然后istream operator>>为它重载:

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);
于 2013-02-26T22:31:30.943 回答