C++ 强制转换多态智能指针对象
我实现了以下智能指针模板类:C++ 强制转换多态智能指针对象,c++,casting,polymorphism,smart-pointers,dynamic-cast,C++,Casting,Polymorphism,Smart Pointers,Dynamic Cast,我实现了以下智能指针模板类: #ifndef __ProjectManager__mSharedPtr__ #define __ProjectManager__mSharedPtr__ #include <stdio.h> #include "RefCount.h" template <class T> class mSmartPtr { T *data; RefCount *rc; public: mSmartPtr(T* srcPtr
#ifndef __ProjectManager__mSharedPtr__
#define __ProjectManager__mSharedPtr__
#include <stdio.h>
#include "RefCount.h"
template <class T>
class mSmartPtr {
T *data;
RefCount *rc;
public:
mSmartPtr(T* srcPtr);
mSmartPtr(const mSmartPtr&);
~mSmartPtr();
T* operator->() const;
T& operator*() const;
mSmartPtr<T>& operator=( mSmartPtr&);
mSmartPtr<T> operator()(mSmartPtr&);
};
template<class T>
mSmartPtr<T> mSmartPtr<T>::operator()(mSmartPtr<T>& src) {
return dynamic_cast<??>(src);
}
template <class T>
mSmartPtr<T>::mSmartPtr(T *srcPtr):
data(srcPtr) {
rc = new RefCount();
rc->add();
}
template<class T>
mSmartPtr<T>::~mSmartPtr() {
if (rc->remove() == 0) {
delete data;
delete rc;
}
}
template<class T>
mSmartPtr<T>::mSmartPtr(const mSmartPtr<T> &src):
data(src.data), rc(src.rc) {
rc->add();
}
template <class T>
T* mSmartPtr<T>::operator->() const {
return data;
}
template<class T>
T& mSmartPtr<T>::operator*() const {
return &data;
}
template <class T>
mSmartPtr<T>& mSmartPtr<T>::operator=( mSmartPtr<T> &src) {
if (this != &src) {
if (rc->remove() == 0) {
delete data;
delete rc;
}
data = src.data;
rc = src.rc;
rc->add();
}
return *this;
}
#endif /* defined(__ProjectManager__mSharedPtr__) */
我需要按以下方式存储数据:
int int main(int argc, char const *argv[])
{
std::vector<mSmartPtr<Base>> v;
mSmartPtr<Derived1> d1 = foo();
v.push_back(d1);
return 0;
}
int-main(int-argc,char-const*argv[]
{
std::向量v;
mSmartPtr d1=foo();
v、 推回(d1);
返回0;
}
我需要以某种方式修复cast操作符,但是如何修复呢?如何在动态转换中获取基类?在转换方法中,提取底层指针并转换它,然后将其放入新的智能指针中。不要忘记复制
RefCount
,并确保目标类有一个虚拟析构函数(这样无论最后处理哪个智能指针,都会调用正确的析构函数)
我不知道如何在外部定义它,但内联定义起作用了
//In the definition, replacing this line
//mSmartPtr<T> operator()(mSmartPtr&)
template<class Tdest>
operator mSmartPtr<Tdest>() {
mSmartPtr<Tdest> retVal(static_cast<Tdest*>(data));
retVal.rc = rc;
retVal.rc.Add();
return retVal;
}
//在定义中,替换此行
//mSmartPtr运算符()(mSmartPtr&)
模板
运算符mSmartPtr(){
mSmartPtr retVal(静态_cast(数据));
retVal.rc=rc;
retVal.rc.Add();
返回返回;
}
理论上,如果您使用C++11,您也可以添加一个采用r值的版本,但我认为这需要一些工作才能正确完成,因此我避免了它。@Guvante
你的代码不起作用,我修改了它如下,但我不知道是否会工作得很好
template<class T>
mSmartPtr<T> mSmartPtr<T>::operator ()(mSmartPtr<T>& src) {
mSmartPtr<T> retVal(dynamic_cast<T*>(src.data));
retVal.rc = src.rc;
retVal.rc.Add();
return retVal;
}
模板
mSmartPtr mSmartPtr::operator()(mSmartPtr&src){
mSmartPtr retVal(动态_cast(src.data));
retVal.rc=src.rc;
retVal.rc.Add();
返回返回;
}
我认为有更好的替代方案。除非您需要在不同的位置执行此操作,否则可以通过更改创建对象的方式来避免头痛
int main(int argc, char const *argv[])
{
std::vector<mSmartPtr<Base>> v;
mSmartPtr<Base> d1 = static_cast<Base*>(foo());
v.push_back(d1);
return 0;
}
int main(int argc,char const*argv[])
{
std::向量v;
mSmartPtr d1=静态_转换(foo());
v、 推回(d1);
返回0;
}
只需避免创建与向量类型不同的
mSmartPtr
。我之前尝试过的可能重复,它不是指我要解决的cast运算符,也不是与问题直接相关,但正如我所做的:带有两个前导下划线的名称是为编译器和标准库内部使用而保留的:这些行是由Xcode新文件组件生成的..您好,谢谢您的评论。我怎样才能把模板参数添加到类方法中?@itorra:我有这个想法,但没有考虑。我将更新答案以包含该位。@itorra:无法理解它,所以我将其定义为内联(可能是内联的一个好方法)。注意,我还添加了一个单独的答案以避免出现这种情况。您需要另一个模板参数来定义输入或输出类型,具体取决于您如何实现它。不幸的是,我不知道如何将我的重新定义为内联。
int main(int argc, char const *argv[])
{
std::vector<mSmartPtr<Base>> v;
mSmartPtr<Base> d1 = static_cast<Base*>(foo());
v.push_back(d1);
return 0;
}