gpt4 book ai didi

c++ - 资源分配和自动释放

转载 作者:搜寻专家 更新时间:2023-10-31 01:59:35 30 4
gpt4 key购买 nike

在我的应用程序中,我得到了很多 class CDbaOciNotifier 的实例。它们都共享一个指向类 OCIEnv 的一个实例的指针。

我想实现的是资源 class OCIEnv 的分配和释放将在 class CDbaOciNotifier 中自动处理。

期望的行为是,使用 class CDbaOciNotifier 的第一个实例将创建环境,之后所有后续通知程序都使用相同的环境。随着最后一个通知程序的销毁,环境也将被销毁(调用自定义删除器)。稍后,这个循环可以通过创建新环境重新开始。

到目前为止我得到了什么(使用静态工厂方法创建通知程序):

#pragma once

#include <string>
#include <memory>
#include "boost\noncopyable.hpp"

class CDbaOciNotifier : private boost::noncopyable
{
public:

virtual ~CDbaOciNotifier(void);

static std::auto_ptr<CDbaOciNotifier> createNotifier(const std::string &tnsName, const std::string &user, const std::string &password);

private:
CDbaOciNotifier(OCIEnv* envhp);

// All notifiers share one environment
static OCIEnv* m_ENVHP;

// Custom deleter
static void freeEnvironment(OCIEnv *env);

OCIEnv* m_envhp;
};

CPP:

#include "DbaOciNotifier.h"

using namespace std;

OCIEnv* CDbaOciNotifier::m_ENVHP = 0;

CDbaOciNotifier::~CDbaOciNotifier(void)
{
}

CDbaOciNotifier::CDbaOciNotifier(OCIEnv* envhp)
:m_envhp(envhp)
{

}

void CDbaOciNotifier::freeEnvironment(OCIEnv *env)
{
OCIHandleFree((dvoid *) env, (ub4) OCI_HTYPE_ENV);
*env = null;
}

auto_ptr<CDbaOciNotifier> CDbaOciNotifier::createNotifier(const string &tnsName, const string &user, const string &password)
{
if(!m_ENVHP)
{
OCIEnvCreate( (OCIEnv **) &m_ENVHP, OCI_EVENTS|OCI_OBJECT, (dvoid *)0,
(dvoid * (*)(dvoid *, size_t)) 0,
(dvoid * (*)(dvoid *, dvoid *, size_t))0,
(void (*)(dvoid *, dvoid *)) 0,
(size_t) 0, (dvoid **) 0 );
}

//shared_ptr<OCIEnv> spEnvhp(m_ENVHP, freeEnvironment); ...got so far...

return auto_ptr<CDbaOciNotifier>(new CDbaOciNotifier(m_ENVHP));
}

我想自己避免计算引用(通知程序),并使用类似 shared_ptr 的东西。

您是否找到了解决我的问题的简单方法?

最佳答案

您的代码中发生了很多事情。这是解决方案,但已简化为仅保留最基本的要素。

class CDbaOciNotifier
{
public:
CDbaOciNotifier() :
m_resource(get_env())
{ }

private:
shared_ptr<OCIEnv> m_env;

struct Delete_env
{
void operator()(OCIEnv* env)
{
OCIHandleFree( ... );
}
};

static shared_ptr<OCIEnv> get_env()
{
// make sure a mutex is involved if CDbaOciNotifier
// can be constructed concurrently.

static weak_ptr<OCIEnv> s_env;

shared_ptr<OCIEnv> env = s_env.lock();
if( ! env )
{
OCIEnv* env_ptr = OCIEnvCreate( ... );
env.reset( env_ptr, Delete_env() );
s_env = env;
}
return env;
}
};

如所写,您不能同时构造 CDbaOciNotifier。如果您想要这种能力,您将需要一个静态互斥锁来保护 s_env

weak_ptr 必须是局部静态函数,否则如果创建全局或静态 CDbaOciNotifier(静态初始化顺序未定义),您的应用可能会爆炸。

关于c++ - 资源分配和自动释放,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2904622/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com