限制多模板参数朋友函数可访问的类实例的范围
Restrict the scope of class instances accessible by multiple template parameter friend function
我想知道我的目标是否可行。
我有一个班级,
#include<iostream>
template<class T> class Class;
template<class T, class W> Class<W> f(Class<T>& C, const Class<T>& D);
template<class T> class Class {
protected: // this could be private
T m_t;
public:
Class(): m_t(T()) {}
Class(T t): m_t(t) {}
T& getT() { return m_t; }
template<class U, class W> friend Class<W> f(Class<U>& C, const Class<U>& D);
};
template<class T, class W> Class<W> f(Class<T>& C, const Class<T>& D)
{
C.m_t += D.m_t;
Class<W> R;
std::cout << R.m_t << std::endl; // I don't want this to be possible
return R;
}
int main()
{
Class<int> C(42), D(24);
std::cout << f<int, char>(C, D).getT() << std::endl;
}
但通过这种方式,f可以访问Class实例的私有/受保护成员,其中Class的类型与f参数的类型不同,如行
std::cout << R.m_t << std::endl;
(R是W型,而不是T型(
我的问题是:有没有一种方法可以将f定义为一个友元函数,该函数具有指定返回类型(W(的模板参数,但只能访问与其参数类型相同的Class对象的私有/受保护成员?
编辑1:@cantordust提交的解决方案虽然干净美观,但当Class和f位于命名空间中时,它就不起作用了,唉,这使得它不适合更通用的用例。例如,如果在对cantordust代码的修改中,namespace n
刚好在include声明之后开始,刚好在main函数之前结束,那么除了将using n::f;
放在main中之外,没有其他方法可以使用f
,这及其含义对于编写良好的C++代码来说是不可原谅的。
编辑2:还有另一种解决方案:定义一个成员函数,可以选择定义一个具有相同参数的类似正则函数,并从中调用成员函数。代码看起来像这样:
// inside Class
template<class W> Class<W> f(Class& C, Class& D);
//outside Class
template<class T> template<class W> Class<W> Class<T>::f(Class<T>& C, Class<T>& D)
{ /* definition */ }
定义正则函数的过程是显而易见的。
您可以间接通过模板类
template<class T> class Class;
template<typename>
struct fs;
template<class T> class Class {
protected: // this could be private
T m_t;
public:
Class(): m_t(T()) {}
Class(T t): m_t(t) {}
T& getT() { return m_t; }
friend struct fs<T>;
};
template<typename T>
struct fs
{
template<typename W>
static Class<W> f(Class<T>& C, const Class<T>& D)
{
C.m_t += D.m_t;
Class<W> R;
std::cout << R.m_t << std::endl; // ill-formed
return R;
}
};
template<class T, class W>
Class<W> f(Class<T>& C, const Class<T>& D)
{
return fs<T>::template f<W>(C, D);
}
Live。
间接性是必要的,因为你不能成为部分专业化的朋友。
在温和的假设下,您不需要辅助结构:
#include<iostream>
template<class T> class Class;
template<typename U, typename W>
Class<W> f(Class<U>& C, const Class<U>& D);
template<class T>
class Class
{
protected: // this could be private
T m_t;
public:
Class()
:
m_t(T())
{}
Class(T t)
:
m_t(t)
{}
T& getT()
{
return m_t;
}
template<typename U, typename W>
friend Class<W> f(Class<T>& C, const Class<T>& D)
{
C.m_t += D.m_t;
Class<W> R;
std::cout << R.m_t << std::endl; // I don't want this to be possible
return R;
}
};
int main()
{
Class<int> C(42), D(24);
std::cout << f<int, char>(C, D).getT() << std::endl;
}
在这里演示
相关文章:
- 尝试通过多个向量访问变量时,向量下标超出范围
- 如何访问超出其块范围的对象?
- 在函数内创建的对象的范围 - 如果在函数外部存储和访问引用,它们是否有效?
- 给定一个C++嵌套的私有结构类型,是否有从文件范围静态函数访问它的策略
- 如何在C++中访问有序映射中的键的范围/间隔?
- 访问提升:shared_ptr 主范围外崩溃,断言失败:px != 0.指针的正确用法是什么?
- 我无法访问变量的值,即使我通过范围传递了它
- 限制多模板参数朋友函数可访问的类实例的范围
- 访问基于范围的循环(如for_each)中的std::map迭代器
- 如何访问范围外的类?
- 无法从另一个函数访问文件范围变量的内容
- 我们如何准备小内存池,其中每个线程可以独立访问某些位置范围?
- 枚举范围无法通过 C++ 中的类中的结构访问
- x64 DLL 堆栈访问超出范围?
- 为什么这个循环变量在循环范围之外是可访问的
- 范围检查检测到的检测代码和超出范围的错误访问
- 向量下标出的范围错误.即使向量的索引大于访问数据的索引,也会发生误差
- 在C 中本地声明隐藏的封闭范围(而非全局)中访问变量
- 为什么可以访问范围之外的枚举器?
- 如何在C 中访问无范围分辨率运算符的标头构件类型