1字节(byte)= 比特8(bit)
字长:指CPU一次能够运算的数据的位数,不同计算机不同。例如64位计算机的CPU一次最多处理64位数据。
位:数据存储的最小单位,在二进制系统中,每个0或1就是一个位(bit)
存储类别:
自动变量 auto
静态变量 atatic
寄存器变量 register
外部变量 extern
自动变量:通常在自定义函数内或代码段中(用“{}”)括起来,定义的变量,都是自动变量,除了加了static关键字修饰的变量,也称为 局部变量
外部变量:(即全局变量)是在函数的外部定义的,它的作用域为从变量定义处开始,到本程序文件的末尾。(如果外部变量不在文件的开头定义,其有效的作用范围只限于定义处到文件末尾。如何在定义点之前的函数想引用该外部变量,则应该在引用之前用关键字extern对该变量进行“外部变量声明”。表示该 变量是一个已经定义的外部变量。)
静态变量: 有时希望函数中的局部变量的值在函数调用结束后不消失而保留原值,这就应该指定局部变量为静态局部变量,用关键字static 进行声明。
寄存器变量:为提高效率,C语言允许将局部变量的值存放在CPU的寄存器中,用关键字 register 声明,
注意:
只有局部自动变量和形式参数可以作为寄存器变量
一个计算机系统中的寄存器数目有限,不能定义任意多个寄存器变量
不能使用取地址运算符 “&” 求寄存器变量的地址
动态内存分配
malloc
calloc :与malloc的区别:calloc会把申请的空间的每个字节初始化为全0
void* calloc(size_t num, size_t size);// 为num个大小为size的元素开辟一款空间,并且把空间的每一个字节初始化为0
realloc:可以做到对动态开辟内存大小的调整
void* realloc(void * ptr,size_t size);// pst是要调整额内存地址// size调整之后新大小// 返回值为调整之后的内存起始位置// 这个函数调整原内存空间大小的基础上,还会将原来内存中的数据移动到新的空间
realloc在调整内存空间时存在两种情况
原有空间之后有足够大的空间,扩展内存就在原有内存之后直接追加空间,原有空间的数据不发生变化
原有空间之后没有足够多的空间,在堆空间上另找一个适合大小的连续空间来使用。这样函数返回的是一个新的内存地址,。
如果realloc申请失败返回NULL指针,老空间ptr被置空,造成内存泄露无法找到原有的内存地址。
文件操作
声明库:
#include <stdio.h>
打开文件:
FILE * fp;fp = fopen(char * str1,"str2");// str1为该文件的文件名(即路径),第二为C语言规定的模式字符串
文件指针底层原理:每个被使用的文件,都在内存中开辟了一个相应的文件信息区,用来存放文件的相关信息(文件名,文件状态,文件位置等)这些信息被保存到结构体中,系统为其声明为FILE,每当打开一个文件的时候,系统就会根据情况自动创建一个FILE结构的变量,并且FILE*指针来维护这个结构。
在main.cpp创建文件 hello.txt ,写入些内容
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>int main(){int ch; 用int类型的变量存储EOpFILE* fp = NULL;fp = fopen("hello.txt", "r"); 打开文件采用读的方式while ((ch = getc(fp)) != EOF){putchar(ch);//输出}fclose(fp);}
文件关闭:
int fclose(FILE* stream)
文件的使用方式:

输入内容:
char * strerror(int errnum)// 从内存数组中搜索错误号errnum,并返回一个指向错误消息字符串的指针,// strerror 生成错误字符串取决于开发平台和编译器// 参数errnum 错误号,通常是errno
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>#include <string.h>#include <errno.h>int main(){int ch; 用int类型的变量存储EOpFILE* fp = NULL;fp = fopen("hello.txt", "w+"); 打开文件采用读的方式if (fp == NULL){printf("%s\n", strerror(errno));return 0;}写入一个字符fputc('a', fp);fclose(fp);fp = NULL;return 0;}
读取一个字符
int ch =fgetc(fp);if(ch!=EOF) // 如果读取的{printf("%c",ch);}
读取指定长度的数据
//定义一个数组char arr[10] = {0};// 在文件指针fp当中读取前五个数据,存放到arr数组当中fgets(arr,5,fp); //将所读取的数据放入arr中printf("%s\n",arr)
将结构体信息写入文件中
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>#include <string.h>#include <errno.h>typedef struct S{char name[10];int age;}stu;int main(){FILE* pf = fopen("stu.txt", "w");if (pf != NULL){stu s = { "小明",18 };// 文件指针 文件写入格式 文件内容fprintf(pf, "%s %d\n", s.name, s.age);fclose(pf);pf = NULL;}return 0;}/* 文件中保存.....小明 18*/
读取文件到结构体中:
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>#include <string.h>#include <errno.h>typedef struct S{char name[10];int age;}stu;int main(){FILE* pf = fopen("stu.txt", "r");if (pf != NULL){stu s;//在文件指针pf中按照 字符串 整型 的格式保存到结构体指针中fscanf(pf, "%s %d", s.name, &s.age);printf("%s %d\n", s.name, s.age);fclose(pf); //关闭pf文件指针pf = NULL; //将文件还真赋值为空}return 0;}// 将stu.txt 文件的内容读取出来
文件的随机读写:指定我们想要读写的位置
fssek()函数:该函数可以从定位位置的偏移量处开始读写
int fseek(FILE*stream,long offset,int origin)//参数分别为 文件流 偏移量,起始位置指针(固定的)// 返回值// 如果成功,fseek返回0,否则它返回一个非零值,在无法查找的设备行,返回值未定义
三种定位指针:
| 名称 | 参考位置 |
| SEEK_SET | 文件开始位置 |
| SEEK_CUR | 当前的文件指针点 |
| SEEK_END | 文件结束点 |
举例:(26英文字母的文件)
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>#include <string.h>#include <errno.h>int main(){FILE* pf = fopen("a.txt", "r");if (pf == NULL){printf("%s\n", strerror(errno));return 0;}定位指针,从开头向后偏移5个单位fseek(pf,5, SEEK_SET);int ch = fgetc(pf);printf("%c\n", ch);//第二次读取,当前指针向后便宜5个单位fseek(pf, 3, SEEK_CUR);ch = fgetc(pf);printf("%c\n", ch);//第三次读取,从文件末尾向前偏移3个单元fseek(pf,-8, SEEK_END);ch = fgetc(pf);printf("%c\n", ch);//关闭文件fclose(pf);pf = NULL;return 0;}
注意:
在每次使用完一次fssek函数后,文件指针会自动向后移动一位。
ftell函数:该函数可以返回文件指针相对于起始位置的偏移量
long int ftell(FILE*stream);
rewind()函数:让文件回到文件初始位置
void rewind(FILE* stream);
#define _CRT_SECURE_NO_WARNINGS#include <stdio.h>#include <string.h>#include <errno.h>int main(){FILE* pf = fopen("a.txt", "r");if (pf == NULL){printf("%s\n", strerror(errno));return 0;}//定位指针,从开头向后偏移5个单位fseek(pf,5, SEEK_SET);int ch = fgetc(pf);printf("%c\t", ch);//s输出相对于起始位置的偏移量printf("%d\n", ftell(pf));//第二次读取,当前指针向后偏移5个单位//让文件指针回到文件初始位置rewind(pf);fseek(pf, 3, SEEK_CUR);ch = fgetc(pf);printf("%c\t", ch);printf("%d\n", ftell(pf));//第三次读取,从文件末尾向前偏移3个单元fseek(pf,-8, SEEK_END);ch = fgetc(pf);printf("%c\t", ch);printf("%d\n", ftell(pf));//关闭文件fclose(pf);pf = NULL;return 0;}
二进制写入文件
size_t fwrite(const void *buffer,size_t size, size_t count, FILE*stream);
例如:
Peo p = { "lisi", 19 };fwrite(&p, sizeof(Peo), 2, pf);fclose(pf);pf = NULL;
读取二进制文件信息
size_t fread(void * buffer,size_t size,size_t count ,FILE*stream);
Peo p = { 0 };fread(&p, sizeof(Peo), 1, pf);printf("%s %d\n", p.name, p.age);fclose(pf);pf = NULL;
文件读取结束原因函数feof()函数
文件读取结束有两种情况:
读取过程中出现异常
读取到文章末尾
文本文件
如果用fgetc()读取,要判断feof()的返回值是否为EOF
如果用fgets()读取,要判断feof()的返回值是否为NULL(0);
二进制文件:
都是使用fread()读取,要判断其返回值与指定读取个数的大小,如果小于实际要读的个数,就说明发生读取异常,如果等于实际要读的个数,就说明是因读取成功而结束;对于读取异常的判断,我们考虑判断ferror()函数的返回值。
若ferror()为真-----异常读取而结束
若feof()为真-------正常读取到尾而结束




