C++ 确保使用C+类方法+;20个概念
我喜欢Java中接口的特性,并期待着新的C++20标准,引入概念 在当前的项目中,我将为同一件事提供多个实现。代码的其余部分应该不受此影响,并以一种通用的“一刀切”方式处理它们。此外,为了帮助其他人编写这个可交换部分的自己的实现,我希望文档有一个中心位置,描述所有需要的部分 我试图让它工作了一段时间,但我一直在与C++20的概念挣扎。因为没有什么真正起作用,我用一个小例子来描述我想要的:C++ 确保使用C+类方法+;20个概念,c++,c++20,c++-concepts,C++,C++20,C++ Concepts,我喜欢Java中接口的特性,并期待着新的C++20标准,引入概念 在当前的项目中,我将为同一件事提供多个实现。代码的其余部分应该不受此影响,并以一种通用的“一刀切”方式处理它们。此外,为了帮助其他人编写这个可交换部分的自己的实现,我希望文档有一个中心位置,描述所有需要的部分 我试图让它工作了一段时间,但我一直在与C++20的概念挣扎。因为没有什么真正起作用,我用一个小例子来描述我想要的: /*应该有一个元素类型,比如float、int、double、std::size\u t*/ 模板 概念Ha
/*应该有一个元素类型,比如float、int、double、std::size\u t*/
模板
概念HasElementType=需要{
typename类::元素;
};
/*文档的中心位置:在概念中。
*由于此处应列出所有相关部分,因此可以对其进行记录。
*/
模板
概念功能=需要{
Class::Class(int);/*具有int的构造函数*/
T类::field;/*具有名为“field”的类型为T的字段*/
int类::foo(T);/*有方法foo,取T,返回int*/
T类::bar(int);/*有方法bar,取int,返回T*/
void类::foobar();/*具有方法foobar,获取void,返回void*/
};
/*把两者放在一起*/
模板
概念MyInterface=HasElementType&&HasFunctions;
上述概念应确保通过my_function()
调用下面的函数对于不同的实现MyObject
∈ <代码>{implementation1,implementation2,…}
/*一些示例函数*/
模板
void my_函数(){
使用T=MyObejct::Element;
T=5;
MyObejct-myObject(1);
T字段=myObject.field;
int foo=myObject.foo(t);
T bar=myObject.bar(1);
myObject.foobar();
}
关于这一点,我有3个问题:
谢谢,摩洛,你问了很多问题,所以我一一回答。首先是你的“HasElement”概念 在这里您可以看到它是如何工作的:
#include <iostream>
#include <type_traits>
class AWithStaticElement{
public:
static int Element;
};
int AWithStaticElement::Element = 12;
class AWithInstanceElement{
public:
int Element;
};
class AWithElementType{
public:
using Element = int;
};
class AWithoutElement{
};
template<typename T>
requires std::is_member_pointer_v<decltype(&T::Element)>
void Foo(T t)
{
std::cout << "Has instance Element " << t.Element << "\n";
}
template<typename T>
requires std::is_pointer_v<decltype(&T::Element)>
void Foo(T t)
{
std::cout << "Has static Element " << t.Element << "\n";
}
template<typename T>
requires requires (T t) { typename T::Element; }
void Foo(T t)
{
std::cout << "Has Element type\n";
}
template<typename... T>
void Foo(T&&... t)
{
std::cout << "Has no Element!\n";
}
int main()
{
Foo(AWithStaticElement{});
Foo(AWithInstanceElement{});
Foo(AWithElementType{});
Foo(AWithoutElement{});
}
#包括
#包括
类AWithStaticElement{
公众:
静态int元素;
};
int AWithStaticElement::Element=12;
类AwiInstanceElement{
公众:
int元素;
};
AWithElementType类{
公众:
使用元素=int;
};
AWithoutElement类{
};
模板
需要std::is_member_pointer_v
void Foo(T)
{
std::cout您有一个合理的想法,但这不是requires表达式的语法
template < typename Class >
concept HasFunctions = requires(Class c, Class::Element e) {
Class(1); // don't use a null pointer constant here!
{ c.field } -> std::same_as<decltype(e)>;
{ c.foo(e) } -> std::same_as<int>;
{ c.bar(1) } -> std::same_as<decltype(e)>;
c.foobar();
};
模板
概念HasFunctions=requires(类c,类::元素e){
类(1);//此处不要使用空指针常量!
{c.field}->std::与相同;
{c.foo(e)}->std::与相同;
{c.bar(1)}->std::与相同;
c、 foobar();
};
请注意,不需要单独测试Class::Element
:如果该类型不存在,那么原子约束将根据需要计算为false
这并不像你的措辞所暗示的那样严格;从int
(可能通过隐式转换、默认参数、构造函数模板等)构造类就足够了例如,它完全忽略了foobar
的返回类型。然而,正如约束作者的常见建议一样,为什么您会关心foobar
是否返回某个内容?如果您希望它是void
,您无论如何也不会对返回值做太多处理。通常,要求您将使用的接口(例如,您将在此处传递int
,并忽略此处的值)而不是试图描述该类型的实现。因此,您可以考虑放宽<代码> STD::SAMEYAS AS ,也许用<代码> STD::Exchange Type到.< /P>每一个StAccOfFuff.com问题。请1。是的,2。基于意见的,但对我来说似乎很好(概念命名除外)。3、基于意见的,但似乎是一个好方法,还有其他方法(根本不检查,SFANAE)“我喜欢java中接口的特性,并且期待新C++ 20标准,引入概念”“这不是概念是什么”java“接口”只是C++中的纯虚拟类。