编写进度条
在之前的文章中,我们已经学会了如何使用vim进行内容的编写,学会了make和makefile进行便捷地编译文件,今天就来实际练习一个程序,编写一个进度条
1.构思程序的结构
1.文件结构
一个进度条程序,我们需要暴露给外界的程序不能过多,所以使用头文件,源文件,和主函数文件分别编写声明以及头文件,进度条文件的主体,在主函数中测试函数是否能被调用
创建三个文件
processbar.c(函数定义处)
processbar.h(函数声明处)
main.c(函数使用处)
2.文件内容的结构
接下来我们来想一下进度条应该是什么样的,它应该是一个从左向右不断递增符号或者色块的程序,即便美术风格大相径庭,但是实现的效果就是这么个样子
------------\>
所以我们知道了,进度条应该有一个主体的填充部分,右边的标识部分,以及左右的限制部分,并且他们应该都在一行随着时间更新
2.回车换行,以及程序编写
在上面的构思中我们可能会有很多想法去设计主体填充部分和右边标识部分,用一个char类型的数组储存并不断填充里面的内容就可以了,但是该怎么做才能让内容打印在一行上呢?
我们知道在打印时\n表示光标移动到开头并下移一行,这个操作就是回车换行,可是我现在不想让他换行就像让他在同一行打印内容,因为要做到进度条的效果,该怎么办,这里引入\r表示只回车不换行,这样光标就会回到开头打印在同一行。使用sleep函数营造时间间隔的效果
但是这样又会产生新的问题,\n不止是回车换行的效果,他还会刷新缓冲区,也就是将打印的东西显示到显示器上,但是\r没有这个效果,所以在循环结束后才会打印一次,不是我们想要的效果,所以在每次循环中使用fflush(stdout),刷新缓冲区,就能够实现类似进度条的效果了
#include "processbar.h"
2 #include <string.h>
3 #include <unistd.h>
4
5 const char* sign = "/-|\\";
6 char s[NUM];
7
15 void processbar(){
16 memset(s,'\0',sizeof(s));
17 int rate = 0;
18 while(rate<=100){
19 if(rate!=100)
20 s[rate] = '>';
21 printf("[%-100s][%d%%][%c]\r",s,rate,sign[rate%4]);
22 fflush(stdout);
23 s[rate++] = STYLE;
24 usleep(100000);
25 }
26 printf("\n");
27
28 }
注意控制好数组的大小,避免出现越界,最后效果类似下图

3.实际使用场景
我们现实生活中的进度条程序的调用一般不是我们上面自己写的那样,一般是使用函数指针进行回调,传入一个参数rate,然后显示对应rate下的情况,所以要改造我们的函数
processbar.c文件
void processbarCore(int rate){
8 if(rate<0||rate>100) return;
9 if(rate!=100) s[rate] = '>';
10 printf("[%-100s][%d%%][%c]\r",s,rate,sign[rate%4]);
11 fflush(stdout);
12 s[rate++] = STYLE;
13 }
main.c文件,使用函数指针进行回调,循环在某个下载任务中进行
#include "processbar.h" 1 #include "processbar.h"
2 #include <unistd.h> | 2 #include <string.h>
3 typedef void(*pb)(int); | 3 #include <unistd.h>
4 | 4
5 void download(pb p){ | 5 const char* sign = "/-|\\";
6 int cur = 0; | 6 char s[NUM];
7 int total = 1000; | 7 void processbarCore(int rate){
8 while(cur<=total){ | 8 if(rate<0||rate>100) return;
9 p(cur*100/total); | 9 if(rate!=100) s[rate] = '>';
10 cur+=10; | 10 printf("[%-100s][%d%%][%c]\r",s,rate,sign[rate%4]);
11 usleep(100000); | 11 fflush(stdout);
12 } | 12 s[rate++] = STYLE;
13 printf("\n"); | 13 }
14 } | 14
15 | 15 void processbar(){
16 int main(){ | 16 memset(s,'\0',sizeof(s));
17 download(processbarCore); | 17 int rate = 0;
18 return 0; | 18 while(rate<=100){
19 }
4.颜色样式设计
可以在网上搜做C语言颜色输出,可以改变进度条的样式,大家自行研究,不再赘述