红联Linux门户
Linux帮助

linux----进度条小代码

发布时间:2017-01-05 10:27:16来源:linux网站作者:逆风的方向我在飞翔
在写进度条代码之前,需要了解缓冲区和回车换行的概念:
 
回车换行
一:回车换行
符号  ASCLL码  意义 
\r   13    回车CR
\n   10    换行NL
在ascii中,回车和换行是不同的字符。0x0A是回车,即光标移动到本行的最左面; 0x0D是换行,即光标
移动到下一行。
回车 \r :本义是光标重新回到本行开头,r的英文return,控制字符可以写成CR,即Carriage Return
换行 \n : 本义是光标往下一行(不一定到下一行行首),n的英文newline,控制字符可以写成LF,即
Line Feed
二:回车换行针对的系统
对于回车换行针对不同的操作系统: windows下enter是 \n\r,unix下是\n,mac下是\r
windows创建的文件是 \n\r结束的, 而Linux,mac这种unix类系统是\n结束的。
例如:
linux----进度条小代码
分别在Windws和Linux中查看此文件可知:
Linux中遇到换行符("\n")会进行回车+换行的操作,回车符反而只会作为控制字符("^M")显示,不发生回车的操作。而windows中要回车符+换行符("\r\n")才会回车+换行,缺少一个控制符或者顺序不对都不能正确的另起一行。
windows换行是\r\n,十六进制数值是:0D0A。
LINUX换行是\n,十六进制数值是:0A
所以在linux保存的文件在windows上用记事本看的话会出现黑点,我们可以在LINUX下用命令把linux的文件格式转换成win格式的。
unix2dos 是把linux文件格式转换成windows文件格式
dos2unix 是把windows格式转换成linux文件格式。
 
缓冲区
一:缓冲区:
针对的是输入输出数据。其又称缓存,是内存空间的一部分存储空间,这些存储空间是用来缓冲输入输出
数据的。
Buffer和Cache:
buffer和cache是两个不同的概念:cache是高速缓存,用于CPU和内存之间的缓冲;buffer是I/O缓存,
用于内存和硬盘的缓冲;简单的说,cache是加速“读”,而buffer是缓冲“写”,前者解决读的问题,
保存从磁盘上读出的数据,后者是解决写的问题,保存即将要写入到磁盘上的数据。
二:为什么要有缓冲区:
在此之前举一个例子:
你有一盒子牙签,200根全掉在地上了,你的全都捡回桌子上。现在有里两种方式:
-----------不用缓冲的方式------------
你蹲下,用右手拿一根牙签,站起来,把那根牙签放在桌子上。
重复这个动作200次。
-----------用缓冲的方式----------------
你蹲下,用右手拿一根牙签,放在左手上。等你的左手拿不下了,站起来把左手的牙签都放在桌上。
再蹲下重复。
在这个方式中,你的左手就是缓冲。缓冲能提交效率的原理就是减少了“蹲下/站起”这个比较费力费时的动作的次数:类似的道理:
在I/O过程中,cpu读取磁盘的速度相对内存读取速度要慢的太多,毕竟让cpu读取数据的时候不能总是在硬盘中读取,否则你cpu光读取数据了,其它的事也就不用做了。因此为了能够加快处理数据的速度,就需要将读取过的数据缓存在内存里。
换句话说,buffer(缓冲区)是一个用于存储速度不同步的设备或优先级不同的设备之间传输数据的区域。一方面,通过缓冲区,可以使进程之间的相互等待变少,从而使从速度慢的设备读入数据时,速度快的设备的操作进程不发生间断。另一方面,可以保护硬盘或减少网络传输的次数。
缓冲区就是一块内存区,它用在输入输出设备和CPU之间,用来缓存数据。它使得低速的输入输出设备和高速的CPU能够协调工作,避免低速的输入输出设备占用CPU,解放出CPU,使其能够高效率工作。
三:缓冲区的类型:
全缓冲:缓冲区满之后才进行I/O操作。
行缓冲:遇到/n之后,执行I/O操作
无缓冲:不进行缓冲,标准出错情况stderr是典型代表,这使得出错信息可以直接尽快地显示出来。
四:缓冲区的刷新:
只有缓冲区被刷新的时候缓冲区中的内容才会写入真实的文件或输出设备上。
下列情况会引发缓冲区的刷新:
1.缓冲区满时;
2.行缓冲区遇到回车时;
3.关闭文件;
C语言:
4.使用特定函数刷新缓冲区: fflush(stdout) 清空输出缓冲区 ; fflush(stdin): 清空输入缓冲区
定义函数:int fflush(FILE* stream);
函数说明:fflush()会强迫将缓冲区内的数据写回参数stream 指定的文件中. 如果参数stream 为
NULL,fflush()会将所有打开的文件数据更新.
返回值:成功返回0, 失败返回EOF, 错误代码存于errno 中.
c++ :
4.用操纵符显示地刷新缓冲区,如用endl,flush等.
5.在每次输出操作执行完毕后,用unitbuf操纵符设置流的内部状态,从而清空缓冲区。
6. 可将输出流与输入流关联起来,在读输入流时将刷新其关联的输出缓冲区
实例:
c语言:
printf("hello world");
fflush(stdout);//结果直接输出,即使缓冲区没满
c++ :
// 操纵符
cout << "hi!" << flush; // flushes the buffer, adds no data
cout << "hi!" << ends; // inserts a null, then flushes the buffer
cout << "hi!" << endl; // inserts a newline, then flushes the buffer
// unitbuf操纵符
cout << unitbuf << "first" << " second" << nounitbuf;
// unitbuf会在每次执行完写操作后都刷新流
// 上条语句等价于
cout << "first" << flush << " second" << flush;
// nounitbuf将流恢复为正常的,由系统管理的缓冲区方式
// 将输入输出绑在一起
// 标准库已经将cin和cout绑定在一起
// 我们可以调用tie()来实现绑定
cin.tie(&cout); // the library ties cin and cout for us
ostream *old_tie = cin.tie();
cin.tie(0); // break tie to cout, cout no longer flushed when cin is read
cin.tie(&cerr); // ties cin and cerr, not necessarily a good idea!
cin.tie(0); // break tie between cin and cerr
cin.tie(old_tie); // restablish normal tie between cin and cout
 
Sleep函数:
功能: 执行挂起一段时间  
用法: unsigned sleep(unsigned seconds);  
注意:
在VC中使用带上头文件#include < windows.h>,在Linux下,gcc编译器中,使用的头文件因gcc版本的不同而不同#include < unistd.h> 
在VC中,Sleep中的第一个英文字符为大写的"S" ,在linux下不要大写,在标准C中是sleep, 不要大写,简单的说VC用Sleep, 别的一律使用sleep
在VC中,Sleep()里面的单位,是以毫秒为单位,所以如果想让函数滞留1秒的话,应该是
Sleep(1000); 在Linux下,sleep()里面的单位是秒,而不是毫秒。
 
usleep函数:
功能:usleep功能把进程挂起一段时间, 单位是微秒us(百万分之一秒)。
语法: void usleep(int micro_seconds);
返回值: 无
注意:这个函数不能工作在 Windows 操作系统中。
usleep() 与sleep()类似,用于延迟挂起进程。进程被挂起放到reday queue。只是一般情况下,延迟时间数量级是秒的时候,尽可能使用sleep()函数。且此函数已被废除,可使用nanosleep。 
如果延迟时间为几十毫秒,或者更小,尽可能使用usleep()函数。这样才能最佳的利用CPU时间。
 
delay函数: 
功能: 将程序的执行暂停一段时间,单位是毫秒ms(千分之一秒)  
用法: void delay(unsigned milliseconds)
delay()是循环等待,该进程还在运行,占用处理器。
sleep()不同,它会被挂起,把处理器让给其他的进程。
 
一个简单进度条代码(vs和gcc)
linux----进度条小代码
#include<string.h>
#include<windows.h> //gcc下可以不加这个头文件
#include<stdio.h>
void fun()
{
// printf("hello bit\n");
char a[101];
int count = 1;
memset(a, ‘\0’,sizeof (a));
char *c = "|/-\";
int i = 0;
while(count <= 100)
{
i = 0;
while(i<4)
{
a[count-1] = ‘#’;
printf( "[%-100s] [%d%%] [%c] \r",a,count++,c[i++]);
fflush(stdout); //使得缓冲区立即输出
Sleep(100); //gcc这个sleep函数单位是秒,我用usleep(10000)单位微秒
}
}
}
int main()
{
fun();
return 0;
}
 
本文永久更新地址:http://www.linuxdiyf.com/linux/27536.html