Wskaźniki czy dobrze to ogarniam?

0
#include "stdafx.h"
#include<iostream>

using namespace std;

int main()
{
    int a = 5; //Przypisuję do a wartośc 5
    int *tomek = new int; //Tworzę wskaźnik, plus przypisuję mu new tak by było miejsce w pamieci do wrzutu danych
    *tomek = a;//Wskaźnik wskazuje teraz na a
    cout <<a<<endl;
    cout << *tomek<<endl;
    a = 7;//Zmieniam wartość a na 7, autoamtycznie zmienia się wartość na jaką wskazuje wskaźnik
    cout << a << endl;
    cout << *tomek << endl;
    //Czy tutaj przed zmianą wskazania, trzeba go wyzerować delete i na nowo wskazać, lub w tym przypadku przypisać jego wartośc, by na coś wskazywał. 
    *tomek = 1;//Przypisuje do wskaźnika wartość 1, po to było to new int, bez tego niemógłbym do niego przypisać wartości bo nie błoby miejsca w pamięci
    cout << a << endl;
    cout << *tomek << endl;
    delete tomek;//Zwalniam pamięć, new int idzie do kosza. 
    //Teraz powinno się chyba przypsiać do wskaźnika Nulla by na coś wskazywał, ps. dzieje się coś jak na nic nie wskazuje po usnięciu jego zawartości new?

    system("pause");
    return 0;
}

Więc, tak jako że zamierzam wejść w klasy, chcę dobrze najpierw ogarniać podstawy, pętle, tablice mam już przećwiczone, znaczy się wiadomo cały czas dochodzą nowe rzeczy, także trudno pisać że się coś ogarnia jak podstawy to nawet nie są podstawy, ale powoli a do przodu, mam takie małe pytanie czy po powyższym kodzie, który w zasadzie nic nie robi, chodzi mi tylko o idee działania wskaźników, czy dobrze to ogarniam, w kwestii zwalniania pamięci zwłaszcza, z góry dzięki za ocenę, pomoc.

0
    int a = 5;
    int *tomek = new int;
    *tomek = a;
    a = 7;//Zmieniam wartość a na 7, autoamtycznie zmienia się wartość na jaką wskazuje wskaźnik

Nie. Niby dlaczego miałaby się zmienić?

0

Faktycznie, gdybym nie dawał new, pewnie by się zmieniło a tak nadal tkwi w pamięci póki jej nie zwolnię, tak jak robię to dalej w kodzie. Ok dzięki.

0

Twój przykład:

using namespace std;

int main()
{
    int a = 5;
    int *tomek = new int;
    *tomek = a; // wskaźnik pobrał wartość a i umieścił ją pod adresem wcześniej otrzymanym przez polecenie new
    cout <<a<<endl;
    cout << *tomek<<endl;
    a = 7; // zmieni się tylko wartość a, tomek zostanie 5
    cout << a << endl;
    cout << *tomek << endl;
    *tomek = 1; // zmieniasz wartość w adresie wskazywanym przez tomka na 1
    cout << a << endl;
    cout << *tomek << endl;
    delete tomek;

}

Jak powinno być (bazując na Twoich komentarzach):

using namespace std;

int main()
{
    int a = 5;
    //int *tomek = new int; nie jest potrzebne w tej wersji
    int *tomek = &a; // wskaźnik wskazuje na a
    cout <<a<<endl;
    cout << *tomek<<endl;
    a = 7; // teraz również zmieni się wartość wskazywana przez wskaźnik
    cout << a << endl;
    cout << *tomek << endl;
    *tomek = 1; // wartość a zmienia się na 1
    cout << a << endl;
    cout << *tomek << endl;
    delete tomek; // nie ma potrzeby, po zakończeniu tego fragmentu kodu miejsce zajmowane przez a i tak zostanie zwolnione
}
1
Zsan napisał(a):
delete tomek; // nie ma potrzeby, po zakończeniu tego fragmentu kodu miejsce zajmowane przez a i tak zostanie zwolnione

}

Brak zwolnienia pamięci przez program przed jego zakończeniem, jest błędem pomimo tego że system operacyjny usuwając proces, posprząta pamięć. Funkcję main() należy traktować tak samo jak i inne funkcje lub zasięgi które pojawić się mogą w programie. Przed funkcją main() oraz po jej zakończeniu można także uruchamiać kod. Jeśli nie posprzątasz po sobie, istnieje ryzyko nieprawidłowego działania tego kodu.

0
   *tomek = 1

Czy przed tym trzeba wyzerować wskaźnik, skoro zmieniam wskazanie wskaźnika i przypisuję mu jakby 1, piszę jakby bo jakbym nie dał new to nie mógłbym tak zrobić. Niby się nie pluje, ale jak to powinno byc robione zgodnie z standardami, przed takim przypisaniem muszę go usunąć z pamięci czy też nie, skoro w następnej linii wartość zostanie zmieniona?

0

@Zsan chyba zapędziłeś się z tym delete.... Takie cos jak pokazałeś zrobi bum... Jak masz system z ochrona pamięci, będzie to tylko bm zamyanego programu, ale nie zawsze tak musi być... Delete używamy tylko wtedy, gdy wczesniej dynamicznie przyznaliśmy pamięć!!!

0

@kaczus rzeczywiście może powinienem był wykomentować tę linijkę by nie było żadnych wątpliwości, że użycie tego delete w drugim wypadku jest niepoprawne

0
hyouka22 napisał(a):

*tomek = a;//Wskaźnik wskazuje teraz na a

Nie, przepisałeś wartość zmiennej a w miejsce wskazywane przez tomek. To co opisuje komentarz robi się tak: tomek = &a;

a = 7;//Zmieniam wartość a na 7, autoamtycznie zmienia się wartość na jaką wskazuje wskaźnik

Nie, ze względu na powyższe.

0
zarazek napisał(a):
hyouka22 napisał(a):
*tomek = a;//Wskaźnik wskazuje teraz na a

Nie, przepisałeś wartość zmiennej a w miejsce wskazywane przez tomek. To co opisuje komentarz robi się tak: tomek = &a;

a = 7;//Zmieniam wartość a na 7, autoamtycznie zmienia się wartość na jaką wskazuje wskaźnik

Nie, ze względu na powyższe.

Ok, rozumiem, to co mam poniżej to kod bez new, tutaj mam to przypisanie. Dzięki za wyjaśnienie.

        int b = 6;
        int *arek;
        arek = &b;
        cout << b << endl;
        cout << *arek << endl;
        cout << &b << endl;
        cout << &*arek << endl;

Teraz mam taki mały random w kwestii tego delete na końcu kodu, stosujemy go, czy nie, bo na logikę po wyjściu z klamry ta zmienna znika, w tym przypadku jest w mainie, ale powiedzmy, że robię funkcję z użyciem tabeli i tam używam wskaźnika, niby po końcu klamry znika zmienna, ale czy mam użyć delete by usnąć wtedy wskaźnik i potem przypisać do niego NULLA czy to zbędne, chodzi mi o to by nie było potem problemów z zwalnianiem pamięci.

1 użytkowników online, w tym zalogowanych: 0, gości: 1, botów: 0