二进制文件:按内存中的存储形式放,C的目标文件和可执行文件(涉及到了计算机处理)
二进制文件效率更高,更安全
文本文件:存储ASCII码;C的源文件
缓冲文件系统,自动分配内存缓存区。非缓冲文件系统需要手动分配
缓冲文件系统的文件缓冲区位于内存数据区中
扇区:512B(字节)
例如,整数1234
typedef struct{
short level; /* 缓冲区使用量 */
unsigned flags; /* 文件状态标志 */
char fd; /* 文件描述符 */
short bsize; /* 缓冲区大小 */
unsigned char *buffer; /* 文件缓冲区的首地址 */
unsigned char *curp; /* 指向文件缓冲区的工作指针 */
unsigned char hold; /* 其他信息 */
unsigned istemp;
short token;
} FILE;
FILE不仅仅是文件的位置,FILE->curp指示文件缓冲区中的数据存储位置
fp++会移动向下一个FILE结构,不能fp++,fp会自动后移,关闭文件后再打开,文件指针则会自动回到开头
fp指向文件在缓冲区上的读写位置
文件处理方式(二进制位rb,rb+这样)
r 只读 w 建立新文件写 a 追加(没有则建立新文件) r+ 读/写 w+
a+
C语言允许同时打开多个文件
不同的文件对应不同的文件指针
不允许同一个文件在关闭前再次打开
文件操作流程
定义文件指针
FILE *fp;
if((fp=fopen("xxxx.txt","r"))==NULL){
printf("mistake");
exit(0); 0表示正常结束
}
复制数据
while(!feof(fp1)){
ch=getc(fp1);
if(ch!=EOF)futc(ch,fp2);
}
关闭文件
if( fclose(fp)){
printf( "Can not close the file!\n" );
exit(0);
}
文件函数(均在stdio.h)
ch=fgetc(fp); 读入一个字符 末尾EOF
fputc(ch,fp); 把ch写入文件fp中 错误EOF
fgets(str,n,fp); fp中读n-1个字符到str中(自动加‘\0'补位) 错误NULL
读完or接受到'\n'(保留)或者EOF(不保留)结束
fputs(str,fp) str写入fp(成功则返回所写的最后一个字符) 错误EOF
fread(待读入地址,数据块地址,数据块个数,fp)多用于二进制
fwrite(待输出地址,数据块地址,数据块个数,fp)多用于二进制
u 只有fscanf,fprintf的fp在开头,其他都在最后。只有fgets错误是NULL,其余EOF
fscanf(fp,“%d”,&a) 规则同scanf
fprintf(fp,“%d",a) 规则同printf
fopen() 错误NULL
fclose(fp) 正确0 错误EOF
rewind(fp) 返回开头
ftell(fp) 当前相对于文件头位置 错误EOF
fseek(fp,位移,开始处) ¨SEEK_SET、SEEK_CUR、SEEK_END;20L(L必须加,-20L表示向右)
feof(fp) 是否到结尾 结束1真 否则0假
ferror(fp) 0表示正常未出错
clearerr(fp) 清楚出错标志和文件结束标志
动态分配
#include<stdlib.h>需要这个库
int *a = (int*)malloc(sizeof(int)); 分配的空间需要有指针指向它
int *a = (int*)malloc(n*sizeof(int)); 数组a[n]
struct List*p;
p = (struct List*)malloc(sizeof(struct List));
free(a);
int *a = (int*)calloc(n,sizeof(int)); 并且全部初始化为0
realloc(p,sizeof(int)) 重新分配
链表
构造链表
struct List{
int data;
struct List *next;
}
读取链表
struct List *readlist(){
int data;
struct List *p , *head=NULL,*tail;
scanf("%d",&data);
while(data!=-1){
p = (struct List*)malloc(sizeof(struct List));
p->data=data;
if(head==NULL) head=p;
else tail->next=p;
tail=p;
scanf( "%d" ,&data);
}
return head;
}
不能用p++到下一个链表,因为链表的位置不是连续的
命令行参数
命令名 参数1 参数2 ... 参数n
argv[0] argv[1] argv[2] argv[n]
argc=n+1
int main(int argc, char argv[]){
}