如何重用同一个类的实例 [英] how to reuse the same instance of a class

查看:85
本文介绍了如何重用同一个类的实例的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

嗨每一个!

我对同一个实例的重复使用存在问题,这是我的代码:

 vector< ConnectedComponent *> cc_tab1; 
while (!queue.empty())
{

marked = Breadth_First_Search(queue [ 0 ]);
ConnectedComponent * cc;
cc = ConnectedComponent;
for int i = 0 ; i< marked.size(); i ++)

{
cout<< manelll<< ENDL;
if (标记为[i] == true
{
string f = m_vertices [i];
cout<< m_nodes.push_back(f)<< ENDL;
cc-> m_nodes.push_back(f);
cout<< cc.m_nodes [<< i<< ] =<< CC-> m_nodes [1] - ;< ENDL;
queue.erase(queue.begin());
}
}
cc_tab1.push_back(cc);
cout<< manouuuuuuuuuuuuuuuuuuuu<< ENDL;
cc-> m_nodes.clear();
delete cc;
k ++;
cout<< k =<< K<< ENDL;
}



这里我正在尝试搜索我有多少ConnectedComponenet,所以我创建了一个ConnectedComponent的实例(* cc),我用它完全我的矢量cc_tab1,之后我注册它,我删除它后清除我的实例的变量,这只适用于一次迭代,它显示我这个错误:

表达式:vector下标超出范围





任何人都可以帮助我



谢谢你知道多少

解决方案

这通常称为对象池。它的优化可以加速算法并使其内存使用更加高效,如果它涉及大量的对象创建/删除。首先要考虑的是:你需要这个优化???不要优化以可接受的速度运行的东西。优化通常会引入邪恶的错误,因为它会使你的代码变得更复杂。

如果你仍然坚持汇集你的对象:你必须隐藏对象的实现,从实际的代码中删除对象使用该对象。池是隐藏这个细节的对象。



  //  按原样提供,不附带保修。未经测试。 
模板< typename T>
class ObjectPool
{
public
ObjectPool ( size_t max_size = 100
:m_MaxSize(max_size)
{}
~ObjectPool()
{
// 我们不在这里优化,保持代码可读更重要
// 因为我们很少创建和删除对象池。 ..
SetMaxPoolSize( 0 );
}
void SetMaxPoolSize( size_t size)
{
m_MaxSize = size;
size_t current_size = m_Objects.size();
if (current_size> size)
{
for size_t i = size; i< current_size; ++ i)
delete m_Objects [i] ;
m_Objects.resize(size);
}
}
T * AcquireObject()
{
if (m_Objects.empty())
return new T;
T * obj = m_Objects.back();
m_Objects.pop_back();
return obj;
}
void ReleaseObject(T * obj)
{
if (m_Objects.size()< m_MaxSize)
m_Objects.push_back(obj);
else
delete obj;
}
private
std :: vector< T *> m_Objects;
size_t m_MaxSize;
};

struct S
{
void ObjMethod( )
{
printf( %s \ n,__ FUNCTION__) ;
}
};

void PoolTest()
{
ObjectPool< S>运;
S * obj = op.AcquireObject();

// TODO:使用对象
obj-> ; ObjMethod();

op.ReleaseObject(obj);
}


// 按原样提供,不附带保证。未经测试。
模板< typename T>
class SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject
{
public
SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject (ObjectPool< T>& pool)
:m_Pool(pool)
{
m_Ptr = pool.AcquireObject();
}
~SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject()
{
Release();
}
void 发​​布()
{
if (m_Ptr)
{
m_Pool.ReleaseObject(m_Ptr);
m_Ptr = NULL;
}
}
T * 运算符 - >()
{
assert(m_Ptr);
return m_Ptr;
}
T& operator *()
{
assert(m_Ptr);
return * m_Ptr;
}
私有
// 禁用复制构造函数
SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject( const SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject&);
private
ObjectPool< T>& m_Pool;
T * m_Ptr;
};

void PoolTestWithRAII()
{
ObjectPool< S>运;

SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject< S> OBJ(OP);
// 使用obj,当它超出范围时(在函数结束时)会自动释放
obj-> ObjMethod();

{
SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject< S> OBJ2(OP);
// 使用obj,当它超出范围时(在函数结束时)会自动释放
obj2-> ObjMethod();
}

printf( 功能结束\ n);
}





编辑:你也可以实现一个永远不会汇集任何东西的空池,当你获得它时创建对象它会在您释放对象时始终删除。如果要在编译时在空池和普通池之间切换,可以使用define进行切换,或者如果要在运行时在它们之间切换,可以在空池和普通池中实现公共接口。 / blockquote>

您正在保存指向cc_tab1中对象的指针,然后删除刚刚推回的对象。



一切试图使用已删除的对象会给你一个问题:如果你没有完成它,为什么要删除一个对象?


嗨!

因为我我是c ++的新手,我只是试图找到一种简单的方法让我得到我想要的东西,我知道这不是最好的解决方案,但我为我工作,我希望你对此提出意见,谢谢你:

矢量< connectedcomponent> ConnectedComponentSearch :: CC_calculation()
{

vector< bool>标;
vector< connectedcomponent> cc_tab;
ConnectedComponent cc;
vector< string>排队
vector< string> cc_nodes; // 一个将具有连接组件节点的向量,我们将在比较中使用它

for int i = 0 ; I< m_vertices_number;我++)>
{
queue.push_back(m_vertices [i]);
cout<< queue [<< i<< ] =<< queue [i]<< endl;
}
cout<< queue [0] =<< queue [ 0 ];
string f = queue [ 0 ];
标记= Breadth_First_Search(f);
for int i = 0 ; I< marked.size();我++)>
{
cout<< 标记为[<< I<< ] =<<标记为[1] - ;< ENDL;
}

(!queue.empty())
{

已标记= Breadth_First_Search(队列[ 0 ]);
for int i = 0 ; I< marked.size();我++)>

{
if (标记为[i] == true
{
string f = m_vertices [i];
cout<< m_nodes.push_back(f)<< ENDL;
cc.m_nodes.push_back(f);
cout<< cc.m_nodes [<< i<< ] =<< cc.m_nodes [1] - ;< ENDL;
queue.erase(queue.begin());
}


}
cc_tab.push_back(cc);
k ++;

}


cout<< ******图表中连接的组件*********<< endl;
for int i = 0 ; i< k; i ++)>
{
for (vector< connectedcomponent> :: size_type j = 0 ; j!= cc_tab [i] .m_nodes.size(); ++ j)
{

cout<< cc_tab [i] .m_nodes [j]<< ENDL;
}
}
int m = 0 ;

for int l = 0 ; l< k- 1 ; l ++)>
{
for int z = m; z< k- 1 ; Z ++)>
{
for (vector< connectedcomponent> :: size_type j = 0 ; j!= cc_tab [m] .m_nodes.size(); ++ j)
{
string f = cc_tab [m] .m_nodes [j];
if (搜索(cc_tab [z + 1] .m_nodes,f)== true
{
cc_tab [z + 1] .m_nodes.erase(cc_tab [z + 1] .m_nodes.begin());
}
}
}
m ++;
}

for int l = 0 ; L< k;升++)>
{
for (vector< connectedcomponent> :: size_type j = 0 ; j!= cc_tab [l] .m_nodes.size(); ++ j)
{
cout<< cc_tab [l] .m_nodes [j]<< ENDL;
}
}

for int i = 0 ; i< maxp.size(); i ++)>
cout<<< maxp.at(i)<< __< ;< ENDL;
return cc_tab;

}< / connectedcomponent>< / connectedcomponent>< / connectedcomponent>< / string>< / string>< / connectedcomponent>< / bool>< / connectedcomponent>



谢谢大家的帮助:)晚安


hi every one !
i have probleme with the resuse of the same instance, here is my code :

vector<ConnectedComponent*> cc_tab1 ;
		while(!queue.empty())
		{
			
			marked=Breadth_First_Search(queue[0]);
		   ConnectedComponent	*cc;
		   cc =new ConnectedComponent;
			for(int i=0;i<marked.size();i++)

			{		
				cout <<"manelll"<< endl; 
				if(marked[i]==true)
				{
					string f= m_vertices[i];
					cout<<"m_nodes.push_back(f)" << endl;
					cc->m_nodes.push_back(f);
					cout<<"cc.m_nodes["<<i<<"]="<< cc->m_nodes[i]<< endl;
					queue.erase( queue.begin());
				}
			}
			cc_tab1.push_back(cc);
			cout << "manouuuuuuuuuuuuuuuuuuuu"<< endl;
			cc->m_nodes.clear();
			delete cc;
			k++;
			cout << "k=" << k<< endl;
		}


here i'm trying to search how much ConnectedComponenet do i have, so i create an instance (*cc)of ConnectedComponent, and i use it to full out my vector cc_tab1, after that i Register it , and i clear the varibles of my instance after i delete it, that works just for one iteration and it shows me this error :

Expression : vector subscript out of range



could any one help me please

Thank you verry much

解决方案

This is called object pooling in general. Its an optimization that can speed up an algorithm and make its memory use much more efficient if it involves a lot of object creation/deletion. First thing to consider: do you need this optimization??? Don't optimize something that runs with acceptable speed. Optimization can often introduce evil bugs because it makes your code more complex.
If you still insist on pooling your objects: You have to hide the implementation of object creation/deletion of the objects from the code that actually uses the object. The pool is the object that hides this detail.

// Provided as is without warranty. Untested.
template <typename T>
class ObjectPool
{
public:
    ObjectPool(size_t max_size=100)
        : m_MaxSize(max_size)
    {}
    ~ObjectPool()
    {
        // We do not optimize here, keeping the code readable is more important
        // as we are creating and deleting an object pool rarely...
        SetMaxPoolSize(0);
    }
    void SetMaxPoolSize(size_t size)
    {
        m_MaxSize = size;
        size_t current_size = m_Objects.size();
        if (current_size > size)
        {
            for (size_t i=size; i<current_size; ++i)
                delete m_Objects[i];
            m_Objects.resize(size);
        }
    }
    T* AcquireObject()
    {
        if (m_Objects.empty())
            return new T;
        T* obj = m_Objects.back();
        m_Objects.pop_back();
        return obj;
    }
    void ReleaseObject(T* obj)
    {
        if (m_Objects.size() < m_MaxSize)
            m_Objects.push_back(obj);
        else
            delete obj;
    }
private:
    std::vector<T*> m_Objects;
    size_t m_MaxSize;
};

struct S
{
    void ObjMethod()
    {
        printf("%s\n", __FUNCTION__);
    }
};

void PoolTest()
{
    ObjectPool<S> op;
    S* obj = op.AcquireObject();

    // TODO: use the object
    obj->ObjMethod();

    op.ReleaseObject(obj);
}


// Provided as is without warranty. Untested.
template <typename T>
class SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject
{
public:
    SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject(ObjectPool<T>& pool)
        : m_Pool(pool)
    {
        m_Ptr = pool.AcquireObject();
    }
    ~SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject()
    {
        Release();
    }
    void Release()
    {
        if (m_Ptr)
        {
            m_Pool.ReleaseObject(m_Ptr);
            m_Ptr = NULL;
        }
    }
    T* operator->()
    {
        assert(m_Ptr);
        return m_Ptr;
    }
    T& operator*()
    {
        assert(m_Ptr);
        return *m_Ptr;
    }
private:
    // disabling copy constructor
    SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject(const SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject&);
private:
    ObjectPool<T>& m_Pool;
    T* m_Ptr;
};

void PoolTestWithRAII()
{
    ObjectPool<S> op;

    SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject<S> obj(op);
    // use obj, it gets release automatically when it goes out of scope (at the end of function)
    obj->ObjMethod();

    {
        SmartPointerLikeSomethingThatAutomaticallyReleaseTheObject<S> obj2(op);
        // use obj, it gets release automatically when it goes out of scope (at the end of function)
        obj2->ObjMethod();
    }

    printf("End of function\n");
}



EDIT: You can also implement a "null pool" that never pools anything, creates the object when you acquire it and it always deletes when you release the object. If you want to switch between a null pool and a normal pool at compile time you can do that with a define, or you can implement a common interface in a null pool and a normal pool if you want to switch between them at runtime.


You are preserving the pointer to an object in your cc_tab1, and then deleting the object you have just pushed back.

Anything which tries to use deleted objects will give you a problem: why are you deleting an object if you haven't finished with it?


hi !
since i'm new in c++ , i just tryed to find a simple way for me to get what i want , i know it is not the best solution but i worked for me , i wish you give your opinion about it thank you :

vector<connectedcomponent> ConnectedComponentSearch::CC_calculation()
{

	vector<bool> marked;
	vector<connectedcomponent> cc_tab ;
	ConnectedComponent cc;
	vector<string> queue ;
	vector<string> cc_nodes ;//a vector that will have the node of a Connected Component , we will use it in the comparaison

	for(int i=0;i<m_vertices_number;i++)>
		{
			queue.push_back(m_vertices[i]);
			cout<<"queue["<<i<< "] =" <<queue[i]<<endl;
		}
	cout << "queue[0]=" << queue[0];
	string f= queue[0];
		marked=Breadth_First_Search(f);
		for(int i=0;i<marked.size();i++)>
		{
			cout<<"marked["<< i<< "] ="<< marked[i]<<endl;
		}

		while(!queue.empty())
		{
			
			marked=Breadth_First_Search(queue[0]);
			for(int i=0;i<marked.size();i++)>

			{	
				if (marked[i]==true)
				{
					string f= m_vertices[i];
					cout<<"m_nodes.push_back(f)" << endl;
					cc.m_nodes.push_back(f);
					cout<<"cc.m_nodes["<<i<<"]="<< cc.m_nodes[i]<< endl;
					queue.erase( queue.begin());
				}
				
			    
			}
			cc_tab.push_back(cc);
			k++;

		}


		cout<<"******The connected components in the graph*********"<<endl;
		for (int i=0; i<k;i++)>
		{
			for(vector<connectedcomponent>::size_type j = 0; j != cc_tab[i].m_nodes.size(); ++j)
            {
   
			cout << cc_tab[i].m_nodes[j] << endl;
	        }
		}
		int m=0;
		
		for (int l=0;l<k-1;l++)>
		{
			for (int z=m; z<k-1;z++)>
			{
			for(vector<connectedcomponent>::size_type j = 0; j != cc_tab[m].m_nodes.size(); ++j)
			{ 
			    string f= cc_tab[m].m_nodes[j];
				if(search(cc_tab[z+1].m_nodes,f)==true)
				{
					cc_tab[z+1].m_nodes.erase(cc_tab[z+1].m_nodes.begin());
			    }
			}
			}
			m++;
		}

		for (int l=0;l<k;l++)>
		{
			for(vector<connectedcomponent>::size_type j = 0; j != cc_tab[l].m_nodes.size(); ++j)
			{  
				cout << cc_tab[l].m_nodes[j] << endl;
			}
		}

		for(int i=0;i<maxp.size();i++)>
			cout<<maxp.at(i)<<"__"<<endl;
		return cc_tab;

}</connectedcomponent></connectedcomponent></connectedcomponent></string></string></connectedcomponent></bool></connectedcomponent>


thank you all for your help :) good night


这篇关于如何重用同一个类的实例的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆