C++ C++;使用struct作为某种类型
假设我有这个结构:C++ C++;使用struct作为某种类型,c++,struct,C++,Struct,假设我有这个结构: struct shape{ int type; shape(){} shape(int _type){type = _type;} }; 可以直接将shape用作int吗?在这种情况下,shape将采用其类型的值。例如: shape s(2); if (s == 1) cout<<"this shape is a circle"<<endl; else if(s == 2) cout<<"this shap
struct shape{
int type;
shape(){}
shape(int _type){type = _type;}
};
可以直接将shape用作int吗?在这种情况下,shape将采用其类型的值。例如:
shape s(2);
if (s == 1) cout<<"this shape is a circle"<<endl;
else if(s == 2) cout<<"this shape is a triangle"<<endl;
else if(s == 3) cout<<"this shape is a rectangle"<<endl;
//...
当我写作的时候
shape s1("circle");
string s2 = "circle";
if(s1 == s2){ ...
它显示错误:与“operator==”不匹配(操作数类型为“shape”和“std::string”),尽管使用int作为类型,它工作正常。您可以添加
运算符int
:
struct shape{
int type;
shape(){}
shape(int _type) : type(_type) {}
operator int() const { return type; }
};
虽然使用cast操作符是一种方法,如@Jarod42所示,但我建议将该操作显式化一点
if-else
语句中使用函数调用和返回值然后
shape s(2);
int type = s.getType();
if (type == 1) cout<<"this shape is a circle"<<endl;
else if(type == 2) cout<<"this shape is a triangle"<<endl;
else if(type == 3) cout<<"this shape is a rectangle"<<endl;
s形(2);
int type=s.getType();
如果(type==1)cout通常,您可以使用运算符T
,其中T
是您要强制转换的类型。如果要强制使用static\u cast(my\u shape)
,则可以在前面添加关键字explicit
:
struct shape
{
int type;
shape() = default;
shape(int _type) : type{ _type } {}
operator int() const { return type; }
explicit operator float() const { return type; }
operator std::string() const
{
switch (type)
{
case 1:
return "circle";
case 2:
return "triangle";
case 3:
return "rectangle";
default:
break;
}
return "(unknown shape)";
}
};
这将适用于内置类型(int
,float
,double
),标准类型(std::string
,std::complex
),自定义结构/类类型,甚至指针或引用(例如,如果您有静态值数组)。您可能想考虑是否需要这些转换运算符(封装是另一个讨论),但这在概念上是如何实现的。
在本例中,您可能还希望引入一个enum
来存储您的类型值:
struct shape
{
enum type_t
{
circle = 1,
triangle,
rectangle
};
type_t type;
operator std::string() const
{
switch (type)
{
case circle:
return "circle";
case triangle:
return "triangle";
case rectangle:
return "rectangle";
default:
break;
}
return "(unknown shape)";
}
shape(type_t _type) : type{ _type } {}
// rest of class as before
};
如果最后您只想通过字符串比较形状,那么有一个更简单、更安全的解决方案:
struct shape{
std::string type;
shape() {}
bool operator==(std::string const& rhs) const {
return type == rhs;
}
};
// and if you want to be able to do string == shape.
bool operator==(std::string const& lhs, shape const& rhs) {
return rhs == lhs;
}
这适用于任何类型吗?例如,operator string()const…
或者即使我有自己的结构,operator s()const…
是否正确?是的,您可以在shape
中定义一个转换运算符,将其实例“转换”为您想要的任何其他类型。是的,您甚至可以返回引用。我尝试使用字符串作为类型,但它没有为形状和字符串之间的运算符==提供匹配。这是因为std::string
是作为operator=
的模板,所以没有operator==
匹配参数。在这种情况下,您可能会显式地转换为字符串:std::string(s)=“circle”
我恐怕要说这不是我要寻找的,我想显式地使用struct作为它的一个属性(可以是int、string或其他任何属性)的类型@Daniel,当然,这是您的选择。根据我的经验,我发现这种隐式转换会导致错误和难以理解的代码code@RSahu转换运算符不必是隐式的。您可以在操作符之前添加显式
说明符,然后它只能通过静态_cast
@RSahu使用。这也被考虑在内,因此OP的cout
调用“应该”被简化。仅供参考,如果相当危险且通常是不明智的话,就沿着这条路径走下去。您经常会含蓄地购买一些您的类不是为之设计的API。只有当您有一个清晰的is-a关系(shape类与int
绝对没有这种关系)时,这才有意义。s+3
意味着什么?这很重要,因为它不再导致编译错误。)cout@Frank这就是为什么您可以进行显式转换的原因,当然,对于一个更为高度开发的shape
API来说,使用流操作符、比较操作符等,让类的最终用户以相关的方式访问一个shape,而不暴露实现细节,这可能更有意义。当然,您知道ready.int是基本数据类型,但字符串不是。您需要重载==运算符,以便在if条件下进行比较。如何将形状s与字符串进行比较?当我尝试s==“circle”
时,它说在shape和string之间没有运算符==。您可以将其作为成员函数bool operator==(std::string s)const
实现为结构定义的一部分。在该函数中,您可以对类型使用开关(如上所述),然后针对每个案例测试字符串的值:案例圆圈:返回s==“圆圈”代码>@Jarod42好吧,你不必为了达到提问者的目标而这么做,但总的来说这绝对是个好主意,我已经把它添加到了答案中。
struct shape
{
enum type_t
{
circle = 1,
triangle,
rectangle
};
type_t type;
operator std::string() const
{
switch (type)
{
case circle:
return "circle";
case triangle:
return "triangle";
case rectangle:
return "rectangle";
default:
break;
}
return "(unknown shape)";
}
shape(type_t _type) : type{ _type } {}
// rest of class as before
};
struct shape{
std::string type;
shape() {}
bool operator==(std::string const& rhs) const {
return type == rhs;
}
};
// and if you want to be able to do string == shape.
bool operator==(std::string const& lhs, shape const& rhs) {
return rhs == lhs;
}