【发布时间】:2013-09-29 00:01:06
【问题描述】:
scanf 允许跳过匹配的标记,只需将* 添加到模式中,如下所示:
int first, second;
scanf("%d %*s %d", &first, &second);
有没有与std::cin 等效的方法?类似的东西(当然,不使用其他变量):
int first, second;
std::cin >> first >> `std::skip` >> second;
【问题讨论】:
scanf 允许跳过匹配的标记,只需将* 添加到模式中,如下所示:
int first, second;
scanf("%d %*s %d", &first, &second);
有没有与std::cin 等效的方法?类似的东西(当然,不使用其他变量):
int first, second;
std::cin >> first >> `std::skip` >> second;
【问题讨论】:
C++ 中的输入流做同样的事情可不是一件简单的事情。函数scanf 获取所有预期格式:"%d %*s %d",并且可以提前确定发生了什么。
另一方面,运营商>> 只是试图满足当前的入口参数。
您有机会编写自己的 istream 操纵器来吃输入,直到达到一个数字。
试试这个我的幼稚代码:
template<typename C, typename T>
basic_istream<C, T>&
eat_until_digit(basic_istream<C, T>& in)
{
const ctype<C>& ct = use_facet <ctype<C>> (in.getloc());
basic_streambuf<C, T>* sb = in.rdbuf();
int c = sb->sgetc();
while (c != T::eof() && !ct.is(ctype_base::digit, c))
c = sb->snextc();
if (c == T::eof())
in.setstate(ios_base::eofbit);
return in;
}
int main()
{
int first, second;
cin >> first >> eat_until_digit >> second;
cout << first << " : " << second << endl;
}
你可以扩展和改进上面的代码来实现你所需要的。
【讨论】:
std::ios::skip::str、std::ios::skip::dec,甚至std::ios::skip::any?太乱了? (:
std::ctype::scan_is 不这样做吗?
scan_is 对于查找掩码很有用,并且可以在内部上述函数中使用,因为 OP 需要一个 IO 操纵器来使用像 cin >> eat_until_digit 这样的输入
您可能正在寻找C++ String Toolkit Library。
查看更多example
或者你可以试试ignore这样的函数:
std::cin >> val1;
std::cin.ignore (1234, ' ');
std::cin >> val3;
类似这样的:-
template <class charT, class traits>
inline std::basic_istream<charT, traits> &
ignoreToken (std::basic_istream<charT, traits> &strm)
{
strm.ignore (1234, ' ');
return strm;
}
然后使用like:
cin >> val1 >> ignoreToken >> val3 >> ignoreToken >> val5;
【讨论】:
std::ios::skip::str 和 std::ios::skip::dec 甚至 std::ios::skip::any 会非常好(:
你可以简单地使用一个虚拟变量
int first, second;
std::string dummy;
cin >> first >> dummy >> second;
但没有直接等效的 AFAIK。
【讨论】: