0

I am getting Memory Leak error. Note: I got the output I want but there is memory leak at the end(Compile with Valgrind(it is memory leak checking tool)) In total I have 5 Files

main.cpp

#include<iostream>
#include "Minister.h"
#include "Minister.h" // intentional
#include "MemberParliament.h"
#include "MemberParliament.h" // intentional

using namespace std;
using namespace sdds;

void printHeader(const char* title)
{
   char oldFill = cout.fill('-');
   cout.width(62);
   cout << "" << endl;

   cout << "|> " << title << endl;

   cout.fill('-');
   cout.width(62);
   cout << "" << endl;
   cout.fill(oldFill);
}

void newElections(Minister& aMinister, const char* district, const char* newPM, double year)
{
   aMinister.NewDistrict(district);
   aMinister.changePM(newPM);
   aMinister.assumeOffice(year);
   cout << "Status of New Election " << aMinister << endl << endl;
}


int main()
{

   printHeader("Person 1: MemberParliament");

   MemberParliament mp("MP9403", 59);
   cout << mp << endl << endl;

   mp.NewDistrict("Scarborough");
   mp.NewDistrict("Mississauga");
   mp.NewDistrict("Huron County");

   cout << endl << mp << endl << endl;

   printHeader("Person 2: Read/Write");
   cin >> mp;
   cout << endl << mp << endl << endl;

   printHeader("Person 3: Minister");

   Minister aMinister("MP9573", 63, 2003, "Harper", "Pickering");
   cout << endl;

   newElections(aMinister, "Whitby", "Trudeau", 2007);

   newElections(aMinister, "Kitchener", "Biden", 2010);

   newElections(aMinister, "Oakville", "Trump", 2015);

   printHeader("Person 4: Read/Write");
   cin >> aMinister;
   cout << endl << (MemberParliament)aMinister;
   cout << endl << aMinister << endl << endl;
   return 0;
}

Minister.h

#ifndef SDDS_MINISTER_H
#define SDDS_MINISTER_H
#include <iostream>
#include "MemberParliament.h"
namespace sdds{
    class Minister : public MemberParliament{
        private:
        char *pm;
        double year;

        public:
        //a custom constructor that receives the following information about the Minister: idd, age, the year assumed office, district, and name of the prime minister. Call the constructor from the base class and pass the relevant data to it. update the private data members of the Minister accordingly
        Minister(const char* id, int age, int year, const char* newPM,const  char* newDistrict);
        ~Minister();
        void changePM(const char* pm);
        void assumeOffice(double year);
        std::ostream& write(std::ostream& os);
        std::istream& read(std::istream& in);
    };

    //overload the insertion and extraction operators to insert a Minister into a stream and extract a Minister from a stream. These operators should call the write/read member functions in the class Minister.
    std::ostream& operator<<(std::ostream& os,const Minister& min);
    std::istream& operator>>(std::istream& in, Minister& min);
}
#endif // SDDS_MINISTER_H

Minister.cpp

#include <iostream>
#include <string.h>
#include "Minister.h"
#include "MemberParliament.h"
using namespace std;
namespace sdds
{
    // implement base class constructor with child class constructor
    Minister::Minister(const char* id, int age, int year, const char* newPM,const  char* newDistrict) : MemberParliament(id, age, newDistrict){
        this->year = year;
        this->pm = new char[strlen(newPM) + 1];
        strcpy(this->pm, newPM);
    }
    void Minister::changePM(const char *pm)
    {
        delete[] this->pm;
        this->pm = new char[strlen(pm) + 1];
        strcpy(this->pm, pm);
    }
    void Minister::assumeOffice(double year)
    {
        this->year = year;
    }
    std::ostream &Minister::write(std::ostream &os)
    {
        MemberParliament::write(os);
        os <<" |" <<" " << this->pm << "/" << this->year;
        return os;
    }
    std::istream &Minister::read(std::istream &in)
    {
        MemberParliament::read(in);
        cout << "Reports TO: ";
        in >> this->pm;
        cout << "Year Assumed Office: ";
        in >> this->year;
        return in;
    }
    std::ostream &operator<<(std::ostream &os,const Minister &min)
    {
        Minister temp = min;
        temp.write(os);
        return os;
    }
    std::istream &operator>>(std::istream &in, Minister &min)
    {
        min.read(in);
        return in;
    }
    Minister::~Minister()
    {
        //delete[] this->pm;
    }

}

MemberParliament.h

#ifndef SDM_MEMBERPARLAMENT_H
#define SDM_MEMBERPARLAMENT_H
#include <iostream>
using namespace std;
namespace sdds{
    class MemberParliament{
        private:
        char *p_id;
        char *district;
        int mp_age;

        public:
        //A custom constructor that receives as parameters the MP Id and age. Set the district the MP represents as Unassigned. Assume all data is valid.
        MemberParliament(const char* id, int age);
        
        MemberParliament(const char* id, int age, const  char* newDistrict);
        ~MemberParliament();
        void NewDistrict(const char* district);
        ostream& write(ostream& os);
        istream& read(istream& in);
    };
    
    std::ostream& operator<<(std::ostream& os,const MemberParliament& mp);
    std::istream& operator>>(std::istream& in, MemberParliament& mp);
    
}
#endif // SDM_MEMBERPARLAMENT_H

MemberParliament.cpp

#include <iostream>
#include <string.h>
#include "Minister.h"
#include "MemberParliament.h"
using namespace std;
namespace sdds
{
    
    MemberParliament::MemberParliament(const char *id, int age, const char *newDistrict)
    {

        this->p_id = new char[strlen(id) + 1];
        strcpy(this->p_id, id);
        this->mp_age = age;
        this->district = new char[strlen(newDistrict) + 1];
        strcpy(this->district, newDistrict);
        printf("|%8s| |          Unassigned ---> %-23s|\n", this->p_id, district);
    }

    MemberParliament::MemberParliament(const char *id, int age)
    {
        //use malloc
        this->p_id = new char[strlen(id) + 1];
        strcpy(this->p_id, id);
        this->mp_age = age;
        
        //set "Unassigned" as default district
        this->district = new char[strlen("Unassigned") + 1];
        strcpy(this->district, "Unassigned");
    }

    void MemberParliament::NewDistrict(const char *district)
    {
        /*print like this:
        |  MP9403| |          Unassigned ---> Scarborough            |
        |  MP9403| |         Scarborough ---> Mississauga            |
        |  MP9403| |         Mississauga ---> Huron County           |
        */
      
        printf("|%8s| |%20s ---> %-23s|\n", this->p_id, this->district, district);
        if (this->district != nullptr)
        {
            delete[] this->district;
        }
        this->district = new char[strlen(district) + 1];
        strcpy(this->district, district);
        // if district is "Unassigned", set it to nullptr
    }
    std::ostream &MemberParliament::write(ostream &os)
    {
        
        os << "| " << this->p_id << " | " << this->mp_age << " | " << this->district;

        return os;
    }
    std::istream &MemberParliament::read(istream &in)
    {
        cout << "Age: ";
        in >> this->mp_age;
        cout << "Id: ";
        in >> this->p_id;
        cout << "District: ";
        in >> this->district;
        return in;
    }

    // overload the insertion operator to print the MemberParliament object
    std::ostream &operator<<(std::ostream &os, const MemberParliament &mp)
    {
        MemberParliament temp = mp;
        temp.write(os);
        return os;
    }
    // overload the extraction operator to read the MemberParliament object
    std::istream &operator>>(std::istream &in, MemberParliament &mp)
    {
        mp.read(in);
        return in;
    }
    MemberParliament::~MemberParliament()
    {
        // delete[] this->p_id;
        // delete[] this->district;
    }
}

And here is the error I am getting

==203530==
==203530== HEAP SUMMARY:
==203530==     in use at exit: 42 bytes in 5 blocks
==203530==   total heap usage: 16 allocs, 11 frees, 72,886 bytes allocated
==203530==
==203530== 6 bytes in 1 blocks are definitely lost in loss record 1 of 5
==203530==    at 0x4C2AC38: operator new[](unsigned long) (vg_replace_malloc.c:433)
==203530==    by 0x4015F2: sdds::Minister::changePM(char const*) (Minister.cpp:23)
==203530==    by 0x400D8B: newElections(sdds::Minister&, char const*, char const*, double) (main_prof.cpp:34)
==203530==    by 0x400FC0: main (main_prof.cpp:67)
==203530==
==203530== 7 bytes in 1 blocks are definitely lost in loss record 2 of 5
==203530==    at 0x4C2AC38: operator new[](unsigned long) (vg_replace_malloc.c:433)
==203530==    by 0x401212: sdds::MemberParliament::MemberParliament(char const*, int) (MemberParliament.cpp:29)
==203530==    by 0x400E0A: main (main_prof.cpp:45)
==203530==
==203530== 7 bytes in 1 blocks are definitely lost in loss record 3 of 5
==203530==    at 0x4C2AC38: operator new[](unsigned long) (vg_replace_malloc.c:433)
==203530==    by 0x401166: sdds::MemberParliament::MemberParliament(char const*, int, char const*) (MemberParliament.cpp:18)
==203530==    by 0x401545: sdds::Minister::Minister(char const*, int, int, char const*, char const*) (Minister.cpp:15)
==203530==    by 0x400F24: main (main_prof.cpp:60)
==203530==
==203530== 9 bytes in 1 blocks are definitely lost in loss record 4 of 5
==203530==    at 0x4C2AC38: operator new[](unsigned long) (vg_replace_malloc.c:433)
==203530==    by 0x4012E4: sdds::MemberParliament::NewDistrict(char const*) (MemberParliament.cpp:51)
==203530==    by 0x400D78: newElections(sdds::Minister&, char const*, char const*, double) (main_prof.cpp:33)
==203530==    by 0x400FC0: main (main_prof.cpp:67)
==203530==
==203530== 13 bytes in 1 blocks are definitely lost in loss record 5 of 5
==203530==    at 0x4C2AC38: operator new[](unsigned long) (vg_replace_malloc.c:433)
==203530==    by 0x4012E4: sdds::MemberParliament::NewDistrict(char const*) (MemberParliament.cpp:51)
==203530==    by 0x400E68: main (main_prof.cpp:50)
==203530==
==203530== LEAK SUMMARY:
==203530==    definitely lost: 42 bytes in 5 blocks
==203530==    indirectly lost: 0 bytes in 0 blocks
==203530==      possibly lost: 0 bytes in 0 blocks
==203530==    still reachable: 0 bytes in 0 blocks
==203530==         suppressed: 0 bytes in 0 blocks

NOTE: I already tried using destructor but it will increases the errors

0 Answers0