简体   繁体   English

我正在尝试学习如何正确分离类头和代码

[英]I'm trying to learn how to properly separate class header and code

I have a class project that I did from college that "works", but isn't constructed properly. 我有一个大学时期的班级项目,该项目“有效”,但结构不正确。

It has a Date class and a Person class. 它具有Date类和Person类。

In my "working" code, all of the class data (constructors, members, and functions) are contained within a single header file for each class (a separate file for each class). 在我的“工作”代码中,所有类数据(构造函数,成员和函数)都包含在每个类的单个头文件中(每个类一个单独的文件)。

The program loads text file data (Persons, presidents and actors) into a vector, sorts, filters and prints the data on the console, and saves it to a file. 该程序将文本文件数据(人员,总裁和演员)加载到矢量中,在控制台上对数据进行排序,过滤和打印,然后将其保存到文件中。

In the Person class constructor (and functions), the Date class is instantiated for a "birthdate" object. 在Person类的构造函数(和函数)中,为“ birthdate”对象实例化Date类。 Then the birthday is used in the program. 然后在程序中使用生日。

The problem I'm having is this: 我遇到的问题是:

I can easily instantiate "Date" in the Person constructor and members, if all the class code is in a header file for each class, AND I make the Date the "Parent" class for Person. 如果所有类代码都在每个类的头文件中,则可以轻松地在Person构造函数和成员中实例化“ Date”,并且将Date设为Person的“ Parent”类。 But if I don't do both of these things, then "Person" doesn't know anything about "Date" and cannot instantiate anything from Date. 但是,如果我不做这两个事情,那么“ Person”对“ Date”一无所知,并且无法实例化Date中的任何内容。

If I use an #include "Date.h" in Person.h, this creates even more problems and doesn't work either. 如果我在Person.h中使用#include“ Date.h”,这会产生更多问题,并且也不起作用。

Of course, "Date" is not a proper parent class for "Person", but it was the only way I could hack the code to make it work lol. 当然,“ Date”不是“ Person”的适当父类,但这是我可以修改代码使其大声笑的唯一方法。 When I first coded this years ago in college, I never did figure out how to divide the class code properly in so that it would compile and run. 多年前,当我在大学里第一次编写代码时,我从未想过如何正确地划分类代码,以使其能够编译和运行。 The "working code" with all the class code in a header file is my hack. 头文件中所有类代码的“工作代码”是我的hack。 I want to learn how to do it the right way. 我想学习正确的方法。

I have pasted in the bare minimum example below of what "works" and what doesn't. 我在下面粘贴了最简单的示例,说明什么“有效”和什么无效。 Any tips to make this code work with the classes divided into header and .cpp files would be much appreciated. 使该代码与分为头文件和.cpp文件的类一起工作的任何技巧将不胜感激。

What works: 什么有效:

class Date {
    private:
        int month;
        int day;
        int year;

    public:
        Date::Date() {}
        virtual ~Date() {}
        Date( int aMonth, int aDay, int aYear ) {
            this->month = aMonth;
            this->year = aYear;
            this->day = aDay;
        }

        // "Getter" functions for the Date class
        int getMonth(){return this->month;}
        int getYear() {return this->year;}
        int getDay() {return this->day;}

        // "Setter" functions for the Date class
        void setDay( int aDay ){ this->day = aDay; }
        void setMonth( int aMonth )  { this->month = aMonth; }
        void setYear( int aYear ) { this->year = aYear; }
};

class Person : public Date{
    private:
        string title;
        string firstName;
        string lastName;
        Date birthDate;

    public:
        Person::Person() {}
        Person(string title, string firstName, string lastName, Date birthDay);
        virtual ~Person() {}

        //"Getter" functions for the Person class
        string getTitle() { return title; }
        string getFirstName() { return firstName; }
        string getLastName() { return lastName; }
        Date getBirthDay() { return birthDate; }

        //"Setter" functions for the Person class
        void setTitle(string Title) { this->title = Title; }
        void setFirstName(string fName) { this->firstName = fName; }
        void setLastName (string lName) { this->lastName = lName; }
        void setBirthday (Date aBirthday) { this->birthDate = aBirthday; }
};

What doesn't work (Doesn't compile): 什么不起作用(不编译):

Date.h Date.h

class Date {
    private:
        int month;
        int day;
        int year;
    public:
        Date();
        virtual ~Date() {}
        Date( int aMonth, int aDay, int aYear );

        //Getters and setters
        int getMonth();
        int getYear() ;
        int getDay();
        void setDay( int aDay );
        void setMonth( int aMonth ) ;
        void setYear( int aYear ) ;

};

Date.cpp Date.cpp

#include "Date.h"
Date::Date() {}
Date::Date( int aMonth, int aDay, int aYear ) {
    this->month = aMonth;
    this->year = aYear;
    this->day = aDay;
}

int Date::getMonth(){return this->month;}
int Date::getYear() {return this->year;}
int Date::getDay()  {return this->day;}

//"Setter" functions for the Date class
void Date::setDay( int aDay ){ this->day = aDay; }
void Date::setMonth( int aMonth )  { this->month = aMonth; }
void Date::setYear( int aYear ) { this->year = aYear; }

Person.h Person.h

#include <string>

class Person{
    private:
        string title;
        string firstName;
        string lastName;
        Date birthDate;

    public:
        //Person::Person() {}
        Person(string title, string firstName, string lastName, Date birthDay); 

        //"Getter" functions for the Person class
        string getTitle() { return title; }
        string getFirstName() { return firstName; }
        string getLastName() { return lastName; }
        Date getBirthDay() { return birthDate; }

        //"Setter" functions for the Person class
        void setTitle(string Title) { this->title = Title; }
        void setFirstName(string fName) { this->firstName = fName; }
        void setLastName (string lName) { this->lastName = lName; }
        void setBirthday (Date aBirthday) { this->birthDate = aBirthday; }
    };

Person.cpp Person.cpp

#include "Person.h"
#include <iostream>
using namespace std;

//Person class constructor with 0 arguments
Person::Person(string atitle, string afirstName, string alastName, Date abirthDay) {
    title = atitle,
          firstName = afirstName,
          lastName = alastName,
          birthday = abirthDay)
}

//"Getter" functions for the Person class
string Person::getTitle() { return title; }
string Person::getFirstName() { return firstName; }
string Person::getLastName() { return lastName; }
Date Person::getBirthDay() { return birthDate; }

//"Setter" functions for the Person class
void Person::setTitle(string Title) { this->title = Title; }
void Person::setFirstName(string fName) { this->firstName = fName; }
void Person::setLastName (string lName) { this->lastName = lName; }
void Person::setBirthday (Date aBirthday) { this->birthDate = aBirthday; }

Operating system notes 操作系统说明

I'm using MS Visual Studio 2012 Update 4 on a Windows 7 PC. 我在Windows 7 PC上使用MS Visual Studio 2012 Update 4。

To prevent redefinition errors, add include guards to header files. 为防止重新定义错误,请在头文件中添加包含防护。 To be portable, use: 为了便于携带,请使用:

#if !defined(THE_HEADER_NAME_H)
#define THE_HEADER_NAME_H
// Usual code and declarations here.
#endif

In Visual Studio, you can use: 在Visual Studio中,可以使用:

#pragma once
// Usual code and declarations here.

In headers, don't write (at global scope level) 在标头中,请勿写入(在全局范围级别)

using namespace XXXXX

because that will cause all files including yours to also use namespace XXXXX which they may not want imposed upon them. 因为这样做会导致包括您在内的所有文件也使用它们可能不希望施加在其上的名称空间XXXXX。 If you use types that are in a namespace, type out the entire type name with namespace, so use: 如果使用名称空间中的类型,请使用名称空间键入整个类型名称,因此请使用:

std::string getTitle()

(In a cpp file, you can have 'using namespace XXXXX' after any #includes) (在cpp文件中,任何#include之后都可以使用“使用命名空间XXXXX”)

You have 2 problems IMHO. 您有2个问题恕我直言。

First is the guards problem that Scott Langham's answer will solve. 首先是斯科特·朗厄姆的答案将解决的警卫问题。

The second is a problem of namespaces. 第二个是名称空间问题。

I assume that in your working source, you have (directly on indirectly via stdafx.h or another include) : 我认为在您的工作源中,您(直接通过stdafx.h或另一个include间接在)上:

#include <string>

using namespace std;

It is not recommended to have using namespace std; 不建议using namespace std; in a .h header file ... but that means that you should use std::string instead of string : .h头文件中...但这意味着您应该使用std::string而不是string

date.h date.h

class Date {
    private:
        int month;
        int day;
        int year;
    public:
        Date::Date() { }                                                //Date class constructor with 0 arguments
        virtual ~Date() {}                                              //Date class destructor
        Date( int aMonth, int aDay, int aYear ) {                       //Date class constructor with 3 arguments
            this->month = aMonth;                                       // Set the private member data with the argument data
            this->year = aYear;
            this->day = aDay;
            }       
        //"Getter" functions for the Date class
        int getMonth(){return this->month;}                             
        int getYear() {return this->year;}
        int getDay() {return this->day;} 

        //"Setter" functions for the Date class
        void setDay( int aDay ){ this->day = aDay; }                    
        void setMonth( int aMonth )  { this->month = aMonth; }  
        void setYear( int aYear ) { this->year = aYear; }

};

person.h (string -> std::string and remove method implementations) person.h(字符串-> std :: string并删除方法实现)

#include <string>
#include "Date.h"

class Person : public Date{

private:                                                                //Private data members
    std::string title;
    std::string firstName;
    std::string lastName;
    Date birthDate;

public:
    Person::Person() {}                                                 //Person class constructor with 0 arguments
    Person(std::string title, 
        std::string firstName, 
        std::string lastName, 
        Date birthDay);                                                 //Person class constructor with 4 arguments

    virtual ~Person(){}                                                 //Person class destructor

    //"Getter" functions for the Person class
    std::string getTitle();
    std::string getFirstName();
    std::string getLastName();
    Date getBirthDay();

    //"Setter" functions for the Person class
    void setTitle(std::string Title);
    void setFirstName(std::string fName);
    void setLastName (std::string lName);
    void setBirthday (Date aBirthday);
};

person.cpp (fixed includes and constructor) person.cpp(固定的包含和构造函数)

#include <string>
#include "Person.h"
#include <iostream>
using namespace std;

//Person class constructor with 0 arguments
Person::Person(string atitle, string afirstName, string alastName, Date abirthDay) {
    title = atitle,
          firstName = afirstName,
          lastName = alastName,
          birthDate = abirthDay;
}

//"Getter" functions for the Person class
string Person::getTitle() { return title; }
string Person::getFirstName() { return firstName; }
string Person::getLastName() { return lastName; }
Date Person::getBirthDay() { return birthDate; }

//"Setter" functions for the Person class
void Person::setTitle(string Title) { this->title = Title; }
void Person::setFirstName(string fName) { this->firstName = fName; }
void Person::setLastName (string lName) { this->lastName = lName; }
void Person::setBirthday (Date aBirthday) { this->birthDate = aBirthday; }

It can even be used without guards, but guard are anyway a good practice. 它甚至可以在没有保护装置的情况下使用,但是保护装置仍然是一种很好的做法。

In fact as Date.h is included in Person.h it should really have a guard - not shown here for simplicity 实际上,由于Date.h包含在Person.h因此它实际上应该有一个防护装置-为简单起见,此处未显示

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何在VSC中正确区分类标题和cpp? - How to properly separate class header and cpp in VSC? 如何将类定义分成2个头文件? - How do i separate a class definition into 2 header files? 我正在尝试在另一个 function 中调用 void 函数,但我不知道如何正确放置它们 - I'm trying to call void functions in another function, but I don't know how to properly place them 我正在尝试插入一组课程 - I'm trying to insert to a set of a class 我试图理解C ++中关联的实验室作业的类中给出的伪代码 - Pseudo-code given in class that I'm trying to comprehend with the associated lab assignment in c++ 我正在尝试编写一个 class,其中子 class 将继承父 class 的方法,但我的代码不会编译 - I'm trying to write a class where the child class will inherit the methods from the parent class, but my code won't compile 我正在尝试学习如何在 C++ 中传递指针,但出现错误:没有匹配的函数用于调用“测试”。 我究竟做错了什么? - I'm trying to learn how to pass pointers in c++, but I get error: no matching function for call to 'test'. What am I doing wrong? 如何正确使用头文件成为一个完整的类? - How to properly use a header file to be a complete class? 使用此代码时,我总是收到错误消息。 我正在尝试在继承的类中使用构造函数。 C ++ - I keep getting an error when I use this code. I'm trying to use constructors in an inherited class. c++ 我将如何划分这堂课? - How would I separate this class?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM