VS2010 nu initializeaza pointeri cu NULL?

Intrebari despre programarea cu VC++ incluzand mediul de dezvoltare, instalare, setari, debugger, compilator, linker si documentatie.
Post Reply
u0m3
Membru
Membru
Posts: 80
Joined: 21 Dec 2008, 19:11
Judet: Bucureşti
Contact:

VS2010 nu initializeaza pointeri cu NULL?

Post by u0m3 » 04 Dec 2009, 21:10

Am intalnit aceasta problema in implementarea listelor inlantuite prin structuri. A se considera urmatorul cod:

Code: Select all

#pragma once
template<typename _T>
class CLinkedList
{
private:
	struct ELEM
	{
		_T m_value;
		ELEM* m_pPrevElem;
		ELEM(_T v, ELEM* prev): m_value(v), m_pPrevElem(prev){};
	};

	ELEM* m_pCurElem;
protected:
public:
	CLinkedList()
	{
	};

	virtual ~CLinkedList()
	{
		ELEM* pCurElem = m_pCurElem;
		ELEM* pNextElem;
		while(pCurElem)
		{
			pNextElem = pCurElem->m_pPrevElem;
			delete pCurElem;
			pCurElem = pNextElem;
		}
	};

	void push(_T val)
	{
		ELEM* p = new ELEM(val, m_pCurElem);
		m_pCurElem = p;
	};

	_T pop(void)
	{
		if(!m_pCurElem)
			throw _T("ERROR");	// custom exception class placeholder
		_T ret = m_pCurElem->m_value;
		ELEM* p = m_pCurElem;
		m_pCurElem = p->m_pPrevElem;
		delete p;
		return ret;
	};
};
Problema este ca in modul Debug ultimul m_pCurElem are valoarea 0xccccccc in loc de 0x0, iar in momentul distrugerii, loop-ul while nu iese si se incearca accesarea unui parametru al unui pointer tip struct, inexistent => exception.


Acesta este comportamentul normal (implicand ca eu sunt fortat sa initializez m_pCurElem cu NULL in constructor) sau este o "chichita" VS2010?


Multumesc anticipat pentru indicatii.


Old-School: If at first you don't succeed, try and try again.
New-School: If at first you don't succeed, destroy every evidence that you have ever tried.
Citate nostime:
  1. Mintile umane sunt ca parasutele... Functioneaza doar daca sunt deschise.
  2. Light travels faster than sound, that's why some people seem Bright ...... untill they Speak...

User avatar
Silviu Ardelean
Senior
Senior
Posts: 1175
Joined: 12 Jul 2007, 09:22
Judet: Timiş
Location: Timisoara
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Silviu Ardelean » 04 Dec 2009, 21:32

Unde aloci tu memorie pentru m_pCurElem? In codul tau, eu nu vad nici un:

Code: Select all

 m_pCurElem = new ELEM(v, prev);

u0m3
Membru
Membru
Posts: 80
Joined: 21 Dec 2008, 19:11
Judet: Bucureşti
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by u0m3 » 04 Dec 2009, 21:48

In push(_T val).
Chiar m_pCurElem = new ELEM(v, prev) nu ai cum sa vezi, acesta fiind si scopul implementarii: de fiecare data cand adaugi un element in lista/stiva, creezi o noua structura careia ii specifici ca elementul precedent este cel curent, apoi cel curent devine cel pe care tocmai l-am creat.

Am vazut o impementare asemanatoare intr-un alocator de memorie tip arena (sau cel putin asa mi-a zis cineva ca se numeste). Din acest motiv sunt nedumerit: comform acelui exemplu, ar trebui sa mearga loop-ul while din destructor, doar ca la mine arunca o exceptie conform careia accesez o zona de memorie interzisa ("Access violation reading location ...").
Last edited by u0m3 on 04 Dec 2009, 21:56, edited 1 time in total.
Old-School: If at first you don't succeed, try and try again.
New-School: If at first you don't succeed, destroy every evidence that you have ever tried.
Citate nostime:
  1. Mintile umane sunt ca parasutele... Functioneaza doar daca sunt deschise.
  2. Light travels faster than sound, that's why some people seem Bright ...... untill they Speak...

User avatar
jos8cal
Banned
Banned
Posts: 86
Joined: 16 Feb 2008, 02:01

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by jos8cal » 04 Dec 2009, 21:54

Pai de ce sa aiba valoarea 0x0 si nu 0xFF342121 in Debug? Valoarea din variabila aia este problema ta, tu ii dai un sens (Bine, mai putin daca esti in .NET, ca acolo este the land of milk and honey). So, nu e nicio chichita VS2010, trebuie sa-ti initializezi variabilele. Pune m_pCurElem = 0 in constructor si gata.

LE: Si btw, valoarea 0xcccccc are un sens, nu e random shit, tocmai din motivul asta exista modul Debug.

0xFDFDFDFD No man's land (normally outside of a process)
0xDDDDDDDD Freed memory
0xCDCDCDCD Uninitialized (global)
0xCCCCCCCC Uninitialized locals (on the stack)
Last edited by jos8cal on 04 Dec 2009, 21:58, edited 1 time in total.

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3778
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Ovidiu Cucu » 04 Dec 2009, 21:56

u0m3 wrote:VS2010 nu initializeaza pointeri cu NULL?
NU.
Daca ai folosi o scula de analiza statica de cod aceasta ar face spume la gura daca ti-ar gasi variabile neinitalizate (pointerul este si el o variabila).
Pentru o variabila membru, te obliga chiar sa o initializazi in lista de initializare a constructorului, indiferent ce faci cu ea mai departe.
In cazul tau trebuie sa scrii

Code: Select all

   CLinkedList() : m_pCurElem(NULL)
   {
   };
In cazul cand nu faci aceasta, in versiunea release e posibil ca, in functie de sistemul de operare pe care ruleaza, o variabila neinitializata sa se afle undeva intr-o zona de memorie umpluta dinainte cu zerouri dar tot atat de bine sa contina te miri ce altceva (in limbajul programatorului roman se spune "carcalaci").
In versiunea debug, variabilele neinitializate se umplu cu 0xCC-uri tocmai ca, aruncand o privire in debugger sa-ti dai seama c-ai uitat ceva...
Vezi articolasul acesta: http://www.codexpert.ro/articole.php?id=7

Deci, regula #0 a variabilelor:
Poa sa ninga, poa sa ploua
Sa se rupa ****-n doua
Nu lasa neinitializata variabila cea noua!
. :D ;)

User avatar
Marius Bancila
Fondator
Fondator
Posts: 2344
Joined: 11 Jul 2007, 11:45
Judet: Timiş
Location: Timisoara
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Marius Bancila » 04 Dec 2009, 22:32

Nu are nici o legatura cu VS 2010. Asa e de cand lumea. Valorile alea "ciudate" le-am explicat la inceputul acestui articol: http://www.codeguru.com/cpp/w-p/win32/t ... php/c9535/.

In release vei avea valorile initializate cu 0, dar ar trebui sa faci tu explicit asta.

PS: ce imi place la alte limbaje ca C# e ca initializeaza implicit orice variabile cu valorile default pt. tipul respectiv, indiferent de setarile de build. Standardul C++ nu specifica nimic de genul acesta, din care cauza exista acest comportament diferit in VC++ in DEBUG si RELEASE, depinzand de seatarile de compilare.
Marius Bancila
Fondator Codexpert, Microsoft MVP VC++
Site personal | Blog

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3778
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Ovidiu Cucu » 04 Dec 2009, 23:13

Marius Bancila wrote:PS: ce imi place la alte limbaje ca C# e ca initializeaza implicit orice variabile cu valorile default pt. tipul respectiv, indiferent de setarile de build. Standardul C++ nu specifica nimic de genul acesta, din care cauza exista acest comportament diferit in VC++ in DEBUG si RELEASE, depinzand de seatarile de compilare.
La vremea cand au pus bazele limbajului C, domnii Kernighan si Ritchie n-au gandit deloc rau cand au lasat posibilitatea programatorilor sa lase neinitializate variabilele (n-a indraznit sa-i contrazica nici Stroustrup si nici cei din comitetul de standardizare :)).
Dupa cum isi amintesc multi programatori de C++ si probabil chiar si cativa programatori de C#, in C variabilele locale se declara la inceput de bloc.
De exemplu

Code: Select all

{
   int sum;  /* usually, here sum is garbage on the stack */
   /* some code here */
   sum = a + b; /* sum takes a meaningful value */
   /* some other code here */ 
   printf("sum=%d", sum);
}
Daca in codul de mai sus compilatorul ar pune automat o valoare default, sa zicem 0, ar pune cel putin o instructine procesor care sa faca asta, logic fara rost, ducand la micsorarea performantei.

Din pacate, in practica programarii (mai binezis a "scrierii de cod" :)) s-au facut tone de greseli de genul

Code: Select all

{
   int sum;  /* usually, here sum is garbage on the stack */
   /* some code here */
   /* nothing like 'sum = ...' then sum is still garbage */
   printf("sum=%d", sum); /*print garbage*/
}
Cu pointerii treaba-i si mai naspa. Folosind pointeri nenitializati, avand te miri ce valori arbitrare, putem fi multumiti daca rezulta un "access violation", altfel Dumnezeu cu mila ce se poate intampla.

// Cat despre limbajele inalte (C#, VB, etc): intradevar ajuta programatori cascati sa nu greseasca si nici sa-si oboseasca capusorul si manutele cu initializarea variabilelor.
// Dar eu unul, nici nu indraznesc sa ma gandesc cat amar de instructini masina baga-n spate pentru asta. ;)

User avatar
Silviu Ardelean
Senior
Senior
Posts: 1175
Joined: 12 Jul 2007, 09:22
Judet: Timiş
Location: Timisoara
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Silviu Ardelean » 04 Dec 2009, 23:22

Ovidiu, daca tot ai amintit de analizatoare statice de cod, sa nu uitam ca acestea nu agreeaza declararea variabilelor neinitializate. :D

User avatar
Ovidiu Cucu
Fondator
Fondator
Posts: 3778
Joined: 11 Jul 2007, 16:10
Judet: Iaşi
Location: Iasi
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Ovidiu Cucu » 04 Dec 2009, 23:30

Silviu Ardelean wrote:Ovidiu, daca tot ai amintit de analizatoare statice de cod, sa nu uitam ca acestea nu agreeaza declararea variabilelor neinitializate. :D
"Nu agreeaza" e putin spus. Cred c-am zis si mai inainte. Turbeaza (ochi injectati, spume la gură, muşcă...). :biggrin:

User avatar
Silviu Ardelean
Senior
Senior
Posts: 1175
Joined: 12 Jul 2007, 09:22
Judet: Timiş
Location: Timisoara
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Silviu Ardelean » 04 Dec 2009, 23:56

Ovidiu Cucu wrote:
Silviu Ardelean wrote:Ovidiu, daca tot ai amintit de analizatoare statice de cod, sa nu uitam ca acestea nu agreeaza declararea variabilelor neinitializate. :D
"Nu agreeaza" e putin spus. Cred c-am zis si mai inainte. Turbeaza (ochi injectati, spume la gură, muşcă...). :biggrin:
Tocmai deaia am amintit de situatie. :twisted:

User avatar
Marius Bancila
Fondator
Fondator
Posts: 2344
Joined: 11 Jul 2007, 11:45
Judet: Timiş
Location: Timisoara
Contact:

Re: VS2010 nu initializeaza pointeri cu NULL?

Post by Marius Bancila » 06 Dec 2009, 21:20

Daca in codul de mai sus compilatorul ar pune automat o valoare default, sa zicem 0, ar pune cel putin o instructine procesor care sa faca asta, logic fara rost, ducand la micsorarea performantei.
Intradevar, la inceputul anilor '70 asta era important. Acum nimeni nu se mai gandeste la asa ceva, pt. ca nu mai are sens. Simplitatea si corectitudinea, programatorul sa aiba cat mai putine sanse sa faca greseli, sunt lucrurile care conteaza.
Marius Bancila
Fondator Codexpert, Microsoft MVP VC++
Site personal | Blog

Post Reply