C++ 接受常量和非常量数据的通用函数及相关函数 对于问题题目,请考虑以下代码: template <typename T> void write(const T& /*data*/) { // use data as const } template <typename T> void read(T& /*data*/) { // modify data } struct S { int a; int b; // a lot of primitive types here }; void output(const S& s) { write(s.a); write(s.b); // ... } void input(S& s) { read(s.a); read(s.b); // ... } int main() { S s; input(s); output(s); }
因此,我可以从C++ 接受常量和非常量数据的通用函数及相关函数 对于问题题目,请考虑以下代码: template <typename T> void write(const T& /*data*/) { // use data as const } template <typename T> void read(T& /*data*/) { // modify data } struct S { int a; int b; // a lot of primitive types here }; void output(const S& s) { write(s.a); write(s.b); // ... } void input(S& s) { read(s.a); read(s.b); // ... } int main() { S s; input(s); output(s); },c++,templates,c++14,C++,Templates,C++14,因此,我可以从input/output调用use函数,如下所示: use<write, S>(s); // in output function use<read, S>(s); // in input fuction 使用;//输入输出函数 使用;//输入函数 如何归档此(或类似)行为以消除代码重复?我正在使用C++14 template <typename S, typename F> void use(S&& s, F&&a
input
/output
调用use
函数,如下所示:
use<write, S>(s); // in output function
use<read, S>(s); // in input fuction
使用;//输入输出函数
使用;//输入函数
如何归档此(或类似)行为以消除代码重复?我正在使用C++14
template <typename S, typename F>
void use(S&& s, F&& f)
{
f(s.a);
f(s.b);
f(s.c);
}
如果需要多种类型:
template <typename S, typename Target>
using EnableFor = std::enable_if_t<std::is_same_v<std::decay_t<S>, Target>>;
template <typename S, typename F>
auto use(S&& s, F&& f) -> EnableFor<S, S0>
{
f(s.a);
f(s.b);
f(s.c);
}
template <typename S, typename F>
auto use(S&& s, F&& f) -> EnableFor<S, S1>
{
f(s.d);
f(s.e);
f(s.f);
}
您可以定义所用模板的界面:
template<class M, class S>
void use(S &&s) {
M::method(s.a);
M::method(s.b);
};
我相信我明白你想要什么,但这是不可能的。目前,在C++类通用流中没有实现所有类的方法。需要访问诸如类的字段数量、相对地址以及编译时的类型等信息
他们正在努力把这个添加到C++中很多年,寻找反射。据我所知,它将不适合C++ 20。 但是,您可以组织代码,使每个读/写方法都易于实现。例如:
class A : public B, public C
{
private:
vector<int> m_v;
int m_x;
};
A类:公共B类、公共C类
{
私人:
向量m_v;
int m_x;
};
然后将其实现为
template<>
void write(const A& a)
{
write((const B&)a);
write((const C&)a);
write(a.m_v);
write(a.m_x);
}
模板
无效写入(常量A&A)
{
写入((常数B&)a);
写((常数C&)a);
书写(a.m_v);
书写(a.m_x);
}
而对于常见的数据结构,如std::vector
则通过write
实现写操作。这需要时间,但将其技术化并使用重定向可以节省大量代码和时间
(您需要做<代码>写/代码>一个朋友函数,或一个成员函数让它访问私有成员)
不能仅仅是<代码>使用(t t)< /> >并让<代码> t <代码> >代码> t&< />代码>还是<代码> cont t&</代码>?在什么基础上,你认为<代码>使用(s)< /> >优于写入
)?@Peter:很简单,想象一个结构的序列化/反序列化代码。你想列出一次成员,而不是两次。FWIW,如果你想序列化一堆不同的类型,请查看boost serialize:@VittorioRomeo-我明白问题的意思。但寻求的解决方案仍然需要执行读写操作的语句成员可能只列出一次,但它们用于更复杂的语句中,这些语句在读写时必须不同。我应该如何处理另一种类型,例如S1{int x,int y;}
?。也就是说,没有a
,b
,c
字段。你可以为此编写另一个使用函数。你可以将S
约束为S0
或S1
以使它们过载。我认为在模板函数方面应该有专门化,不是吗?älёxölü将来我会带着反射来,但现在这就是你所拥有的一切。älёxölüt:专门化不能很好地处理函数模板和完美的转发。我会在enable_if
或C++20中的概念中使用两个重载。“人们需要访问诸如类的字段数量、相对地址以及编译时的类型等信息。”这在C++17.Google for“magic\u get
”中就有可能实现。有趣的是,它确实可以解决一半的问题(我们仍然需要解决识别字段的准确位置的问题,因为对齐规则使其变得非常重要)。不幸的是,magic\u get
在类派生自其他任何东西时都不起作用-仅适用于普通结构/类。
template<class M, class S>
void use(S &&s) {
M::method(s.a);
M::method(s.b);
};
template <typename T>
void write(const T& /*data*/)
{
// use data as const
}
struct writer {
template <typename T>
static void method(const T& t)
{
write(t);
}
};
use<writer>(s);
struct reader {
template <typename T>
static void method(T& t)
{
read(t);
}
};
use<reader>(s);
class A : public B, public C
{
private:
vector<int> m_v;
int m_x;
};
template<>
void write(const A& a)
{
write((const B&)a);
write((const C&)a);
write(a.m_v);
write(a.m_x);
}