[C++ ]Lista i Access violation raz jest raz niema

0

Witam, napisałem listę:

CPP:

//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
//\\//\\ TLLista //\\//\\ TLLista //\\//\\ TLLista //\\//\\ TLLista //\\//\\
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
TLLista::TLLista()
{
wsk_p = NULL;
wsk_k = NULL;
}
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
void TLLista::dodaj(String nazwa_zmiennej, Extended wartosc)
{
TLListaElement *a;
a = (struct TLListaElement*)malloc(sizeof(struct TLListaElement));
a->nazwa = nazwa_zmiennej;  //////////////////////////////////////////////////////////////////////////////////////////////////////////////// <--- TU
a->wartosc = wartosc;
if (wsk_p==NULL && wsk_k==NULL)
  {
  wsk_p=a;
  wsk_k=a;
  a->next=NULL;
  a->prev=NULL;
  }
else
  {
  a->prev = wsk_k;
  a->next = NULL;
  (wsk_k)->next = a;
  (wsk_k)=a;
  }
}
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
void TLLista::usun_ostatni()
{
TLListaElement *a;
if ((wsk_k)!=NULL)
  {
  if ((wsk_k)==(wsk_p))
      {
      wsk_k=NULL;
      free(wsk_p);
      wsk_p=NULL;
      }
  else
      {
      a=(wsk_k)->prev;
      a->next=NULL;
      free(wsk_k);
      wsk_k=a;
      };
  }
}
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
void TLLista::usun_wszystko()
{
while ((wsk_k)!=NULL) usun_ostatni();
}
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
Extended TLLista::jaka_wartosc(String nazwa_zmiennej)
{
TLListaElement *temp_wsk;
temp_wsk = wsk_p;

while ((*temp_wsk).nazwa != nazwa_zmiennej)
    {
    if ((*temp_wsk).next == NULL )
      {
      Form1->p_Show_Message("Błąd", "Niemożna odczytać wartości zmiennej, ponieważ jeszcze jej nie zainicjowano.",2);
      return 0;
      }
    temp_wsk = (*temp_wsk).next;
    }
return (*temp_wsk).wartosc;
}
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
void TLLista::zmien_wartosc(String nazwa_zmiennej, Extended wartosc)
{
TLListaElement *temp_wsk;
temp_wsk = wsk_p;

if ((wsk_k)!=NULL)
  {
  while ((*temp_wsk).nazwa != nazwa_zmiennej)
    {
    if ((*temp_wsk).next == NULL )
      {
      dodaj(nazwa_zmiennej, wartosc);
      }
    temp_wsk = (*temp_wsk).next;
    }
  (*temp_wsk).wartosc = wartosc;
  }
else
  {
  dodaj(nazwa_zmiennej, wartosc);  
  }
}
//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\//\\
TLLista::~TLLista()
{
usun_wszystko();
}

Header

struct TLListaElement
  {
  TLListaElement *next, *prev;
  String nazwa;
  Extended wartosc; // od 3,6x10^-4951 do 1,1x10^4932
  };

class TLLista
  {
  private:  
    TLListaElement *wsk_p,*wsk_k;
  public:
    TLLista();
    ~TLLista();
    void usun_ostatni();
    void usun_wszystko();    
    void dodaj(String nazwa_zmiennej, Extended wartosc);
    Extended jaka_wartosc(String nazwa_zmiennej);
    void zmien_wartosc(String nazwa_zmiennej, Extended wartosc);    
  };

A używam tak

Zmienne = new TLLista();

Zmienne->dodaj("addd",2);
Zmienne->dodaj("dcdd",7);
Zmienne->dodaj("ddbd",3);
Zmienne->dodaj("dddt",5);
Zmienne->dodaj("ddtd",4);

Problem jest w tym że czasem pojawia się komunikat o błędzie "Access violation". Błąd występuje w czasie wykonania przypisywania (linijka w kodzie zaznaczona jako <--- TU)

0

problem polega na tym, że tworzysz obiekt TLListaElement na stercie za pomocą malloc zamiast operatorem new. Skoro używasz już klas to zapomnij o malloc!
Efekt jest taki, że masz niezainicjowane pole TLListaElement::nazwa, które WYMAGA wywołania konstruktora. W momencie posłużenia się tym polem standardowa biblioteka poddaje się.

0

Wielkie dzięki. Ten fragment był kopiowany ;) Trzeba zamić 1 linijke na 2 z kodu poniżej.

//a = (struct TLListaElement*)malloc(sizeof(struct TLListaElement));
a = new TLListaElement;

Temat do zamknięcia może ktoś będzie szukał jeszcze.

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