Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

I need to design a program using linked list stack to receive an input then gene

ID: 3771191 • Letter: I

Question

I need to design a program using linked list stack to receive an input then generate its output according to the operand and operator inserted. For example if I typed "1 2 3 X C" it will push only the operand to the stack so 1 2 3 will be pushed then reading X to print out the stack, and C to clear the stack. The other operators are S and P to sum and multiply all the values in the stack, pop all values then put the result back to the stack. + - * / will pop two operand then push only result back to the stack, ! to negative an operand (pop then push the result back to the stack), and $ to end the program.

My question is I'm using 'valgrind' to detect memory leaks and I always comeup with at least 24 bytes lost. I couldn't remember the exact amount but as I inputted more lines it sometimes increased to 48 bytes or 96. I tried to input just 1 > enter > $, the program already have the memory leaks of 24 bytes. I can't find why I have the leaks. Could anyone help me or explain why there's a memory leaks?

Below are the codes I'm coding, I was given the abstractstack.h then I need to implement LLStack.h and program.cpp by myself.

program.cpp

#include <string>
#include <cstdlib>
#include <iostream>
#include "abstractstack.h"
#include "llstack.h"

using namespace std;
int main ()
{
const char OPER[10]={'+','-','*','/','!','S','P','X','C','$'};
LLStack <int> A;
A.clear();
char in1;
int x,y;
int loop1=0;
int positionOper=0;
int result=0;
bool check=false;
  
do
{
cin>>in1;
check=false;
loop1=0;
while(loop1<10)
{
if(in1==OPER[loop1])
{
check=true;
positionOper=loop1;
loop1=10; //make it stop looping
}
loop1++;
}
if(check==false)
{
x=in1-'0';
   //x=atoi(in1.c_str());
A.push(x);
}
else
{
if((A.isEmpty()==false)&&(positionOper<4)) //+ - * /
{
   x=A.top();
   A.pop();
   y=A.top();
   A.pop();
}  
switch(positionOper)
{
   case 0:
result=x+y;
       break;
   case 1:
result=y-x;
       break;
   case 2:
result=x*y;
       break;
   case 3:
result=y/x;
       break;
   case 4:
       x=A.top();
result=(-1)*x;
       break;
   case 5:
       result=A.sumLLStack();
       A.clear();
       break;
   case 6:
       result=A.productLLStack();
       A.clear();
       break;
   case 7:
       A.printList();
       break;
   case 8:
   A.pop();
   A.pop();
       A.clear();
       break;
   }

if(positionOper<4) // + - * /
{
   A.push(result);
   }
   else if(positionOper==4)
   {
   A.pop();
A.push(result);
   }
   }
}while(in1!='$');
  
A.clear();
return 0;
}

Abstractstack.h

/* @file: abstractstack.h
* Definition of templated class stack
* Implementing A.D.T. Stack
* @C - Galaxy Express Software
*
* Version 15.3.0
*/

/* ____________________
/
| AbstractStack Class |
____________________/

Purpose: Implements a Stack ADT using.

Error Handling: Whenever a function is given invalid parameter values
THROWS a 'Oops' object.

*/
#ifndef ABSTRACTSTACK_H
#define ABSTRACTSTACK_H

#include <string>

using namespace std;

/* --------------- Class 'Oops' ---------------
Class
Thrown when an error is encountered.
Member 'm_msg' stores an error message.
*/
class Oops
{
   string m_errormsg;
public:
   Oops(const string &msg) : m_errormsg(msg) {}
   const string& getMsg() const
   {
       return m_errormsg;
   }
};


/* --------------- Abstract Class AbstractStack --------------- */
template < typename T >
class AbstractStack
{
public:

// Purpose: Checks if a stack is empty
// Returns: 'true' if the stack is empty
// 'false' otherwise
virtual bool isEmpty() const = 0;


// Purpose: looks at the top of the stack
// Returns: a const reference to the element currently on top of the stack
// Exception: if the stack is empty, THROW a 'Oops' object with an error message!!!
virtual const T& top() const throw ( Oops ) = 0;

// Purpose: push an element into the stack
// Parameters: x is the value to push into the stack
// Postconditions: x is now the element at the top of the stack,
virtual void push(const T& x) = 0;

// Purpose: pop the stack
// Postconditions: the element formerly at the top of the stack has
// been removed
// Note: Poping an empty stack results in an empty stack.
virtual void pop() = 0;


// Purpose: clears the stack
// Postconditions: the stack is now empty
virtual void clear() = 0;


// Purpose: DESTRUCTOR
virtual ~AbstractStack() {}

};

#endif

LLStack.h

#ifndef LLSTACK_H
#define LLSTACK_H

#include "abstractstack.h"

template <typename T>
class LLStack: public virtual AbstractStack<T>
{
protected:
   T m_data;
   LLStack* m_next;
  
public:
LLStack(): m_next(NULL){}
  
int getData(const int position)
{
   int data=0;
   if(!isEmpty())
   {
   if(position==0)
data=m_data;
else if(position==1)
data=m_next->m_data;
}
return data;
}
  
  
// Purpose: Checks if a stack is empty
// Returns: 'true' if the stack is empty
// 'false' otherwise
bool isEmpty() const
{
if(m_next==NULL)
return true;
else
return false;
}


// Purpose: looks at the top of the stack
// Returns: a const reference to the element currently on top of the stack
// Exception: if the stack is empty, THROW a 'Oops' object with an error message!!!
const T& top() const throw ( Oops )
{
if(m_next!=NULL)
   return this->m_data;
   else
   throw Oops("The stack is empty");
}

// Purpose: push an element into the stack
// Parameters: x is the value to push into the stack
// Postconditions: x is now the element at the top of the stack,
void push(const T& x)
{
LLStack* tmp=new LLStack;
tmp->m_data=m_data;
tmp->m_next=m_next;
m_data=x;
m_next=tmp;
tmp=NULL;
delete tmp;
}

// Purpose: pop the stack
// Postconditions: the element formerly at the top of the stack has
// been removed
// Note: Poping an empty stack results in an empty stack.
void pop()
{
if(m_next!=NULL)
{
   LLStack* tmp=m_next;
   m_data=tmp->m_data;
   m_next=tmp->m_next;
   delete tmp;
   }
}


// Purpose: clears the stack
// Postconditions: the stack is now empty
void clear()
{
m_next=NULL;
while(isEmpty()==false)
{
pop();
}
}
  
void printList()
{
cout<<"[ ";
if(isEmpty()==false)
{
LLStack* tmp=this;
  
   while(!(tmp->isEmpty()))
   {
   cout<<tmp->m_data<<" ";
   tmp=tmp->m_next;
}
// delete tmp;
   }
   cout<<"]"<<endl;
      
}

int sumLLStack()
{
LLStack* tmp=this;
   int result=0;
   while(tmp->m_next!=NULL)
   {
   result+=tmp->m_data;
tmp=tmp->m_next;
   }
   delete tmp;
   return result;
}
  
int productLLStack()
{
LLStack* tmp=this;
   int result=1;
   while(tmp->m_next!=NULL)
   {
   result*=tmp->m_data;
tmp=tmp->m_next;
   }
   delete tmp;
   return result;
}

  
~LLStack()
{
m_next=NULL;
}  

};


#endif

#include <string>
#include <cstdlib>
#include <iostream>
#include "abstractstack.h"
#include "llstack.h"

using namespace std;
int main ()
{
const char OPER[10]={'+','-','*','/','!','S','P','X','C','$'};
LLStack <int> A;
A.clear();
char in1;
int x,y;
int loop1=0;
int positionOper=0;
int result=0;
bool check=false;
  
do
{
cin>>in1;
check=false;
loop1=0;
while(loop1<10)
{
if(in1==OPER[loop1])
{
check=true;
positionOper=loop1;
loop1=10; //make it stop looping
}
loop1++;
}
if(check==false)
{
x=in1-'0';
   //x=atoi(in1.c_str());
A.push(x);
}
else
{
if((A.isEmpty()==false)&&(positionOper<4)) //+ - * /
{
   x=A.top();
   A.pop();
   y=A.top();
   A.pop();
}  
switch(positionOper)
{
   case 0:
result=x+y;
       break;
   case 1:
result=y-x;
       break;
   case 2:
result=x*y;
       break;
   case 3:
result=y/x;
       break;
   case 4:
       x=A.top();
result=(-1)*x;
       break;
   case 5:
       result=A.sumLLStack();
       A.clear();
       break;
   case 6:
       result=A.productLLStack();
       A.clear();
       break;
   case 7:
       A.printList();
       break;
   case 8:
   A.pop();
   A.pop();
       A.clear();
       break;
   }

if(positionOper<4) // + - * /
{
   A.push(result);
   }
   else if(positionOper==4)
   {
   A.pop();
A.push(result);
   }
   }
}while(in1!='$');
  
A.clear();
return 0;
}

Explanation / Answer

Memory leaks happens in a program whenever a allocated memory is there and it is not freed.

The problem is there in the print list function where the allocated temp is not deleted.   void printList()
{
cout<<"[ ";
if(isEmpty()==false)
{
LLStack* tmp=this;
  
   while(!(tmp->isEmpty()))
   {
   cout<<tmp->m_data<<" ";
   tmp=tmp->m_next;
}
// delete tmp;
   }
   cout<<"]"<<endl;

delete temp should not be commented here. This should fix the leak problem.

Hire Me For All Your Tutoring Needs
Integrity-first tutoring: clear explanations, guidance, and feedback.
Drop an Email at
drjack9650@gmail.com
Chat Now And Get Quote