rep*_*ant 2 c++ memory static vector copy-constructor
我在游戏中有一个星级课程,我希望它们使用相同的纹理,所以我想出了这个代码......
sf::Texture* Star::starTexture = NULL;
unsigned int Star::refCount = 0;
Star::Star() : starSpeed(0), starScale(0), locX(0), locY(0)
{
if (starTexture == NULL)
{
starTexture = new sf::Texture();
}
refCount++;
}
Star::~Star()
{
refCount--;
if (refCount == 0)
{
delete starTexture;
starTexture = NULL;
}
}
Run Code Online (Sandbox Code Playgroud)
我正在使用这样的星级......
for (int i = 0; i < STAR_COUNT; ++i)
{
Star star;
star.Initialize(/* blah blah */);
starVector.push_back(star);
}
Run Code Online (Sandbox Code Playgroud)
我是"高级c ++技术"的新手,我担心这不起作用.我需要定义一个复制构造函数吗?矢量会使我的引用计数搞乱吗?我愿意接受更好的方法来做到这一点.我想我可以保持类外的纹理,并在初始化每个星时传递一个引用,但我更喜欢留在类中的纹理...
是的,如果你没有明确定义copy constructor并copy assignment operator为你上课,它会搞砸.
STL容器vector具有按值复制的语义.将Star对象复制到a时vector,会复制其中的原始指针.所以你现在有多个指向单个内存的指针,这肯定会使你快速走向未定义的行为,充其量.
你应该做的是明确定义这些功能.手动执行该内存的深层复制并正确增加引用计数.
更好的方法是在类中boost::shared_ptr或std::tr1::shared_ptr类内部保存RAII对象,并让它自动处理资源管理(包括引用计数内容).然后,您不再需要显式定义这些函数.
class Star
{
..
private:
std::tr1::shared_ptr<sf::Texture> m_starTexture;
};
// link the smart pointer w/ resource
Star::Star(): m_starTexture(new Texture())
{
...
}
Run Code Online (Sandbox Code Playgroud)
这保证可以通过语言功能工作:
在这种情况下,复制智能指针的功能将正确地增加引用计数,而它的析构函数将减少引用计数,并在ref count等于0时释放资源.