C语言进阶:宏定义,头文件,让C文件拆分了还能运行

宏定义

宏定义通常有三种用法:

  1. 当作常量使用
  2. 当作函数使用
  3. 编译预处理

1. 宏定义常量

预定义宏:

预定义宏 作用
__LINE__ 当前所在文件的行号 %d
__FILE__ 表示当前源文件 %s
__DATE__ 文件被编译的日期 %s
__TIME__ 文件被编译的时间 %s

测试:

#include <stdio.h>

int main(){
   
        printf("%s:%d\n",__FILE__,__LINE__);
        printf("%s:%s\n",__DATE__,__TIME__);
}

结果为:

def5.c:4
Apr  4 2021:05:50:11

自定义宏:
本质就是做替换
#define PI 3.1415926

注意:后面没分号

2. 代参数的宏

与函数不同,不用定义也能直接改变数值,因为宏定义的本质是替换

#include <stdio.h>

#define NUM 5

#define SWAP(n,m) \
        int t=n;  \
        n=m;      \
        m=t;

#define ARR_SIZE(arr) sizeof(arr)/sizeof(arr[0])

#define SQUARE(x) x*x

#define CUBE(x) x*x*x

int main(){
   
        int a = 10;
        int b = 20;
        printf("a:%d\tb:%d\n",a,b);
        SWAP(a,b);
        printf("a:%d\tb:%d\n",a,b);

        int arr[NUM];
        printf("%d\n",sizeof(arr)/sizeof(arr[0]));
        printf("%d\n",ARR_SIZE(arr));

        printf("%d\n",SQUARE(8));
        printf("%d\n",CUBE(3));
}

结果为:

a:10	b:20
a:20	b:10
5
5
64
27

得最小值或最大值,也可以使用宏定义完成

#define MIN(a,b) ((a)<(b)?(a):(b))

边际效应:
问题:
printf("%d\n",CUBE(3+2));
会造成 3+2*3+2*3+2

解决:
需要加括号
#define CUBE(x) ((x)*(x)*(x))

3. 编译预处理

#ifdef TEST
如果定义了 TEST ,则编译第一部分
如果没有定义 TEST ,则编译第二部分

#include <stdio.h>

// #define TEST

int main(){
   
#ifdef TEST
        printf("123\n");
#else
        printf("abc\n");
#endif
}

结果为:

[admin@localhost cfile]$ gcc def2.c -o def2
[admin@localhost cfile]$ ./def2
abc

如果没有定义 TEST 也可以在编译时后面加 -DTEST ,表示定义了 TEST

[admin@localhost cfile]$ gcc def2.c -o def2 -DTEST
[admin@localhost cfile]$ ./def2
123

#ifndef TEST
如果没定义 TEST ,则编译第一部分
如果定义了 TEST ,则编译第二部分


头文件

1. 文件拆分

学生登陆系统拆分:

把注册登录功能和其他功能分两部分拆分

  1. 结构体(剪切)、函数声明(函数内容不用),都放在 login.h
    结构体(剪切)、函数声明(函数内容不用),都放在 student.h
  2. 先把注册登陆部分的放在login.c,需要头文件,并加 #include “login.h”
    把学生信息部分的放在student.c,需要头文件,并加 #include “student.h”
  3. gcc -c login.c 生成 login.o
    gcc -c student.c 生成 student.o
  4. 在main函数文件中写头文件
    #include “login.h”
    #include “student.h”
  5. 编译时 gcc main.c login.o student.o -o stud
    也可以 gcc -c main.c 生成 main.o,编译时 gcc main.o login.o student.o ,相当于连接所有编译文件

login.c 文件内容

#include <stdio.h>
#include <stdbool.h>
#include <stdlib.h>
#include <string.h>
#include "login.h"

//录入注册信息
bool RegisterUser(const char* path){
   
        printf("首次登陆需要注册\n");
        User current;
        printf("注册用户名:");
        scanf("%s",current.name);
        printf("注册密码:");
        scanf("%s",current.password);

        FILE* pf = fopen(path,"w");
        if(NULL == pf){
   
                return false;
        }
        fprintf(pf,"%s %s",current.name,current.password);
        fclose(pf);
        pf = NULL;
        return true;
}

//验证用户和密码是否正确
bool Login(const char* path){
   
        FILE* pf = fopen(path,"r");
        if(NULL == pf){
       //如果没存过用户信息,则存用户信息
                return RegisterUser(path);    //第一次登陆要注册,注册成功直接进入
        }
        printf("Login...\n");
        User current;
        printf("请输入用户名:");
        scanf("%s",current.name);
        printf("请输入密码:");
        scanf("%s",current
  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值