1

I have a function and a class as below

class Vertex {
public:
    int mId;
public:
    Vertex(int info=-1) : mId(info) {

    }
};

class Edge {
public:
    Vertex mStart, mEnd;
    int mWeight;
public:
    Edge(Vertex start=-1, Vertex end=-1, int wt=-1) :
        mStart(start), mEnd(end), mWeight(wt) {
    }
};

class Graph {
    void addEdge(const Edge& e) {
        //Adds this edge to a vector
    }
};

shared_ptr<Graph> mygraph(new Graph(13 //no of vertices
                             , 17   //no of edges
                             , false));

mygraph->addEdge(Edge( 1, 2, 1));
mygraph->addEdge(Edge( 3, 1, 1));
mygraph->addEdge(Edge( 1, 6, 2));
mygraph->addEdge(Edge( 1, 7, 4));
...

Here I am passing direct Edge values in a constructor and get no crash. But I guess there will be a memory leak here. Whats the correct way to pass an object by reference after doing construction?

PS: Assume that Vertex is an implicit constructor accepting int as id.

tariq zafar
  • 659
  • 7
  • 24
  • 6
    You didn't use new for the edges -> no memory leak. – Borgleader Jan 20 '14 at 10:14
  • 1
    The code looks perfectly fine. There will be no memory leak as nothing is allocated from the free store except the `Graph` in the `shared_ptr` (bonus points for that). – molbdnilo Jan 20 '14 at 10:16
  • @molbdnilo Thanks for the comment. I wanted to confirm whether this way of construction and passing to a function without using objects is fine? – tariq zafar Jan 20 '14 at 10:37
  • @tariqzafar It's not only fine, it's usually recommended, although I don't understand what you mean by "without using objects" - you are using objects. – molbdnilo Jan 20 '14 at 10:45
  • @molbdnilo I actually meant that instead of writing Edge e(1, 2, 1) I am writing Edge(1, 2, 1). Thanks for clarifying :) – tariq zafar Jan 20 '14 at 11:06

1 Answers1

3

There wouldn't be any memory leaks, destructors will be automatically called, as @Borgleader wrote

You didn't use new for the edges -> no memory leak If you don't name objects it doesn't mean they wouldn't be destroyed. Everything's okay.

Although you can perform a little optimisation if you are using C++11. In your code object Edge is created, then passed by a const reference to a function addEdge(), where it will be copied to a vector with a copy constructor. You can avoid this overhead by using std::vector::emplace_back! And templates. Like so:

class Graph {
    public:
    template<class... Args>
    void addEdge(Args&& ...args) {
        //Assuming vector is std::vector<Edge>
        vector.emplace_back(args...);
    }
};
mygraph->addEdge(1, 2, 1);

Of course all created objects will be automatically destroyed when vector is cleared.

And, BTW, if you ever doubt whethere your program has memory leaks, Valgrind is at your service!

Update:

I've coded a tiny and simple example showing the difference, see it at http://ideone.com/ARzhL2. You can scroll directrly to a stdout section to see the result.

mexus
  • 990
  • 6
  • 6
  • Maybe you will find this useful: http://stackoverflow.com/questions/413477/is-there-a-good-valgrind-substitute-for-windows – mexus Nov 13 '14 at 06:31