Bellek

2013-03-08 37 views
6

yeniden tahsis edilmiyor Bir projenin ortasındayım ve malloc() ve realloc() kullanmaya çalışıyorum. Ne zaman malloc olduğumu biliyorum, işe yarıyor ama realloc kullandığımda, ayrılmış bellek miktarını hiç değiştirmiyor. Ben her zaman bu realloc zaten bozuk bellek yeniden tahsis edecektir.Bellek

Bu şunlardır: Ben malloc kullanarak bu yapılar 7 yapmak istediğinizde I will,

struct student { 
    int age; 
    int numOfClasses; 
    int gender; //0 male; 1 female 
} student; 

:

#include <stdlib.h> 

Ben bir yapı var burada

ben ne var Bu kod satırını kullanın:

student stud* = (structure*) malloc(7*sizeof(student)); 

Bu hat çalışır. Bu kod satırı yapının büyüklüğünü ve katları 7 ile alır. Kısacası, bu 7 yapıdan oluşan bir dizi yapmak için yeterli hafızaya sahip olacaktır. İşte

enter image description here

: Ben 8'e bunu değiştirmek istiyorum eğer A önceki malloced bellek ve B yeni malloced (veya realloced) bellek nerede

Şimdi, bu yapacağını Ben kodunda kaç: bildiğim kadarıyla

stud = (student*)realloc(stud, 8*sizeof(student)); 

, realloc ikinci parametrede değişkeni alır ve bellek bu miktarı mallocs. Ardından, işaretçiyi (veya önceki malloced) alır ve sadece malloced belleğe verilen işaretçiden olabildiğince fazla doldurur. Tabii ki, ikinci parametre önceki malloced boyuttan daha büyük olmalı ya da stud sonunda bir miktar hafızayı kaybedecektir. Şimdi benim sorunum burası. Yukarıdaki satırı aradığımda hiçbir şey değişmez. Malloced dizi hala 7 uzunluğundadır. Ayrıca eminim ki, realloc için yeterli belleğim var.

Bunu doğru mu yapıyorum? Sorunum nerede olabilir?

+8

Kötü dizinin hala 7 uzunluğunda olduğunu mu düşünüyorsun? –

+0

Bu sizin sorununuz ile ilgili değil, ama bence yapınızın bir “enum” için mükemmel bir kullanımı var. – teppic

cevap

11

realloc adlı davranışa sahip olma davranışınız neredeyse doğrudur. Farklı bir işaretçi döndürmek için 'un'a sahip olmaması; İlk bloktan sonra yeterince kullanılmamış bellek olabilir, bu yüzden yığın yöneticisi aynı göstericiyi size geri döndürebilir (ancak bloğun artık daha büyük olduğunu bilecek şekilde kendi iç durumunu ayarlayabilir). Yine de, küçük bir hata yaptınız.

stud = (student*)realloc(stud, 8*sizeof(student)); 

Burada realloc dönüş değeri ile stud işaretçi yerini almaktadır. Bellek açılmasından dolayı NULL döndürürse, orijinal stud işaretçinizi kaybettiniz ve bellek sızdırıldı. Bunun yerine geçici bir işaretçi kullanmalısınız.

tmp = realloc(stud, 8*sizeof(student)); 
if (tmp) 
    stud = tmp; 

Ayrıca, hala sekizinci yuvaya bir şey koymanız gerektiğini unutmayın. Yeniden açıldıktan sonra sekizinci bölüm geçerli bir bellek ayrılmış, ancak içinde anlamlı bir şey depolayana kadar çöp içeriyor.

+0

Yeniden emin olmak için yeterli bellek olduğundan eminim. –

+1

Tamam, ama hala neden bozuk dizinin hala 7 uzunluğunda olduğunu düşündüğünüzü açıklamıyorsunuz. –

+0

Bu, 7'den 8'e neden ayrılmadığını bilmiyorum. –

4

Bu benim bu önerileri olurdu rağmen, çalışması gerekir:

malloc'dan dönüşü döküm vermeyin. C de işe yaramaz ve <stdlib.h>'u dahil etmeyi unuttuğunuzu gizleyebilir.

NULL, NULL geri dönüşü durumunda bir bellek sızıntısı yarattığından, ptr = realloc (ptr, ...) kullanmayın. Bunun yerine, tip işaret olmamak işaretçi kullanılarak bir ifade referans yani

if ((new_ptr = realloc (stud, 8 * sizeof (*stud))) != NULL) { 
    stud = new_ptr; 
} else { 
    scream_and_die("out of memory"); 
} 

kullanımı ve sizeof (*stud) kullanmak (bu tahsis işaretçi Belirli bir tip bağımsız olmak üzere). Bu şekilde, typedef'i yeniden adlandırdığınızda, malloc/realloc hattında değişiklik yapılmasına gerek yoktur. Bir başka deyişle, C dinamik hafıza paylaşımı için en iyi yöntem, N sometypes bir dizi için

#include <stdlib.h> 
sometype *ptr; 
... 
ptr = malloc (N * sizeof *ptr); 

olup.