• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

zwalnianie zaalokowanej pamięci (delete [])

Object Storage Arubacloud
0 głosów
135 wizyt
pytanie zadane 31 grudnia 2018 w C i C++ przez SeekingAnswers Nowicjusz (140 p.)

Witam wszystkich, przychodzę do Was z problemem dot. zwalniania pamięci. Mianowicie przedstawię Wam dwa kody zawierające funkcję zwracającą adres tablicy elementów parzystych z tablicy przekazanej do funkcji jako argument. 

Kody różnią się jedną linijką - 1) zwalnia zaalokowaną dynamicznie pamięć, natomiast 2) nie. Przy sprawdzaniu finalnej tablicy elementów parzystych dla kodu 1) widoczne są błędy, dla kodu 2) wartości są prawidłowe. 

Jak powinien wyglądać poprawny kod dla wariantu 1)?

 

1)

#include <iostream>

using namespace std;

int *funkcja(int *poczatek, int *koniec, int &ile){
    ile=0;
    int rozmiar=0;
    int *tablica=NULL;
while(poczatek<=koniec){
if(*poczatek%2==0){
ile++;
    int *robocza= new int[rozmiar+1];
    for(int i=0;i<rozmiar;i++){

        *(robocza+i)=*(tablica+i);
    }

    *(robocza+rozmiar)=*(poczatek);
  /*  for(int i=0;i<ile;i++){
    cout<<"R:"<<*(robocza+i)<<" ";
}
cout<<endl; */

    tablica=robocza;
delete[] robocza;
    rozmiar++;

/*for(int i=0;i<ile;i++){
    cout<<"T:"<<*(tablica+i)<<" ";
}
cout<<endl; */

}

poczatek++;
}
for(int i=0;i<ile;i++){
    cout<<*(tablica+i)<<" ";
}
cout<<endl;
return tablica;

}



int main()
{
    int tab[]={2,4,3,8,10,12};
    int *pocz=tab;
    int *kon=&tab[5];
    int ile=0;

    cout<<funkcja(pocz,kon,ile);
}

Wynik: 

2)

#include <iostream>

using namespace std;

int *funkcja(int *poczatek, int *koniec, int &ile){
    ile=0;
    int rozmiar=0;
    int *tablica=NULL;
while(poczatek<=koniec){
if(*poczatek%2==0){
ile++;
    int *robocza= new int[rozmiar+1];
    for(int i=0;i<rozmiar;i++){

        *(robocza+i)=*(tablica+i);
    }

    *(robocza+rozmiar)=*(poczatek);
  /*  for(int i=0;i<ile;i++){
    cout<<"R:"<<*(robocza+i)<<" ";
}
cout<<endl; */

    tablica=robocza;

    rozmiar++;

/*for(int i=0;i<ile;i++){
    cout<<"T:"<<*(tablica+i)<<" ";
}
cout<<endl; */

}

poczatek++;
}
for(int i=0;i<ile;i++){
    cout<<*(tablica+i)<<" ";
}
cout<<endl;
return tablica;

}



int main()
{
    int tab[]={2,4,3,8,10,12};
    int *pocz=tab;
    int *kon=&tab[5];
    int ile=0;

    cout<<funkcja(pocz,kon,ile);
}

Wynik:

Jak widać w wynikach, początkowe wartości w kodzie 1) pochodzą z niewiadomego źródła.

Z góry dziękuję za wyjaśnienia! :)

1 odpowiedź

+1 głos
odpowiedź 31 grudnia 2018 przez j23 Mędrzec (194,920 p.)
tablica = robocza;
delete[] robocza;
...

return tablica;

tablica i robocza po wykonaniu delete będą wskazywać na ten sam zwolniony blok pamięci, dlatego masz dziwne wartości.

 

Tak zrób:

	while(poczatek <= koniec) 
	{
		if(*poczatek % 2 == 0) 
		{
			ile++;
			int *robocza = new int[rozmiar + 1];
			for(int i = 0; i < rozmiar; i++) {
				robocza[ i] = tablica[i];
			}

			delete[] tablica;
			tablica = robocza;

			robocza[rozmiar++] = *poczatek;
		}

		++poczatek;
	}

 

komentarz 31 grudnia 2018 przez SeekingAnswers Nowicjusz (140 p.)

Dziękuję serdecznie za odpowiedź. Rozumiem, że linia kodu:

robocza[rozmiar++] = *poczatek;

może być zastąpiona poprzez:

tablica[rozmiar++] = *poczatek;

gdyż obydwa wskaźniki wskazują na ten sam blok pamięci, a zwracamy 

return tablica;

bo ten wskaźnik jest globalnie zadeklarowany.

1
komentarz 31 grudnia 2018 przez j23 Mędrzec (194,920 p.)
  1. tak
  2. tak

Podobne pytania

+1 głos
2 odpowiedzi 877 wizyt
pytanie zadane 16 września 2018 w C i C++ przez k4to Początkujący (310 p.)
0 głosów
3 odpowiedzi 455 wizyt
pytanie zadane 5 października 2017 w C i C++ przez hitem Początkujący (300 p.)
0 głosów
1 odpowiedź 250 wizyt

92,539 zapytań

141,382 odpowiedzi

319,477 komentarzy

61,928 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj.

Akademia Sekuraka

Kolejna edycja największej imprezy hakerskiej w Polsce, czyli Mega Sekurak Hacking Party odbędzie się już 20 maja 2024r. Z tej okazji mamy dla Was kod: pasjamshp - jeżeli wpiszecie go w koszyku, to wówczas otrzymacie 40% zniżki na bilet w wersji standard!

Więcej informacji na temat imprezy znajdziecie tutaj. Dziękujemy ekipie Sekuraka za taką fajną zniżkę dla wszystkich Pasjonatów!

Akademia Sekuraka

Niedawno wystartował dodruk tej świetnej, rozchwytywanej książki (około 940 stron). Mamy dla Was kod: pasja (wpiszcie go w koszyku), dzięki któremu otrzymujemy 10% zniżki - dziękujemy zaprzyjaźnionej ekipie Sekuraka za taki bonus dla Pasjonatów! Książka to pierwszy tom z serii o ITsec, który łagodnie wprowadzi w świat bezpieczeństwa IT każdą osobę - warto, polecamy!

...