Creating instance in an another class of an object

三世轮回 提交于 2021-02-11 12:54:24

问题


I need to create an instance in class Crop of Plant class and i cant manage to find a way to make that work. Hope you guys can help at that.

This my main where i'm sending an object to the class crop.

int main(){

char select = 'a';
int plant_num = 2;
int crop_num = 0;

Crop crop[10];
Plant plant[20];

plant[0] = Plant("Carrots",'c');    
plant[1] = Plant("Lettuce",'l');
plant[2] = Plant("Rosemary",'r');

crop[0] = Crop(plant[0],4,2);
crop_num++;

cout << "Garden Designer" << endl;
cout << "===============";

}

class crop is where i want the instance of plant class

class Crop {

private:
    int g_length;
    int w_width;
    Plant PlantType;

public:
    Crop();
    Crop(const Plant&, int, int);

};  

class plant of which i want the instance of in class crop

class Plant {

private:
    char plant[20];
    char p_symbol;

public: 
    Plant();
    Plant(const char* n, char s);
};

Crop.cpp

#include <iostream>
#include <iomanip>
#include <cstring>
#include <new>
#include "crop.h"
using namespace std;


Crop::Crop(){



}

 Crop::Crop(const Plant& temp, int l, int w){



}

sorry if im missing something. really confused if you need Plant.cpp file content just ask me. I didn't think that file would be needed.


回答1:


There is something called a Member initializer list and its place is in the constructors definition after its parameters list, preceded by a semicolon, followed by a body of a constructor. So to initialize members you can write

Crop::Crop(const Plant& temp, int l, int w) : 
  g_length(l), 
  w_width(w), 
  PlantType(temp) 
{ }

What this does is call the appropriate constructors of the members. They don't have to be copy constructors. You can explicitly call default one or any else, although it probably does not make much sense in your case.

It is because the members are instantiated before executing the body of the constructor. You would not have problem with ints, as they can be set inside the body. References, however, need to be valid at all the times, so nothing inside the body will have a "null-reference".

You could do:

Crop::Crop(const Plant& temp, int l, int w) : PlantType(temp) 
{ 
   g_length = l;
   w_width = w;
}

But any member not initialized explicitly gets initialized with a default constructor, so at //here g_lenght exists and has a value (either 0 or trash i don't recall if default is zero, i think it's thrash), and then in the body operator= gets called. While the 1st case, object is created via copy constructor.

Often this is not a big difference, however for more complicated types it might be important. Especially if constructing an empty object takes long time, and then assignment is also complicated. It's simply to better set-up object once, than create it and reset with operator=.

I personally like the look of 2nd for some reason, but it is considered a worse practice, because logically those members are meant to be constructed using some value from the start.




回答2:


You're on the right track here:

crop[0] = Crop(plant[0],4,2);

This calls the constructor of the class Crop with the correct parameters. This constructor is supposed to initialize the corresponding data members with these values, but the constructor that actually takes these parameters does nothing:

Crop::Crop(const Plant& temp, int l, int w) {
    // ...
}

Use the member initializer list to initialize your data members:

Crop::Crop(const Plant& temp, int l, int w)
    : g_length(l), g_width(w), PlantType(temp)
{ }

The constructor body isn't needed until we need to do something after we've initialized our data members.




回答3:


Your Crop constructor receives the Plant (and two integers) and completely ignores them. Try:

Crop::Crop(const Plant& temp, int l, int w) :
    g_length(l), w_width(w), PlantType(temp) {}


来源:https://stackoverflow.com/questions/26289540/creating-instance-in-an-another-class-of-an-object

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!