Zhaozhong Chen
Zhaozhong Chen

Reputation: 85

When should I use new and smart pointer

I read the following code

student* input(string name, int age)
{
  student *st = new student(name,age);
  return st;
}

where student is just a simple class with following function and member

class student{

  public:
    student(string na, int ag);
    void show();
  private:
    string name;
    int age;
};

show is just a function to print a sentence. Main function is the following

int main(){
  student *st = input("guagua",25);
  if(!st){ cout<<"no pointer"<<endl;}
  st->show();
  delete st;
  return 0;
}

My understanding is that because I use new so in the main function I need delete st. If I use the following code the take the place of student *st = new student(name,age);, do I still need to delete st?

  student te(name,age);
  student *st;
  st = &te;

If not because now st is a raw pointer, why people need new? We can all use the similar way to take the place of new. Another problem is that some people suggest to use smart pointer to avoid we forget delete a pointer. Then I just use raw pointer in every place like above, it seems we do not need delete at all? I know there must some place I didn't understand, hope you can help me. Thanks

Upvotes: 0

Views: 50

Answers (1)

Guillaume Racicot
Guillaume Racicot

Reputation: 41840

My understanding is that because I use new so in the main function I need delete st.

That is correct.

If I use the following code the take the place of student *st = new student(name,age);, do I still need to delete st?

student te(name,age);
student *st;
st = &te;

No. You will probably crash. Remember that stack values are destroyed after their scope. In this code, te will die after the function returns. st will point to a dead object.

Another problem is that some people suggest to use smart pointer to avoid we forget delete a pointer.

Indeed, you should not have new or delete unless you're doing something special. You can get away easily with smart pointer without any runtime penalty. You're example using std::unique_ptr (a unique owner, many observers) will look like this:

std::unique_ptr<student> input(string name, int age) {
    // auto is std::unique_ptr<student>
    auto st = std::make_unique<student>(name,age);
    return st;
}

int main() {
    // auto is std::unique_ptr<student>
    auto st = input("guagua",25);

    if(!st){
        std::cout << "no pointer" << std::endl;
    }
    
    st->show();
    // delete st; // no delete to do
    return 0;
}

Even better, if you can do it with values, you won't need dynamic memory management or unique pointers at all:

student input(string name, int age) {
    student st{name, age};
    return st;
}

int main() {
    // auto is student
    auto st = input("guagua",25);

    // The following is not needed, a value is never null
    //if(!st){
    //    std::cout << "no pointer" << std::endl;
    //}
    
    st.show();

    // delete st; // no delete to do
    return 0;
}

Upvotes: 3

Related Questions