#pragma once

#include "expression.h"
#include "debug.h"

class ExpPtr
	{
		Expression * _exp;
		unsigned int * _refCount;
		
		void _copy(const ExpPtr & other);
		void _release();
		
	public:
	//Конструкторы
		ExpPtr(Expression * exp); 
		ExpPtr(const ExpPtr & other);
	//
		ExpPtr & operator=(const ExpPtr & other);
		Expression * operator->();
	//Деструктор
		~ExpPtr();
	//
	};
	
ExpPtr::ExpPtr(Expression *a):_exp(a),_refCount(new unsigned int(1))
{
	//*_refCount = 1;
	*dout << "+";
}

ExpPtr::ExpPtr(const ExpPtr & other) {_copy(other);}

ExpPtr::~ExpPtr() {_release();}

void ExpPtr::_release()
{
	*dout << "-";
	*_refCount = *_refCount - 1;

	if(*_refCount==0)
	{
		delete _exp;
		delete _refCount;
		*dout << "~";
	}
}

void ExpPtr::_copy(const ExpPtr & other)
{
	_exp = other._exp;
	_refCount = other._refCount;
	*other._refCount = *other._refCount + 1;
	*dout << "+";
}


ExpPtr & ExpPtr::operator=(const ExpPtr & other)
{
	if (this->_exp == other._exp) return *this;
	//if (this== &other) return *this;
	this->_release();
	this->_copy(other);

	return *this;
}

Expression * ExpPtr::operator->() {return _exp;}