Конструктор класса не сохраняет переменные - PullRequest
4 голосов
/ 13 апреля 2019

При попытке использовать метод получения для получения значения переменной в моем классе Employee ничего не возвращается и не выводится.

Я пытался использовать сеттеры, которые мало что могут сделать, так как они все еще используют метод this->, но ничего не достигает того, что я установил.

class Employee {
 Employee(int empNum, std::string name, std::string address, std::string 
phone);

private: 
 int empNum;
 std::string name;
 std::string address;
 std::string phone;
};

class HourlyEmployee : public Employee {
 HourlyEmployee(int empNum, std::string name, std::string address, 
std::string phone, double hourlyWage, double hoursWorked);

//getters
 double getHoursWorked();
 double getHourlyWage();

//setters
 void setHoursWorked(double hoursWorked);
 void setHourlyWage(double hourlyWage);

private:
 double hoursWorked;
 double hourlyWage;
}

//CPP file
Employee::Employee(int empNum, std::string name, std::string address, 
std::string phone) {
 this->empNum = empNum;
 this->name = name;
 this->address = address;
 this->phone = phone;
}
HourlyEmployee::HourlyEmployee(int empNum, std::string name, std::string 
address, std::string phone, double hoursWorked, double hourlyWage) {
 Employee(empNum, name, address, phone);
 this->hoursWorked = hoursWorked;
 this->hourlyWage = hourlyWage;
}

//main
HourlyEmployee hourly1(1, "H. Potter", "Privet Drive", "201-9090", 12.00, 
40.00);
cout << hourly1.getPhone() << " " << hourly1.getName() << " " << 
hourly1.getHoursWorked();

Это не полный код, но он должен выводить телефон и имя и отработанные часы, но по какой-то причине он выводит только два пробела, а затем часы работы. Я могу только предположить, что переменные name, phone и т. Д. На самом деле не были установлены, поэтому они ничего не возвращают. Итак, как мне установить эти переменные?

Ответы [ 3 ]

4 голосов
/ 13 апреля 2019

C ++ не обрабатывает вызовы конструктора специально в телах конструктора.Следующая строка

Employee(empNum, name, address, phone);

создаст новый, совершенно отдельный экземпляр Employee, а затем отбросит его, потому что результирующий объект не назначен ни для чего.Значения полей этого объекта не копируются в экземпляр HourlyEmployee, который вы создаете.

Чтобы использовать конструктор суперкласса в подклассе 1, используйте список инициализатора члена в определении конструктора подкласса.

HourlyEmployee::HourlyEmployee(int empNum, std::string name, std::string 
address, std::string phone, double hoursWorked, double hourlyWage)
        : Employee(empNum, name, address, phone) {
    this->hoursWorked = hoursWorked;
    this->hourlyWage = hourlyWage;
}

Таким образом, C ++ будет вызывать конструктор Employee для инициализации того же объекта, который инициализируется этим конструктором HourlyEmployee.

Вы можете даже пойти немного дальше и сократить ваши конструкторы до просто списков инициализаторов членов.Приятным побочным эффектом является то, что при этом не требуется вводить this-> или придумывать разные схемы именования.

Employee::Employee(int empNum, std::string name, std::string address, 
std::string phone) 
        : empNum(empNum),
          name(name),
          address(address),
          phone(phone) {}

HourlyEmployee::HourlyEmployee(int empNum, std::string name, std::string 
address, std::string phone, double hoursWorked, double hourlyWage)
        : Employee(empNum, name, address, phone),
          hoursWorked(hoursWorked),
          hourlyWage(hourlyWage) {}

Вы можете узнать больше по ссылке выше, но процитируйте короткое объяснение:

Перед началом выполнения составного оператора, который формирует тело функции конструктора, завершается инициализация всех прямых баз, виртуальных баз и нестатических элементов данных.Список инициализаторов элементов - это место, где можно указать инициализацию этих объектов по умолчанию.

1 голос
/ 13 апреля 2019

Конструктор производного класса HourlyEmployee вызывает базовый конструктор неверным образом.

Вы должны написать код следующим образом:

HourlyEmployee::HourlyEmployee(int empNum, std::string name, std::string 
    address, std::string phone, double hoursWorked, double hourlyWage) :
    Employee(empNum, name, address, phone)
{
    this->hoursWorked = hoursWorked;
    this->hourlyWage = hourlyWage;
}

Кроме того, имя параметра всех вашихКонструкторы совпадают с именами ваших членов, это НЕ хорошая идея.Лучше назовите их по-другому.

1 голос
/ 13 апреля 2019

Вам нужно использовать список инициализатора в конструкторе подкласса, например:

#include <iostream>

class Employee {
public:
 Employee(int empNum, std::string name, std::string address, std::string phone) {
   this->empNum = empNum;
   this->name = name;
   this->address = address;
   this->phone = phone;
 }

 std::string getPhone() { return phone; }
 std::string getName() { return name; }

private: 
 int empNum;
 std::string name;
 std::string address;
 std::string phone;
};

class HourlyEmployee : public Employee {
public:
 HourlyEmployee(int empNum, std::string name, std::string address, std::string phone, double hoursWorked, double hourlyWage) 
 : Employee(empNum, name, address, phone) {
   this->hoursWorked = hoursWorked;
   this->hourlyWage = hourlyWage;
 }

 double getHoursWorked() { return hoursWorked; }
 double getHourlyWage() { return hourlyWage; }

private:
 double hoursWorked;
 double hourlyWage;
};

int main(void)
{
  HourlyEmployee hourly1(1, "H. Potter", "Privet Drive", "201-9090", 12.00, 40.00);
  std::cout << hourly1.getPhone() << " " << hourly1.getName() << " " << 
  hourly1.getHoursWorked();
  return 0;
}

Вывод:

201-9090 H. Potter 12

Однако я настоятельно рекомендую вам использовать список инициализации для всех членов данных вашего класса, а именно для базового и производного класса в этом случае.

...