Panel użytkownika
Nazwa użytkownika:
Hasło:
Nie masz jeszcze konta?

Kopiowanie Dynamicznie Allokowanej Pamięci C++

Ostatnio zmodyfikowano 2016-07-29 12:47
Autor Wiadomość
Mentaris
Temat założony przez niniejszego użytkownika
Kopiowanie Dynamicznie Allokowanej Pamięci C++
» 2016-07-26 14:22:04
Mam problem z kopiowaniem bloków pamięci w DAMie, mianowicie stworzylem sobie taki kodzik:
C/C++
//konstruktor
i_colD = 3;
colisionData = new int[ i_colD ];
for( int i = 1; i < i_colD; i++ )
     colisionData[ i ] = NULL;

// w metodzie w tej samej klasie
i_colD += 4;
int * bd = new int[ i_colD ];
for( int i = 1; i < i_colD - 3; i++ )
     bd[ i ] = colisionData[ i ];

delete[] colisionData;
colisionData = new int[ i_colD ];
memset( colisionData, 0, i_colD * sizeof( colisionData ) );
for( int i = 1; i < i_colD - 3; i++ )
     colisionData[ i ] = bd[ i ];

delete[] bd;
i on działa, lecz z gdy chciałem zmienić pętle for w metodzie na np
memcpy(&bd,&colisionData,sizeof(colisionData));/memcpy(&bd,&colisionData,(i_colD-4)*sizeof(colisionData));
 to wywala błąd: _block_type_is_valid(pHeap->nBlockUse)lub 0xC0000005: Access violation reading location, a nawet było że bd is corrupted

A jak już postanowiłem z tego zrobić funkcjie czyli:
C/C++
void DAMChanger( int ** aray, int g_size, int array_size )
{
    int c = sizeof * aray;
    int * bd = new int[ g_size ];
    for( int i = 1; i < g_size - array_size; i++ )
         bd[ i ] = * aray[ i ];
   
    delete[] * aray;
    * aray = new int[ g_size ];
    memset( * aray, 0, g_size * sizeof( * aray ) );
    for( int i = 1; i < g_size; i++ )
         * aray[ i ] = bd[ i ];
   
    delete[] bd;
}

// wywołanie:
DAMChanger( & colisionData, i_colD, 3 );
To wywala mi błąd 0xC0000005: Access violation reading location
Nie czaje, jeśli chodzi o tą funkcje to dwa * znaczy że wskaźnik wskazuje na wskaźnik którym jesli colisionData, która posiada dane.
Może gdzieś robię błąd? Pewnie tak i to w dodatku jakiś głupi. Pomożecie? Jak żyć?
MVS 2013 Profesional
P-150264
pekfos
» 2016-07-26 15:18:27
Tablice indeksuje się od zera. Po co, twoim zdaniem, dwa razy alokujesz tablicę w nowym rozmiarze?
P-150268
j23
» 2016-07-26 15:21:42
sizeof(colisionData) nie zwróci Ci wielkości tablicy dynamicznie przydzielonej, jedynie wielkości wskaźnika colisionData, czyli 4 lub 8.
P-150269
mateczek
» 2016-07-26 15:27:18
C/C++
for( int i = 1; i < g_size - array_size; i++ )
     bd[ i ] = * aray[ i ];

delete[] * aray;
//skopiować tablicę i potem kasować źródło?? pętla staje się zbędna!!!
bd = array
array = nullptr
P-150270
Mentaris
Temat założony przez niniejszego użytkownika
» 2016-07-26 20:09:06
@pekfos Masz racje, poprawione lecz dużo się nie zmieniło. Pierwsza alokacja jest w konstruktorze jako startowa. Bez niej wywali mi błąd że nie ma z czego kopiować, ponieważ zanim alokuje drugi raz już w metodzie, to kopiuje dane do tego "tymczasowego kontenera" bd (chyba, ponieważ jak skopiuje ze wskaźnika bez tablicy do wskaźnika z tablicą?). Więc chyba dobrze robię.O ile poprawnie rozumiem twoje pytanie.

@j23 A to dlatego ludzie mnożą to przez ilość miejsc w tablicy? np: i_colD*sizeof(colisionData) ?

@mateczek Skasowałem pętle, wprowadziłem ten twój, o wiele milej wyglądający sposób, lecz niestety teraz wywala _block_type_is_valid(pHeap->nBlockUse);
C/C++
void DAMChanger( int ** aray, int g_size, int array_size )
{
    int * bd = new int[ g_size ];
    bd = * aray;
    * aray = nullptr;
    * aray = new int[ g_size ];
    memset( * aray, 0, g_size * sizeof( int ) );
    * aray = bd;
    delete[] bd;
}
Ponieważ, o to ci chodziło, prawda?

PS: Proszę też was o wyrozumiałość, DAMy to dość trudny temat, ale uwierzcie, staram się jak mogę.
P-150277
pekfos
» 2016-07-26 21:26:17
C/C++
int * bd = new int[ g_size ];
bd = * aray;
Niezbyt inteligentnie.

C/C++
* aray = new int[ g_size ];
//..
* aray = bd;
Jw.

C/C++
* aray = bd;
delete[] bd;
Jw.

W tym kodzie chyba nic nie jest zrobione poprawnie. Nawet sizeof jest użyte źle, pomimo tego, że zwracano ci na to uwagę.
P-150283
Mentaris
Temat założony przez niniejszego użytkownika
» 2016-07-26 22:50:27
@pefkos ale teksty typu mało inteligentnie możesz sobie darować (uwierz, to nie motywuje). Liczyłem raczej na opis dlaczego tam widzisz błąd a nie jakieś swoje docinki, w przeciwnym wypadku podziękuje, możesz darować sobie pisanie. Najwidoczniej, nie jestem na tyle inteligentny by sam dopatrzeć się błędu, może ty na moim miejscu byś był. A co do sizeof, to nie poprawiałem go w kodzie na stronie, ponieważ chodziło mi tylko o potwierdzenie czy mateczko to miał na myśli. Co nie znaczy że ignoruje j23 czy ciebie.
P-150290
pekfos
» 2016-07-27 01:07:51
Liczyłem raczej na opis dlaczego tam widzisz błąd a nie jakieś swoje docinki, w przeciwnym wypadku podziękuje, możesz darować sobie pisanie.
Podałem 2 wybrane linie, co tu więcej opisywać? Założyłem, że zinterpretowanie takiego minimalnego wycinka kodu nie będzie stanowić problemu, ale cóż..
1. Alokujesz pamięć, po czym natychmiast tracisz adres pamięci bo przypisujesz do wskaźnika coś innego.
2. To samo co 1. ale wcześniej przynajmniej coś zrobiłeś z traconą pamięcią.
3. Przekazujesz na zewnątrz funkcji adres pamięci, którą natychmiast zwalniasz. Zostajesz całkiem bez pamięci, zwolniłeś jeden blok, 2 bloki zgubiłeś.
C/C++
bd = * aray;
// nic związanego z bd
* aray = bd;
delete[] bd;
Twoja funkcja po prostu zwalnia przekazany blok (nie licząc wycieków pamięci).

Najwidoczniej, nie jestem na tyle inteligentny by sam dopatrzeć się błędu
A próbowałeś? Wykonać kod w myślach? Trudno uwierzyć, że nie zauważyłbyś, że tracisz informacje. W końcu to tylko 2 instrukcje do wykonania i jedna zmienna do pilnowania. Tak jakby sam widok dwóch kolejnych przypisań do jednej zmiennej nie był podejrzany.
P-150294
« 1 » 2
  Strona 1 z 2 Następna strona