CAutoNativePtr - 用于在托管代码中使用本地对象的托管智能指针






4.98/5 (30投票s)
CAutoNativePtr 是一个托管模板类,充当智能指针,方便在托管代码中使用原生对象。
概述
CAutoNativePtr
是一个托管模板类,充当智能指针,方便在托管代码中使用原生对象。
template
<
typename T
>
ref class CAutoNativePtr
这里,T
是被包装的原生类型。 该类管理一个智能指针,它会在超出范围或包含的托管对象在垃圾回收期间被最终确定时自动释放原生资源。 复制构造函数和赋值运算符会转移所有权,这意味着任何时候只有一个 CAutoNativePtr
可以拥有特定的原生对象(除非您编写直接覆盖此规则的错误代码)。
使用该类
以下是一些示例代码,展示了如何使用该类。
class Native
{
public:
void F()
{
}
};
class Derived : public Native{};
void SomeFunc(Native){} //Function takes a Native object
void SomeOtherFunc(Native*){} //Function takes a Native*
ref class Ref
{
CAutoNativePtr<Native> m_native; //Declare the smart pointer object
public:
Ref()
{
}
Ref(Native* pN) : m_native(pN) //Constructor that takes a T*
{
}
//Copy constructor comes into play here
Ref(CAutoNativePtr<Native> pN) : m_native(pN)
{
}
//Assigning from a T*
void Change(Native* pNew)
{
m_native = pNew;
}
//Assigning from another smart pointer
void Change(CAutoNativePtr<Native> pNew)
{
m_native = pNew;
}
void DoStuff()
{
if(!m_native) // Logical NOT applied via T* cast
{
}
else
{
m_native->F(); //-> operator at work here
SomeFunc(*m_native); //The T* cast at work
SomeOtherFunc(m_native); //The T* cast at work
}
}
bool DoComparisons(CAutoNativePtr<Native> a1,
CAutoNativePtr<Native> a2, CAutoNativePtr<Native> a3)
{
//Operators == and != applied via T* cast
return (a1 == a2) && (a1 != a3);
}
void Close()
{
m_native.Destroy(); //Free native resource
}
};
int main()
{
CAutoNativePtr<Derived> d1(new Derived);
CAutoNativePtr<Derived> d2(new Derived);
//Specialized constructor for derived types is called here
CAutoNativePtr<Native> n1(d1);
//Specialized assignment operator for derived types is called here
n1 = d2;
return 0;
}
类参考
方法
CAutoNativePtr
- 构造函数
您可以使用四个重载。
CAutoNativePtr()
CAutoNativePtr(T* t)
CAutoNativePtr(CAutoNativePtr<T>% an)
template<typename TDERIVED> CAutoNativePtr(CAutoNativePtr<TDERIVED>% an)
无参数构造函数创建一个 CAutoNativePtr
,它包装一个类型为 T
的 nullptr
对象。 接受 T*
的重载可用于包装现有指针。 然后,有两个复制构造函数重载,其中一个是从 CAutoNativePtr<T>
(相同类型)复制构造,另一个是从 CAutoNativePtr<TDERIVED>
复制构造(它包装 T
的派生类型)。 当您复制构造一个 CAutoNativePtr
对象时,源对象的 T*
会被分离,因为任何给定时间只能有一个 CAutoNativePtr
拥有一个 T*
,否则我们最终会进行双重删除。
~CAutoNativePtr
/!CAutoNativePtr
- 析构函数和终结器
!CAutoNativePtr()
~CAutoNativePtr()
已分配的对象(如果有)将被释放。 通过让析构函数调用终结器,支持堆栈语义和非确定性垃圾回收。
Attach
- 接管现有的 T*
void Attach(T* t)
CAutoNativePtr
将拥有 T*
的所有权,如果存在现有的 T*
,它将被删除。
Detach
- 释放 T*
T* Detach()
底层 T*
被释放,现在由调用者来释放对象。
Destroy
- 删除底层 T*
void Destroy()
底层 T*
被删除。 一旦您进行此调用,CAutoNativePtr
将不再拥有任何对象。
运算符
operator->
- 指向成员运算符的指针
static T* operator->(CAutoNativePtr<T>% an)
这将返回底层 T*
对象,并允许用户使用 ->
运算符访问 T
方法和字段。
operator T*
- 转换为 T*
static operator T*(CAutoNativePtr<T>% an)
这是转换为底层 T*
。 这意味着您可以在需要 T*
的地方传递一个 CAutoNativePtr
对象,这非常方便。
operator=
- 赋值运算符
赋值运算符有三个重载。
CAutoNativePtr<T>% operator=(T* t)
CAutoNativePtr<T>% operator=(CAutoNativePtr<T>% an)
template<typename TDERIVED> CAutoNativePtr<T>% operator=(CAutoNativePtr<TDERIVED>% an)
第一个接受一个 T*
。 如果 CAutoNativePtr
当前拥有一个 T*
,则在获取新的 T*
的所有权之前,该 T*
将被释放。 其他两个重载用于从 CAutoNativePtr
对象赋值,其中一个专门用于处理拥有 T
派生对象的 CAutoNativePtr
对象。 获取所有权时,所有权会被转移,这意味着源对象会失去对 T*
的所有权,这样做是为了避免双重删除。
历史
- 2006 年 1 月 19 日:首次发布文章和代码