C++ - 工程中头文件的定义

头文件

头文件大家都明白,里面存放了我们需要使用的『工具』,也是我们在使用某个类库的时候,需要include进来的内容。

定义头文件

定义头文件需要注意以下内容:

  1. 要防止被重复include
  2. 在某些情况下只写声明(declare),不写定义(define)

首先如何防止重复include呢?其实很简单,就是加上:

#ifndef
#define SYMBOL
#endif

例如如下我定义了一个头文件,名字叫做Header.h,里面的内容可以写成如下的样子:

//
//  Header.h
//  HihocoderTest
//
//  Created by Alps on 16/6/23.
//  Copyright © 2016年 chen. All rights reserved.
//

#ifndef Header_h
#define Header_h

//write code here


#endif /* Header_h */

这样就可以防止被重复include了。

那么是不是一定没有问题了呢?
不是的!

假如Header.h里面写了除了declare还有define的内容例如:

//
//  Header.h
//  HihocoderTest
//
//  Created by Alps on 16/6/23.
//  Copyright © 2016年 chen. All rights reserved.
//

#ifndef Header_h
#define Header_h

//write code here
int add(){
    return 0;
} //declare and define

#endif /* Header_h */

假如出现一种情况:

三个文件:
Header.h
Main.cpp
Test.h

其中
Test.h
#include Header.h

Main.cpp
#include Header.h
#include Test.h

这种情况,在编译链接的阶段,会报错的,redeclared的错误。

但是如果只有声明的话,是不会有问题的。所以这就是为什么我们平时在添加这些库文件的头文件,没有遇到redclared的问题。

所以可以在头文件里这样写:

//
//  Header.h
//  HihocoderTest
//
//  Created by Alps on 16/6/23.
//  Copyright © 2016年 chen. All rights reserved.
//

#ifndef Header_h
#define Header_h

//write code here
int add(); //declare without define

int add(); // redeclare is also ok

#endif /* Header_h */

即使写两个,也不会有问题。

特殊情况

在我们定义类的时候,我们一般的定义形式是,把类和类方法的声明和类方法的定义分开来写:

正常定义类

例如类User

文件:
User.h
User.cpp
//
//  User.h
//  HihocoderTest
//
//  Created by Alps on 16/7/24.
//  Copyright © 2016年 chen. All rights reserved.
//

#ifndef User_h
#define User_h

#include <stdio.h>
#include <string>
#include <cstring>

class User{
private:
    std::string name;
    std::string sex;
public:
    User();
    User(std::string n, std::string s);

    std::string getName();
    void setName(std::string name);
};

#endif /* User_h */

而User.cpp文件:

//
//  User.cpp
//  HihocoderTest
//
//  Created by Alps on 16/7/24.
//  Copyright © 2016年 chen. All rights reserved.
//

#include "User.hpp"

User::User(std::string n, std::string s):name(n), sex(s){}

std::string User::getName(){
    return this->name;
}

void User::setName(std::string name){
    this->name = name;
}

特殊写法

现在新的标准里,在建立头文件的时候,后缀名是:hpp了,其实是为了方便把类的声明和定义放在一起了。

写法如下:

//
//  User.hpp
//  HihocoderTest
//
//  Created by Alps on 16/7/24.
//  Copyright © 2016年 chen. All rights reserved.
//

#ifndef User_hpp
#define User_hpp

#include <stdio.h>
#include <string>
#include <cstring>

class User{
private:
    std::string name;
    std::string sex;
public:
    User();
    User(std::string n, std::string s);

    std::string getName();
    void setName(std::string name);
};

User::User(std::string n, std::string s):name(n), sex(s){}

std::string User::getName(){
    return this->name;
}

void User::setName(std::string name){
    this->name = name;
}

#endif /* User_hpp */

这样不是出现了我上面说的,会出现在链接阶段的redeclare的情况么 ?

其实不会的,是因为这个是类,实际上,所有的这些都算是类的声明而已,因为类是不会在编译阶段就知道占用内存大小的,所以这个和普通的函数声明一样,这样就不会出现redeclare了。

疑问

那为什么int a; int a;这种我只是声明了,没有定义也会报错呢? 是因为基本类型是在认为声明的时候就定义了。所以不能重复声明的。

总结

总结起来就是,正常情况一般还是把声明和定义分开放,这样可以让工程的结构更为清晰。

类是可以放在一起的。也就是hpp文件。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值