[英]Do I have to use delete to avoid memory leaks? I have used new to allocate the structure instances
以下代碼實現了一個簡單的哈希函數。 我已經用new
運算符分配了struct實例。
程序結束時是否可以使用delete
運算符?
如果是這樣,我該怎么辦? [針對該結構的每個實例的delete
語句? 還是有一種更簡單的方法? ]
#include <iostream>
#define SIZE 10
using namespace std;
typedef struct myhashtag
{
int data;
struct myhashtag * next;
} myhash;
void printhash(myhash array[])
{
// print fn
}
void hash(int data, myhash array[])
{
int h = data % SIZE;
myhash * newhash = new myhash;
newhash->data = data;
newhash->next = NULL;
if(array[h].next == NULL) //first insert
{
array[h].next = newhash;
return;
}
myhash * iter = array[h].next;
while(iter->next != NULL)
{
iter = iter->next;
}
iter->next = newhash;
return;
}
int main()
{
myhash array[SIZE];int i;
for(i=0; i<SIZE; i++)
{
array[i].data = 0;
array[i].next = NULL;
}
while(1)
{
cout << "\nSo, what would you like to enter? : ";
cin >> i;
hash(i, array);
printhash(array);
}
// the deletes go here
return 0;
}
通常,對於每個帶有new的分配,您確實確實需要執行一次刪除(或對數組執行delete [])。
如果您使用的是Linux,那么valgrind可以幫助檢測內存泄漏。
C ++的最新版本以及Boost庫提供了各種智能指針,當不再引用該對象時,它們基本上將自動釋放內存。
在您選擇的C ++書中查找std :: unique_ptr。
是的,您應該始終刪除分配的任何動態內存。
您可以實現一個簡單的RAII容器來處理內存清理。 只需創建一個類以充當句柄,即可在其構造函數中通知內存。 將其刪除在其析構函數中,並提供某種訪問機制。 這樣,將在聲明句柄的作用域末尾自動清除所有內存。
C ++確實要求您管理對象的生存期。 它不像許多Java或C#書籍可能會讓您相信的那么難。 但是,是的,在不使用垃圾回收器的情況下 ,您需要確保正確調用delete
。
我可以想象有兩種方法可以對您發布的代碼執行此操作。 正如其他人所建議的,第一種是使用std::unique_ptr
。
第二個是給您的struct
一個析構函數。 我不太清楚為什么您要使用經典的C typedef struct ...
慣用語(在C中這樣做是為了不必經常使用struct
關鍵字,但不必使用struct
關鍵字就像在C ++中一樣)。 我將其保留在下面的代碼中,但我想將其標記為非慣用語:
typedef struct myhashtag
{
int data;
struct myhashtag * next;
~myhashtag()
{
if (next) {
delete next;
}
}
} myhash;
(您仍然需要確保delete
放置“在此處發生刪除”的注釋的頭節點)。
但是,這假定在列表末尾將next
正確分配給NULL
。 您發布的代碼可以做到這一點,但這僅是按慣例執行的。 較為慣用的方法是:
struct hash_node {
int data;
hash_node* next;
hash_node(int d, n = NULL) : data(d), next(n) { }
~hash_node()
{
if (next) {
delete next;
}
}
};
void hash(int data, hash_node* array)
{
int h = data % SIZE;
hash_node* newhash = new hash_node(data);
if(array[h].next == NULL) //first insert
{
array[h].next = newhash;
return;
}
hash_node* iter = array[h].next;
while(iter->next != NULL)
{
iter = iter->next;
}
iter->next = newhash;
return;
}
更為慣用的方法是:
#include <list>
#include <iostream>
using namespace std'
int main()
{
list<int> list_that_the_code_was_calling_a_hash;
while(1) {
cout << "\nSo, what would you like to enter? : ";
cin >> i;
list_that_the_code_was_calling_a_hash.push_back(i);
if (list_that_the_code_was_calling_a_hash.size() > 10) {
list_that_the_code_was_calling_a_hash.pop_front();
}
printhash(list_that_the_code_was_calling_a_hash);
}
return 0;
}
許多人會建議使用std::vector
因為std::list
根本無法與您的CPU緩存良好地交互。 是的,當您在容器中間進行裝填時, std::vector
會進行更多復制。 但是通過非常友好的緩存,它可以彌補以上不足。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.