So i'm trying to run a class with static functions that can find if a binary tree has only 0 and 1 values. in particular, root must be equal to 0, every node equal to 0 must have 1 as left and right children, and every node equal to 1 must have 0 as left and right children.
I tried to create a new class, and compiler doesn't give me any error. This is Binary Tree class code:
#ifndef _Bin_treecC_H_
#define _Bin_treecC_H_
#include "Bin_tree.h"
#include "exceptions.h"
template <class T>
class Bin_treec : public Bin_tree<T, int> {
static const int NIL = -1;
public:
typedef typename Bin_tree<T, int>::value_type value_type;
typedef typename Bin_tree<T, int>::Nodo Nodo;
struct _cella {
Nodo genitore;
Nodo sinistro;
Nodo destro;
value_type valore;
};
typedef struct _cella Cella;
// costruttori e distruttori
Bin_treec();
Bin_treec(int);
~Bin_treec();
// operatori
void create();
bool empty() const;
Nodo root() const;
Nodo parent(Nodo) const;
Nodo sx(Nodo) const;
Nodo dx(Nodo) const;
bool sx_empty(Nodo) const;
bool dx_empty(Nodo) const;
//void costr(Bin_treec<T>);
void erase(Nodo);
T read(Nodo) const;
void write(Nodo, value_type);
void ins_root();
void ins_sx(Nodo);
void ins_dx(Nodo);
private:
int MAXLUNG;
Cella* spazio;
int nNodi;
Nodo inizio;
Nodo libera;
};
template <class T>
Bin_treec<T>::Bin_treec()
{
MAXLUNG = 100;
spazio = new Cella[MAXLUNG];
create();
}
template <class T>
Bin_treec<T>::Bin_treec(int nNodi) : MAXLUNG(nNodi)
{
spazio = new Cella[nNodi];
create();
}
template <class T>
Bin_treec<T>::~Bin_treec()
{
erase(inizio);
delete[] spazio;
}
template <class T>
void Bin_treec<T>::create()
{
inizio = NIL;
for (int i = 0; i < MAXLUNG; i++)
{
spazio[i].sinistro = (i + 1) % MAXLUNG;
}
libera = 0;
nNodi = 0;
}
template <class T>
bool Bin_treec<T>::empty() const
{
return(nNodi == 0);
}
template <class T>
typename Bin_treec<T>::Nodo Bin_treec<T>::root() const
{
return(inizio);
}
template <class T>
typename Bin_treec<T>::Nodo Bin_treec<T>::parent(Nodo n) const
{
if (n != inizio)
return (spazio[n].genitore);
else
return(n);
}
template <class T>
typename Bin_treec<T>::Nodo Bin_treec<T>::sx(Nodo n) const
{
if (!sx_empty(n))
return (spazio[n].sinistro);
else
return(n);
};
template <class T>
typename Bin_treec<T>::Nodo Bin_treec<T>::dx(Nodo n) const
{
if (!dx_empty(n))
return (spazio[n].destro);
else
return(n);
}
template <class T>
bool Bin_treec<T>::sx_empty(Bin_treec<T>::Nodo n) const
{
return (spazio[n].sinistro == NIL); \\HERE VISUAL SAYS THERE IS AN ERROR.
}
template <class T>
bool Bin_treec<T>::dx_empty(Bin_treec<T>::Nodo n) const
{
return (spazio[n].destro == NIL);
}
template <class T>
void Bin_treec<T>::ins_root()
{
if (inizio == NIL)
{
inizio = libera;
libera = spazio[libera].sinistro;
spazio[inizio].sinistro = NIL;
spazio[inizio].destro = NIL;
nNodi++;
}
else
throw RootExists();
}
template <class T>
void Bin_treec<T>::ins_sx(Nodo n)
{
if (inizio == NIL)
throw EmptyTree();
if (n == NIL)
throw NullNode();
if (spazio[n].sinistro != NIL)
throw NodeExists();
if (nNodi >= MAXLUNG)
throw FullSize();
else
{
Nodo q = libera;
libera = spazio[libera].sinistro;
spazio[n].sinistro = q;
spazio[q].sinistro = NIL;
spazio[q].genitore = n;
spazio[q].destro = NIL;
nNodi++;
}
}
template <class T>
void Bin_treec<T>::ins_dx(Nodo n)
{
if (inizio == NIL)
throw EmptyTree();
if (n == NIL)
throw NullNode();
if (spazio[n].destro != NIL)
throw NodeExists();
if (nNodi >= MAXLUNG)
throw FullSize();
else
{
Nodo q = libera;
libera = spazio[libera].sinistro;
spazio[n].destro = q;
spazio[q].genitore = n;
spazio[q].sinistro = NIL;
spazio[q].destro = NIL;
nNodi++;
}
}
template <class T>
void Bin_treec<T>::erase(Nodo n)
{
if (n != NIL) {
if (!sx_empty(n))
erase(spazio[n].sinistro);
if (!dx_empty(n))
erase(spazio[n].destro);
if (n != inizio) {
Nodo p = parent(n);
if (spazio[p].sinistro == n)
spazio[p].sinistro = NIL;
else
spazio[p].destro = NIL;
}
else
inizio = NIL;
nNodi--;
spazio[n].sinistro = libera;
libera = n;
}
else
throw NullNode();
}
template <class T>
T Bin_treec<T>::read(Nodo n) const
{
if (n != NIL)
return (spazio[n].valore);
else
throw NullNode();
}
template <class T>
void Bin_treec<T>::write(Nodo n, value_type a)
{
if (n != NIL)
spazio[n].valore = a;
else
throw NullNode();
}
#endif /* _Bin_treecC_H_ */
this is the class which controls if rules are respected:
#ifndef _ZERO_ONE_BINARY_TREE_H_
#define _ZERO_ONE_BINARY_TREE_H_
#include "bin_treec.h"
using namespace std;
template <class T>
class zero_one_binary_tree
{
public:
static bool is_zero_one(const Bin_treec <T>& B)
{
Bin_treec<T> S = B;
if (!S.empty() && S.root() == 0)
checkzeroone(S.root(),S);
if (checkzeroone(S.root(),S) == false)
return false;
else
return true;
}
static bool checkzeroone(int n, const Bin_treec <T>& H)
{
Bin_treec<T> J = H;
if (n == 0)
{
if (!J.sx_empty(n) && !J.dx_empty(n)) {
if (J.sx(n) == 1 && J.dx(n) == 1)
{
checkzeroone(J.sx(n), J);
checkzeroone(J.dx(n), J);
}
else if (J.sx(n) != 1 || J.dx(n) != 1) {
if ((J.sx_empty(n) && J.dx_empty(n))) {
cout << "nodo foglia, tutto corretto!" << endl;
return true;
}
else{
return false;
}
}
}
}
if (n == 1)
{
if (!J.sx_empty(n) && !J.dx_empty(n)) {
if (J.sx(n) == 0 && J.dx(n) == 0)
{
checkzeroone(J.sx(n), J);
checkzeroone(J.dx(n), J);
}
else if (J.sx(n) != 0 || J.dx(n) != 0) {
if ((J.sx_empty(n) && J.dx_empty(n))) {
cout << "nodo foglia, tutto corretto!" << endl;
return true;
}
else {
return false;
}
}
}
}
}
};
#endif
This is the main:
#include "zero_one_binary_tree.h"
#include <iostream>
using namespace std;
int main() {
Bin_treec<int> T;
typename Bin_treec<int>::Nodo n1 = 0, n2 = 0;
T.ins_root();
T.write(T.root(), 0);
n1 = T.root();
T.ins_sx(n1);
T.ins_dx(n1);
T.write(T.sx(n1), 2);
n1 = T.dx(n1);
T.write(n1, 3);
T.ins_dx(n1);
T.write(T.dx(n1), 4);
T.print();
cout << T;
zero_one_binary_tree<int>::is_zero_one(T);
}
When i try to run the exe, it suddently stops and says that:
Unhandled exception thrown: read access violation.
this->**spazio** was 0xE019E256. occurred
The error reports me to the row i reported inside the code (line 139) and I don't know how to solve it. In my opinion there is a problem with how i'm passing node children but actually I can't solve this. It's not the first time it happens with my code so any help would be appreciated!
Aucun commentaire:
Enregistrer un commentaire