使用cin以特定格式阅读
Reading in a specific format with cin
如何使用cin以特定格式读取?示例:-为了读取复数,我希望用户像往常一样输入:x+yi,所以我想要这样的东西:cin>>x>>"+">>y>>"i";但这是一个错误。什么是正确的方法?非常感谢您的帮助。
一个非常简单的解决方案:
char plus,img;
double x,y;
cin>> x >> plus >> y >> img;
if (plus!='+' || img!='i') ...error
在"现实生活"代码中,您构建/使用class complex
,并重载运算符>>.
我在Ideone尝试:http://ideone.com/ZhSprF
#include <iostream>
using namespace std;
int main()
{
char plus{},img{};
double x{},y{};
cin>> x >> plus >> y >> img;
if (plus!='+' || img!='i')
cout << "nError: "<< "x=" << x <<", plus=" << plus <<", y=" << y <<", img=" << img;
else
cout << "nComplex: " << x << plus << y << img;
return 0;
}
stdin:3 + 4i
-->stdout:Complex: 3+4i
stdin:1E4L1e3g
-->stdout:Error: x=10000, plus=L, y=1000, img=g
stdin:a+3i
-->stdout:Error: x=0, plus=, y=0, img=
stdin:1e3+93E-2i
-->stdout:Complex: 1000+0.93i
根据我对一个模糊相关问题的回答,使用流解析通常是个坏主意,但可以做到:
我写了一些可以读取字符串和字符文字的代码。与正常的流读取一样,如果它获得无效数据,它会设置流的坏比特。这应该适用于所有类型的流,包括宽流。将以下四个功能粘贴在标题中:
#include <iostream>
#include <string>
#include <array>
#include <cstring>
template<class e, class t, int N>
std::basic_istream<e,t>& operator>>(std::basic_istream<e,t>& in, const e(&literal)[N]) {
std::array<e, N-1> buffer; //get buffer
in >> buffer[0]; //skips whitespace
if (N>2)
in.read(&buffer[1], N-2); //read the rest
if (strncmp(&buffer[0], literal, N-1)) //if it failed
in.setstate(in.rdstate() | std::ios::badbit); //set the state
return in;
}
template<class e, class t>
std::basic_istream<e,t>& operator>>(std::basic_istream<e,t>& in, const e& literal) {
e buffer; //get buffer
in >> buffer; //read data
if (buffer != literal) //if it failed
in.setstate(in.rdstate() | std::ios::badbit); //set the state
return in;
}
//redirect mutable char arrays to their normal function
template<class e, class t, int N>
std::basic_istream<e,t>& operator>>(std::basic_istream<e,t>& in, e(&carray)[N]) {
return std::operator>>(in, carray);
}
它将使输入字符变得非常容易:
if (cin>>x>>"+">>y>>"i";) {
// read correctly
}
概念验证。现在,您可以cin
字符串和字符文字,如果输入不完全匹配,它的行为就像任何其他未能正确输入的类型一样。请注意,这只匹配不是第一个字符的字符串文字中的空白。它只有三个功能,所有这些功能都非常简单。
最好只使用std::complex
。
下面是一个伪代码,说明了我的评论:
struct Complex { double real, imag; }
istream& operator>> (Complex& c, istream& str)
{
// read until whitespace
char C;
string Buffer;
enum { READING_REAL, READING_PLUS, READING_IMAG }
State = READING_REAL;
C = str.peek();
while (/* C is not whitespace */)
{
// actually read C
switch(State) {
case READ_REAL:
// check if it fits allowed double syntax
// continue until first double is read
/* when it is
c.real = parsedouble(Buffer);
Buffer.clear();
State = READ_PLUS;
*/
case READ_PLUS:
// accept plus sign
case READ_IMAG:
// read 2nd double
}
}
}
请注意,此操作可能会失败。
相关文章:
- 如何在openssl-ecc中获取十六进制格式的私钥
- 将"打开的CV图像"中的"颜色"转换为整数格式
- TDateTime格式在C++Builder中不会更改
- 如何防止clang格式在流运算符调用之间添加换行符<<
- 检查不带转换的扫描格式
- 当我尝试使用 sstream 和分面将 Boost Time_duration转换为字符串时,我没有得到所需的格式
- 是否可以从格式字符串中检索"width"
- clang格式:宏的缩进
- clang格式:禁用排序包含
- 在用于格式4的arm模拟器中实现功能时的一个问题
- 将RGB图像保存为PPM格式
- 询问在设计我的手臂模拟器功能表示格式1
- 当使用比格式支持的精度更高的精度来显示数字时,会写出什么数据
- 带有Protobuf序列化的C++Hazelcast:字符串不是UTF-8格式的
- 如何将strftime中的格式错误作为异常捕获
- 将CHW格式的浮点向量转换为cv::Mat
- 如何将二进制格式的 C++ 对象的 std::vector 保存到磁盘?
- 如何以叮当格式设置评论的行长?
- 为什么我需要C++中不同的排序格式来对这个USACO代码上的数组和优先级队列进行排序
- Vulkan 中的动态顶点缓冲区格式设置