简体   繁体   中英

C++ - Class constructor creates objects, but the result of the construction is different

I have a class project in C++. The goal is to sort a phonebook (txt file) when inserting in a linked list .

Here are the classes :

class Person
{
    public:
        string Name
        string Firstname;
        string Adress;
        int PostalCode;
        string Telephone;
        Person();
        ~Person();
};

class Link
{
    friend class List;
    Link *next;
    Person *pers;
    public:
        Link();
        Link(string data);
};

class List
{
    // debut is the start of the chained list
    Link *start;
    public:
        List(string data)
        {
            start = NewLinkPerson(data, NULL);
        }
};

Link::Link(string data)
{
    next = NULL;
    Person p;
    p.put_data(data);
    pers = &p;
}

Link::Link()
{
    next = NULL;
    Person p;
    pers = &p;
}

And then, the function NewLinkPerson is detailed as such :

Maillon * NewLinkPerson(string data, Maillon *ssuiv)
{
    Maillon * nouveau = new Maillon(data);
    nouveau->suiv = ssuiv;
    return nouveau;
}

The problem is that the object created is not the one I ordered the program him to create. If I output the object pers of type Person in the constructor, it will be filled with the data I asked. But when it leaves the constructor, the data is gone, and is filled with random strings from the memory.

What could be causing the issue ? I have tried many things, but none of them seem to works, all mainly returned a Segmentation Fault.

EDIT : A function I forgot to put there :

void Person::put_data(string data)
{
    int sep1 = data.find("|");
    int sep2 = data.find("|", sep1+1);
    int sep3 = data.find("|", sep2+1);
    int sep4 = data.find("|", sep3+1);
    Name = data.substr(0, sep1);
    Firstname = data.substr(sep1+1, sep2-sep1-1);
    Adress = data.substr(sep2+1, sep3-sep2-1);
    Telephone = data.substr(sep4+1, data.npos);
    string ccode = data.substr(sep3+1, sep4-sep3-1);
    PostalCode = std::stoi(ccode.c_str());
}

Edit 2 : Translated to english

Your code has undefined behavior

Link::Link(string data)
{
    next = NULL;
    Person p;
    p.put_data(data);
    pers = &p;
}

Link::Link()
{
    next = NULL;
    Person p;
    pers = &p;
}

In both constructors in the above code you create a local Person , p , and then you have pers point to it. After the constructor ends p goes out of scope, gets destroyed and now pers points to an object that no longer exists. Any dereference of pers after that will it still points to the deleted object is undefined behavior.

To fix this just get rid of the pointer for pers . If you store it as a value then you do not need any dynamic memory allocation and you get away from pointer syntax. Link should be

class Link
{
    friend class List;
    Link *next;
    Person pers; // no pointer here
    public:
        Link();
        Link(string data);
};

And then the constructors can be defined like

Link::Link(string data)
{
    next = NULL;
    pers.put_data(data);
}

Link::Link()
{
    next = NULL;
}

If you have to have pers as a pointer then you can allocate persistent storage for it with new . If you do that then you need to make sure you delete it in the destructor of the class and that you have copy symantics. For more on this see What is The Rule of Three?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM