I am pretty proficient with C, and freeing memory in C is a must.
我非常精通C,并且在C中释放内存是必须的。
However, I'm starting my first C++ project, and I've heard some things about how you don't need to free memory, by using shared pointers and other things.
但是,我正在开始我的第一个C ++项目,并且我已经听说过一些关于如何不需要释放内存的东西,通过使用共享指针和其他东西。
Where should I read about this? Is this a valuable replacement for proper delete
C++ functionality? How does it work?
我应该在哪里读到这个?这是正确删除C ++功能的有价值的替代品吗?它是如何工作的?
EDIT
I'm confused, some people are saying that I should allocate using new
and use smart pointers for the deallocation process.
我很困惑,有些人说我应该使用new分配并使用智能指针进行释放过程。
Other people are saying that I shouldn't allocate dynamic memory in the first place.
其他人说我不应该首先分配动态内存。
Others are saying that if I use new I also have to use delete just like C.
其他人说,如果我使用新的我也必须像C一样使用删除。
So which method is considered more standard and more-often used?
那么哪种方法被认为更标准,更经常使用?
14 个解决方案
#1
18
Where should I read about this?
我应该在哪里读到这个?
Herb Sutter's Exceptional C++ and Scott Meyers's More Effective C++ are both excellent books that cover the subject in detail.
Herb Sutter的Exceptional C ++和Scott Meyers的“更有效的C ++”都是出色的书籍,详细介绍了这一主题。
There is also a lot of discussion on the web (Google or * searches for "RAII" or "smart pointer" will no doubt yield many good results).
网上也有很多讨论(谷歌或*搜索“RAII”或“智能指针”无疑会产生很多好结果)。
Is this a valuable replacement for proper
delete
C++ functionality?这是正确删除C ++功能的有价值的替代品吗?
Absolutely. The ability not to worry about cleaning up resources, especially when an exception is thrown, is one of the most valuable aspects of using RAII and smart pointers.
绝对。不用担心清理资源的能力,特别是在抛出异常时,是使用RAII和智能指针的最有价值的方面之一。
#2
9
What I meant in my comment (sorry for being terse - I had to run out to the shops) is that you should be using:
我在评论中的意思(对不起是简洁 - 我不得不跑到商店)是你应该使用的:
std::string s = "foobar";
rather than:
std::string * s = new std::string( "foobar" );
...
delete s;
and:
vector <Person> p;
p.push_back( Person( "fred" ) );
rather than:
vector <Person *> p;
p.push_back( new Person( "fred" ) );
You should always be using classes that manage memory for you. In C++ the main reason for creating an object using new is that you don't know its type at compile-time. If that isn't the reason, think long and hard before using new and delete, or even smart pointers.
您应始终使用为您管理内存的类。在C ++中,使用new创建对象的主要原因是您在编译时不知道它的类型。如果这不是原因,那么在使用new和delete之前,甚至是智能指针之前要认真思考。
#3
5
If you allocate dynamic memory (with new), you need to free it (with delete), just like using malloc/free in C. The power of C++ is that it gives you lots of ways of NOT calling new, in which case you don't need to call delete.
如果你分配动态内存(使用new),你需要释放它(使用delete),就像在C中使用malloc / free一样.C ++的强大之处在于它为你提供了许多不调用new的方法,在这种情况下你不需要调用删除。
#4
4
You still have to worry about freeing memory in C++, it's just that there are better methods/tools for doing so. One can argue that attention to memory management in C++ is more difficult as well due to the added requirement of writing exception safe code. This makes things such as:
您仍然需要担心在C ++中释放内存,只是有更好的方法/工具可以实现。可以说,由于编写异常安全代码的额外要求,在C ++中对内存管理的关注也更加困难。这使得事情如下:
MyClass *y = new MyClass;
doSomething(y);
delete y;
Look completely harmless until you find that doSomething()
throws an exception and now you have a memory leak. This becomes even more dangerous as code is maintained as the code above could have been safe prior to someone changing the doSomething()
function in a later release.
看起来完全无害,直到你发现doSomething()抛出异常,现在你有内存泄漏。这变得更加危险,因为代码被维护,因为在以后的版本中有人更改doSomething()函数之前,上面的代码可能是安全的。
Following the RAII methodology is a big part of fixing memory management challenges and using auto_ptr
's or shared pointers provided by libraries such as Boost make it easier to incorporate these methods into your code.
遵循RAII方法是修复内存管理挑战的重要部分,使用由Boost等库提供的auto_ptr或共享指针可以更轻松地将这些方法合并到代码中。
Note that auto_ptr
is not a "shared" pointer. It is an object that takes ownership of the dynamically allocated object and gives that ownership away on assignment and copy. It doesn't count references to the memory. This makes it unsuitable for use within standard containers and many in general prefer the shared_ptr of Boost to the auto_ptr provided by the standard.
请注意,auto_ptr不是“共享”指针。它是一个对象,它获取动态分配的对象的所有权,并在分配和复制时提供所有权。它不计算对内存的引用。这使得它不适合在标准容器中使用,并且许多人通常更喜欢Boost的shared_ptr到标准提供的auto_ptr。
It is never safe to put auto_ptrs into standard containers. Some people will tell you that their compiler and library compiles this fine, and others will tell you that they've seen exactly this example recommended in the documentation of a certain popular compiler; don't listen to them.
将auto_ptrs放入标准容器中绝对不安全。有些人会告诉你他们的编译器和库编译得很好,而其他人会告诉你他们已经看到了某个流行编译器的文档中推荐的这个例子;别听他们说
The problem is that auto_ptr does not quite meet the requirements of a type you can put into containers, because copies of auto_ptrs are not equivalent. For one thing, there's nothing that says a vector can't just decide to up and make an "extra" internal copy of some object it contains. For another, when you call generic functions that will copy elements, like sort() does, the functions have to be able to assume that copies are going to be equivalent. At least one popular sort internally takes a copy of a "pivot" element, and if you try to make it work on auto_ptrs it will merrily take a copy of the pivot auto_ptr object (thereby taking ownership and putting it in a temporary auto_ptr on the side), do the rest of its work on the sequence (including taking further copies of the now-non-owning auto_ptr that was picked as a pivot value), and when the sort is over the pivot is destroyed and you have a problem: At least one auto_ptr in the sequence (the one that was the pivot value) no longer owns the pointer it once held, and in fact the pointer it held has already been deleted!
问题是auto_ptr不能完全满足您可以放入容器的类型的要求,因为auto_ptrs的副本不等同。首先,没有任何东西可以说矢量不能仅仅决定了它所包含的某个对象的“额外”内部副本。另一方面,当您调用将复制元素的泛型函数(如sort())时,函数必须能够假定副本将是等效的。至少有一个流行的排序在内部获取一个“pivot”元素的副本,如果你试图使它在auto_ptrs上工作,它将快乐地获取一个pivot auto_ptr对象的副本(从而获得所有权并将其放在一个临时的auto_ptr上()),对序列进行剩余的工作(包括获取作为透视值的现在非拥有的auto_ptr的更多副本),当排序结束时,数据库被销毁并且您遇到问题:序列中至少有一个auto_ptr(作为透视值的那个)不再拥有它曾经拥有的指针,事实上它所持有的指针已被删除!
Taken From: Using auto_ptr Effectively
取自:有效使用auto_ptr
#5
2
Well, of course you need to delete. I would rephrase this as 'what libraries can I use that can automate the deletion of allocated memory?'. I'd recommend you start by reading up the Boost Smart pointers page.
好吧,当然你需要删除。我将其改为'我可以使用哪些库可以自动删除已分配的内存?'。我建议你先阅读Boost Smart指针页面。
#7
2
The best answer I can give you is: something needs to call delete for each object created with new. Whether you do it manually, or using a scope-based smart pointer, or a reference-counted smart pointer, or even a non-deterministic garbage collector, it still needs to be done.
我能给你的最好答案是:对于用new创建的每个对象,需要调用delete。无论您是手动执行,还是使用基于作用域的智能指针,或引用计数的智能指针,甚至是非确定性垃圾收集器,它仍然需要完成。
Having said that, I have not manually called delete in 10 years or so. Whenever I can I create an automatic object (on the stack); when I need to create an object on the heap for some reason I try using a scope-based smart pointer, and in rare cases when there is a legitimate reason to have shared ownership, I use a reference counted smart pointer.
话虽如此,我还没有在10年左右手动调用删除。每当我可以创建一个自动对象(在堆栈上);当我需要在堆上创建一个对象由于某种原因我尝试使用基于范围的智能指针,并且在极少数情况下,当有合法的理由拥有共享所有权时,我使用引用计数智能指针。
#8
2
This is a great question, and actually several in one:
这是一个很好的问题,实际上是几个一个:
Do I need to worry about Managing Memory?
Yes! There is no garbage collection in C++. Anytime you allocate something with new
you need to either call delete
in your own code, or delegate that responsibility to something like a smart pointer.
是! C ++中没有垃圾收集。无论何时使用new分配内容,都需要在自己的代码中调用delete,或者将该职责委托给智能指针。
When Should I use dynamic memory allocation?
The reasons you'd want to use dynamic memory allocation (allocating with new
). Some of these include:
您想要使用动态内存分配的原因(使用new分配)。其中一些包括:
- You don't know the size of the thing you are allocating at compile time
- You don't know the type of the thing you are allocating at compile time
- You are reusing the same data in different contexts and don't want to pay the performance overhead of copying that data around.
你不知道你在编译时分配的东西的大小
您不知道在编译时分配的事物的类型
您正在不同的上下文中重用相同的数据,并且不希望支付复制该数据的性能开销。
There are lots of other reasons, and these are gross over generalizations, but you get the idea.
还有很多其他原因,这些都是粗略概括,但你明白了。
What tools can I use to help me with memory management?
Smart pointers are the way to go here. A smart pointer will take ownership of memory that you allocate, and then release that memory automatically for you at a specific time depending on the policy the smart pointer.
智能指针是这里的方式。智能指针将获取您分配的内存的所有权,然后在特定时间为您自动释放该内存,具体取决于智能指针的策略。
For example, a boost::scoped_ptr will deallocate memory for you when it goes out of scope
例如,boost :: scoped_ptr会在超出范围时为您释放内存
{
scoped_ptr<MyClass> myVar( new MyClass() );
// do Something with myVar
} // myVar goes out of scope and calls delete on its MyClass
In general you should use smart pointers over raw pointers anytime you can. It will save you years of tracking down memory leaks.
通常,您应该随时使用智能指针而不是原始指针。它将为您节省数年的内存泄漏追踪时间。
Smart pointers come in many forms including:
智能指针有多种形式,包括:
If you can use Boost smart pointers I would. They rock!
如果你可以使用Boost智能指针。他们摇滚!
#9
1
Since C++ does not have a garbage collector built into the language, you need to be aware of what memory you have dynamically allocated and how that memory is being freed.
由于C ++没有内置于该语言中的垃圾收集器,因此您需要了解动态分配的内存以及释放内存的方式。
That said, you can use smart pointers to alleviate the problem of having to manually free memory via delete
- for example, see Smart Ponters (boost).
也就是说,您可以使用智能指针来缓解必须通过删除手动释放内存的问题 - 例如,请参阅Smart Ponters(boost)。
#10
1
First and foremost, before you get into the business of using auto_ptr's and writing your own RAII classes, learn to use the Standard Template Library. It provides many common container classes that automatically allocate their internal memory when you instantiate them and free it up when they go out of scope - things like vectors, lists, maps, and so forth. When you employ STL, using the new-operator and delete (or malloc and free) is rarely necessary.
首先,在您开始使用auto_ptr并编写自己的RAII类之前,请学习使用标准模板库。它提供了许多常见的容器类,当你实例化它们时会自动分配它们的内部存储器,当它们超出范围时释放它们 - 比如矢量,列表,地图等等。当您使用STL时,很少需要使用new-operator和delete(或malloc和free)。
#11
1
Freeing memory in C++ is just as much a must as in C.
在C ++中释放内存与在C中一样是必须的。
What you may be thinking of is a smart pointer library (the standard library's auto_ptr among others) - which will do reference counting for you.
你可能想到的是一个智能指针库(标准库的auto_ptr等) - 它将为你做引用计数。
#12
0
'm confused, some people are saying that I should allocate using new and use smart pointers for the deallocation process.
很困惑,有些人说我应该使用新的分配并使用智能指针进行重新分配过程。
They're right. Just like in C you still need to manage all your memory one way or another. however there are ways to use the language to automate delete.
他们是对的。就像在C中一样,你仍然需要以这种或那种方式管理你所有的记忆。但是有一些方法可以使用该语言来自动删除。
Smart pointers are basically local scope wrappers for pointers which use the object .dtor to delete the corresponding pointer once the smart pointer - which is like any other objecton the stack - goes out of scope
智能指针基本上是指针的局部范围包装器,一旦智能指针(就像堆栈中的任何其他对象一样)超出范围,使用对象.dtor删除相应的指针
#13
0
The beauty of C++ is that you have explicit control over when things are created and when things are destroyed. Do it right and you will not have issues with memory leaks etc.
C ++的优点在于,您可以明确控制何时创建事物以及何时销毁事物。做得对,你不会有内存泄漏等问题。
Depending on your environment, you may want to create objects on the stack or you may want to dynamically allocated (create them on the 'heap' - heap in quotes because its an overused term but is good enough for now).
根据您的环境,您可能希望在堆栈上创建对象,或者您可能希望动态分配(在'堆'上创建它们 - 在引号中堆,因为它是一个过度使用的术语但现在已经足够好了)。
Foo x; // created on the stack - automatically destroyed when the program exits that block of code it was created in.
Foo x; //在堆栈上创建 - 当程序退出创建它的代码块时自动销毁。
Foo *y = new Foo; // created on the heap - its O.K. to pass this one around since you control when its destroyed
Foo * y = new Foo; //在堆上创建 - 它的O.K.通过这个,因为你控制它被摧毁
Whenever you use 'new', you should use the corresponding version of delete... somewhere, somehow. If you use new to initialize a smart pointer like:
每当你使用'new'时,你应该以某种方式使用相应版本的delete ...某处。如果您使用new来初始化智能指针,例如:
std::auto_ptr x = new Foo;
std :: auto_ptr x = new Foo;
You are actually creating two items. An instance of auto_ptr and an instance of Foo. auto_ptr is created on the stack, Foo on the heap.
您实际上是在创建两个项目。 auto_ptr的一个实例和Foo的一个实例。 auto_ptr是在堆栈上创建的,堆上的Foo。
When the stack 'unwinds', it will automatically call delete on that instance of Foo. Automatically cleaning it up for you.
当堆栈“展开”时,它将自动在该Foo实例上调用delete。自动清理它。
So, general rule of thumb, use the stack version whenever possible/practical. In most instances it will be faster as well.
因此,一般经验法则,尽可能/实用时使用堆栈版本。在大多数情况下,它也会更快。
#14
0
In order of preference, you should:
按照优先顺序,您应该:
-
Avoid handling allocation yourself at all. C++'s STL (standard template library) comes with a lot of containers that handle allocation for you. Use
vector
instead of dynamically allocated arrays. Usestring
instead ofchar *
for arrays of characters. Try to seek out an appropriate container from the STL rather than designing your own.避免自己处理分配。 C ++的STL(标准模板库)附带了许多处理分配的容器。使用向量而不是动态分配的数组。对于字符数组,请使用字符串而不是char *。尝试从STL中寻找合适的容器,而不是设计自己的容器。
-
If you are designing your own class and honestly need dynamic allocation (and you usually won't if you compose your class using members of the STL), place all instances of
new
(new[]
) in your constructor and all instances ofdelete
(delete[]
) in your destructor. You shouldn't needmalloc
andfree
, generally.如果你正在设计自己的类并且诚实地需要动态分配(如果使用STL的成员编写类,通常不会这样做),将new(new [])的所有实例放在构造函数和delete的所有实例中(在析构函数中删除[])。一般来说,你不应该需要malloc和free。
-
If you are unable to keep your allocations paired within constructors and destructors, use smart pointers. Really this is not so different from #2; smart pointers are basically just special classes which use destructors to ensure deallocation happens.
如果您无法在构造函数和析构函数中保持分配配对,请使用智能指针。真的,这与#2没那么不同;智能指针基本上只是使用析构函数来确保重新分配的特殊类。
#1
18
Where should I read about this?
我应该在哪里读到这个?
Herb Sutter's Exceptional C++ and Scott Meyers's More Effective C++ are both excellent books that cover the subject in detail.
Herb Sutter的Exceptional C ++和Scott Meyers的“更有效的C ++”都是出色的书籍,详细介绍了这一主题。
There is also a lot of discussion on the web (Google or * searches for "RAII" or "smart pointer" will no doubt yield many good results).
网上也有很多讨论(谷歌或*搜索“RAII”或“智能指针”无疑会产生很多好结果)。
Is this a valuable replacement for proper
delete
C++ functionality?这是正确删除C ++功能的有价值的替代品吗?
Absolutely. The ability not to worry about cleaning up resources, especially when an exception is thrown, is one of the most valuable aspects of using RAII and smart pointers.
绝对。不用担心清理资源的能力,特别是在抛出异常时,是使用RAII和智能指针的最有价值的方面之一。
#2
9
What I meant in my comment (sorry for being terse - I had to run out to the shops) is that you should be using:
我在评论中的意思(对不起是简洁 - 我不得不跑到商店)是你应该使用的:
std::string s = "foobar";
rather than:
std::string * s = new std::string( "foobar" );
...
delete s;
and:
vector <Person> p;
p.push_back( Person( "fred" ) );
rather than:
vector <Person *> p;
p.push_back( new Person( "fred" ) );
You should always be using classes that manage memory for you. In C++ the main reason for creating an object using new is that you don't know its type at compile-time. If that isn't the reason, think long and hard before using new and delete, or even smart pointers.
您应始终使用为您管理内存的类。在C ++中,使用new创建对象的主要原因是您在编译时不知道它的类型。如果这不是原因,那么在使用new和delete之前,甚至是智能指针之前要认真思考。
#3
5
If you allocate dynamic memory (with new), you need to free it (with delete), just like using malloc/free in C. The power of C++ is that it gives you lots of ways of NOT calling new, in which case you don't need to call delete.
如果你分配动态内存(使用new),你需要释放它(使用delete),就像在C中使用malloc / free一样.C ++的强大之处在于它为你提供了许多不调用new的方法,在这种情况下你不需要调用删除。
#4
4
You still have to worry about freeing memory in C++, it's just that there are better methods/tools for doing so. One can argue that attention to memory management in C++ is more difficult as well due to the added requirement of writing exception safe code. This makes things such as:
您仍然需要担心在C ++中释放内存,只是有更好的方法/工具可以实现。可以说,由于编写异常安全代码的额外要求,在C ++中对内存管理的关注也更加困难。这使得事情如下:
MyClass *y = new MyClass;
doSomething(y);
delete y;
Look completely harmless until you find that doSomething()
throws an exception and now you have a memory leak. This becomes even more dangerous as code is maintained as the code above could have been safe prior to someone changing the doSomething()
function in a later release.
看起来完全无害,直到你发现doSomething()抛出异常,现在你有内存泄漏。这变得更加危险,因为代码被维护,因为在以后的版本中有人更改doSomething()函数之前,上面的代码可能是安全的。
Following the RAII methodology is a big part of fixing memory management challenges and using auto_ptr
's or shared pointers provided by libraries such as Boost make it easier to incorporate these methods into your code.
遵循RAII方法是修复内存管理挑战的重要部分,使用由Boost等库提供的auto_ptr或共享指针可以更轻松地将这些方法合并到代码中。
Note that auto_ptr
is not a "shared" pointer. It is an object that takes ownership of the dynamically allocated object and gives that ownership away on assignment and copy. It doesn't count references to the memory. This makes it unsuitable for use within standard containers and many in general prefer the shared_ptr of Boost to the auto_ptr provided by the standard.
请注意,auto_ptr不是“共享”指针。它是一个对象,它获取动态分配的对象的所有权,并在分配和复制时提供所有权。它不计算对内存的引用。这使得它不适合在标准容器中使用,并且许多人通常更喜欢Boost的shared_ptr到标准提供的auto_ptr。
It is never safe to put auto_ptrs into standard containers. Some people will tell you that their compiler and library compiles this fine, and others will tell you that they've seen exactly this example recommended in the documentation of a certain popular compiler; don't listen to them.
将auto_ptrs放入标准容器中绝对不安全。有些人会告诉你他们的编译器和库编译得很好,而其他人会告诉你他们已经看到了某个流行编译器的文档中推荐的这个例子;别听他们说
The problem is that auto_ptr does not quite meet the requirements of a type you can put into containers, because copies of auto_ptrs are not equivalent. For one thing, there's nothing that says a vector can't just decide to up and make an "extra" internal copy of some object it contains. For another, when you call generic functions that will copy elements, like sort() does, the functions have to be able to assume that copies are going to be equivalent. At least one popular sort internally takes a copy of a "pivot" element, and if you try to make it work on auto_ptrs it will merrily take a copy of the pivot auto_ptr object (thereby taking ownership and putting it in a temporary auto_ptr on the side), do the rest of its work on the sequence (including taking further copies of the now-non-owning auto_ptr that was picked as a pivot value), and when the sort is over the pivot is destroyed and you have a problem: At least one auto_ptr in the sequence (the one that was the pivot value) no longer owns the pointer it once held, and in fact the pointer it held has already been deleted!
问题是auto_ptr不能完全满足您可以放入容器的类型的要求,因为auto_ptrs的副本不等同。首先,没有任何东西可以说矢量不能仅仅决定了它所包含的某个对象的“额外”内部副本。另一方面,当您调用将复制元素的泛型函数(如sort())时,函数必须能够假定副本将是等效的。至少有一个流行的排序在内部获取一个“pivot”元素的副本,如果你试图使它在auto_ptrs上工作,它将快乐地获取一个pivot auto_ptr对象的副本(从而获得所有权并将其放在一个临时的auto_ptr上()),对序列进行剩余的工作(包括获取作为透视值的现在非拥有的auto_ptr的更多副本),当排序结束时,数据库被销毁并且您遇到问题:序列中至少有一个auto_ptr(作为透视值的那个)不再拥有它曾经拥有的指针,事实上它所持有的指针已被删除!
Taken From: Using auto_ptr Effectively
取自:有效使用auto_ptr
#5
2
Well, of course you need to delete. I would rephrase this as 'what libraries can I use that can automate the deletion of allocated memory?'. I'd recommend you start by reading up the Boost Smart pointers page.
好吧,当然你需要删除。我将其改为'我可以使用哪些库可以自动删除已分配的内存?'。我建议你先阅读Boost Smart指针页面。
#6
#7
2
The best answer I can give you is: something needs to call delete for each object created with new. Whether you do it manually, or using a scope-based smart pointer, or a reference-counted smart pointer, or even a non-deterministic garbage collector, it still needs to be done.
我能给你的最好答案是:对于用new创建的每个对象,需要调用delete。无论您是手动执行,还是使用基于作用域的智能指针,或引用计数的智能指针,甚至是非确定性垃圾收集器,它仍然需要完成。
Having said that, I have not manually called delete in 10 years or so. Whenever I can I create an automatic object (on the stack); when I need to create an object on the heap for some reason I try using a scope-based smart pointer, and in rare cases when there is a legitimate reason to have shared ownership, I use a reference counted smart pointer.
话虽如此,我还没有在10年左右手动调用删除。每当我可以创建一个自动对象(在堆栈上);当我需要在堆上创建一个对象由于某种原因我尝试使用基于范围的智能指针,并且在极少数情况下,当有合法的理由拥有共享所有权时,我使用引用计数智能指针。
#8
2
This is a great question, and actually several in one:
这是一个很好的问题,实际上是几个一个:
Do I need to worry about Managing Memory?
Yes! There is no garbage collection in C++. Anytime you allocate something with new
you need to either call delete
in your own code, or delegate that responsibility to something like a smart pointer.
是! C ++中没有垃圾收集。无论何时使用new分配内容,都需要在自己的代码中调用delete,或者将该职责委托给智能指针。
When Should I use dynamic memory allocation?
The reasons you'd want to use dynamic memory allocation (allocating with new
). Some of these include:
您想要使用动态内存分配的原因(使用new分配)。其中一些包括:
- You don't know the size of the thing you are allocating at compile time
- You don't know the type of the thing you are allocating at compile time
- You are reusing the same data in different contexts and don't want to pay the performance overhead of copying that data around.
你不知道你在编译时分配的东西的大小
您不知道在编译时分配的事物的类型
您正在不同的上下文中重用相同的数据,并且不希望支付复制该数据的性能开销。
There are lots of other reasons, and these are gross over generalizations, but you get the idea.
还有很多其他原因,这些都是粗略概括,但你明白了。
What tools can I use to help me with memory management?
Smart pointers are the way to go here. A smart pointer will take ownership of memory that you allocate, and then release that memory automatically for you at a specific time depending on the policy the smart pointer.
智能指针是这里的方式。智能指针将获取您分配的内存的所有权,然后在特定时间为您自动释放该内存,具体取决于智能指针的策略。
For example, a boost::scoped_ptr will deallocate memory for you when it goes out of scope
例如,boost :: scoped_ptr会在超出范围时为您释放内存
{
scoped_ptr<MyClass> myVar( new MyClass() );
// do Something with myVar
} // myVar goes out of scope and calls delete on its MyClass
In general you should use smart pointers over raw pointers anytime you can. It will save you years of tracking down memory leaks.
通常,您应该随时使用智能指针而不是原始指针。它将为您节省数年的内存泄漏追踪时间。
Smart pointers come in many forms including:
智能指针有多种形式,包括:
If you can use Boost smart pointers I would. They rock!
如果你可以使用Boost智能指针。他们摇滚!
#9
1
Since C++ does not have a garbage collector built into the language, you need to be aware of what memory you have dynamically allocated and how that memory is being freed.
由于C ++没有内置于该语言中的垃圾收集器,因此您需要了解动态分配的内存以及释放内存的方式。
That said, you can use smart pointers to alleviate the problem of having to manually free memory via delete
- for example, see Smart Ponters (boost).
也就是说,您可以使用智能指针来缓解必须通过删除手动释放内存的问题 - 例如,请参阅Smart Ponters(boost)。
#10
1
First and foremost, before you get into the business of using auto_ptr's and writing your own RAII classes, learn to use the Standard Template Library. It provides many common container classes that automatically allocate their internal memory when you instantiate them and free it up when they go out of scope - things like vectors, lists, maps, and so forth. When you employ STL, using the new-operator and delete (or malloc and free) is rarely necessary.
首先,在您开始使用auto_ptr并编写自己的RAII类之前,请学习使用标准模板库。它提供了许多常见的容器类,当你实例化它们时会自动分配它们的内部存储器,当它们超出范围时释放它们 - 比如矢量,列表,地图等等。当您使用STL时,很少需要使用new-operator和delete(或malloc和free)。
#11
1
Freeing memory in C++ is just as much a must as in C.
在C ++中释放内存与在C中一样是必须的。
What you may be thinking of is a smart pointer library (the standard library's auto_ptr among others) - which will do reference counting for you.
你可能想到的是一个智能指针库(标准库的auto_ptr等) - 它将为你做引用计数。
#12
0
'm confused, some people are saying that I should allocate using new and use smart pointers for the deallocation process.
很困惑,有些人说我应该使用新的分配并使用智能指针进行重新分配过程。
They're right. Just like in C you still need to manage all your memory one way or another. however there are ways to use the language to automate delete.
他们是对的。就像在C中一样,你仍然需要以这种或那种方式管理你所有的记忆。但是有一些方法可以使用该语言来自动删除。
Smart pointers are basically local scope wrappers for pointers which use the object .dtor to delete the corresponding pointer once the smart pointer - which is like any other objecton the stack - goes out of scope
智能指针基本上是指针的局部范围包装器,一旦智能指针(就像堆栈中的任何其他对象一样)超出范围,使用对象.dtor删除相应的指针
#13
0
The beauty of C++ is that you have explicit control over when things are created and when things are destroyed. Do it right and you will not have issues with memory leaks etc.
C ++的优点在于,您可以明确控制何时创建事物以及何时销毁事物。做得对,你不会有内存泄漏等问题。
Depending on your environment, you may want to create objects on the stack or you may want to dynamically allocated (create them on the 'heap' - heap in quotes because its an overused term but is good enough for now).
根据您的环境,您可能希望在堆栈上创建对象,或者您可能希望动态分配(在'堆'上创建它们 - 在引号中堆,因为它是一个过度使用的术语但现在已经足够好了)。
Foo x; // created on the stack - automatically destroyed when the program exits that block of code it was created in.
Foo x; //在堆栈上创建 - 当程序退出创建它的代码块时自动销毁。
Foo *y = new Foo; // created on the heap - its O.K. to pass this one around since you control when its destroyed
Foo * y = new Foo; //在堆上创建 - 它的O.K.通过这个,因为你控制它被摧毁
Whenever you use 'new', you should use the corresponding version of delete... somewhere, somehow. If you use new to initialize a smart pointer like:
每当你使用'new'时,你应该以某种方式使用相应版本的delete ...某处。如果您使用new来初始化智能指针,例如:
std::auto_ptr x = new Foo;
std :: auto_ptr x = new Foo;
You are actually creating two items. An instance of auto_ptr and an instance of Foo. auto_ptr is created on the stack, Foo on the heap.
您实际上是在创建两个项目。 auto_ptr的一个实例和Foo的一个实例。 auto_ptr是在堆栈上创建的,堆上的Foo。
When the stack 'unwinds', it will automatically call delete on that instance of Foo. Automatically cleaning it up for you.
当堆栈“展开”时,它将自动在该Foo实例上调用delete。自动清理它。
So, general rule of thumb, use the stack version whenever possible/practical. In most instances it will be faster as well.
因此,一般经验法则,尽可能/实用时使用堆栈版本。在大多数情况下,它也会更快。
#14
0
In order of preference, you should:
按照优先顺序,您应该:
-
Avoid handling allocation yourself at all. C++'s STL (standard template library) comes with a lot of containers that handle allocation for you. Use
vector
instead of dynamically allocated arrays. Usestring
instead ofchar *
for arrays of characters. Try to seek out an appropriate container from the STL rather than designing your own.避免自己处理分配。 C ++的STL(标准模板库)附带了许多处理分配的容器。使用向量而不是动态分配的数组。对于字符数组,请使用字符串而不是char *。尝试从STL中寻找合适的容器,而不是设计自己的容器。
-
If you are designing your own class and honestly need dynamic allocation (and you usually won't if you compose your class using members of the STL), place all instances of
new
(new[]
) in your constructor and all instances ofdelete
(delete[]
) in your destructor. You shouldn't needmalloc
andfree
, generally.如果你正在设计自己的类并且诚实地需要动态分配(如果使用STL的成员编写类,通常不会这样做),将new(new [])的所有实例放在构造函数和delete的所有实例中(在析构函数中删除[])。一般来说,你不应该需要malloc和free。
-
If you are unable to keep your allocations paired within constructors and destructors, use smart pointers. Really this is not so different from #2; smart pointers are basically just special classes which use destructors to ensure deallocation happens.
如果您无法在构造函数和析构函数中保持分配配对,请使用智能指针。真的,这与#2没那么不同;智能指针基本上只是使用析构函数来确保重新分配的特殊类。