您的位置:首页 > 运维架构 > Linux

Linux c 文件管理简介

2007-02-28 11:32 253 查看
Linux下可以通过系统调用来读写文件,也可以通过标准函数库来读写文件。
1) 系统调用

open()

声明:
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h> //Linux系统不需要这个头文件
int open(const char *path, int oflags);
int open(const char *path, int oflags, mode_t mode);oflags参数:
当调用open系统调用的时候,下面三个参数,必须要选择一个作为参数:
O_RDONLY // 打开的文件只能读
O_WRONLY // 打开的文件只能写
O_RDWR // 打开的文件可以读也可以写

除了上面的参数,还可以添加一下参数(他们是可选的):
O_APPEND // 写文件的时候从文件尾开始写
O_TRUNC // 清空文件内容
O_CREAT // 创建文件
O_EXCL // 当存在O_CREAT参数的时候,O_EXCL确保只有在文件不存在的时候才建立文件mode参数:
只有在oflags参数中含有O_CREAT才使用下面的参数
S_IRUSR // 建立文件时,权限设置为创建文件的用户可读
S_IWUSR // 建立文件时,权限设置为创建文件的用户可写
S_IXUSR // 建立文件时,权限设置为创建文件的用户可执行
S_IRGRP // 建立文件时,权限设置为创建文件的用户所在组的所有用户可读
S_IWGRP // 建立文件时,权限设置为创建文件的用户所在组的所有用户可写
S_IXGRP // 建立文件时,权限设置为创建文件的用户所在组的所有用户可执行
S_IROTH // 建立文件时,权限设置为其他用户可以读
S_IWOTH // 建立文件时,权限设置为其他用户可以写
S_IXOTH // 建立文件时,权限设置为其他用户可以执行

注意,创建出来的文件权限不一定和这里设置的一模一样,因为umask会影响权限的值,详细参考:http://www.i170.com/user/killercat/Article_54617 中的(3)访问权限返回值:
返回值是一个文件描述符,-1表示open()调用失败范例:
int f = open("/home/killercat/Desktop/1",O_CREAT | O_TRUNC | O_EXCL | O_WRONLY, S_IRUSR | S_IWUSR); // 打开/home/killercat/Desktop/1文件,建立的文件权限设置成用户可读可写(这个和umask有关)

int f = open("/home/killercat/Desktop/1",O_RDWR); // 打开一个文件,可读也可以写

write()

声明:
#include <unistd.h>
size_t write(int fildes, const void *buf, size_t nbytes);
读取buf数组中长度为nbytes个字节的数据到fildes文件描述符,表示的文件中去,返回值为真正写入了多少字节的数据范例:
write(1,"hello world",5); // 在文件描述符1表示的文件中写入"hello",实际上就是在屏幕打印hello

int f = open("/home/killercat/Desktop/1",O_RDWR);
write(f,"hello world",11); // 向/home/killercat/Desktop/1中写入"hello world"

read()

声明:
#include <unistd.h>
size_t read(int fildes, const void *buf, size_t nbytes);
读取文件描述符fides表示的文件中长度为nbytes字节的数据到 buf 数组中去,返回为实际读的数据的长度,注意从什么位置开始读取数据,有一个指针决定,文件指针可以通过lseek()系统调用修改,刚被打开的文件中,文件指针指向文件首位置范例:
char buf[1024];
int f = open("/home/killercat/Desktop/1",O_RDWR);
read(f,buf,11); // 读取文件"/home/killercat/Desktop/1"中11个字节,保存到buf中去,注意一下,读取的是字节,也就是一个中文字,应该读取2个字节(gbk编码)

close()

声明:
#include <unistd.h>
int close(int fildes);
关闭文件描述符为fides的文件,成功时返回0,失败返回-1。注意,进程被结束的时候,与之有关的文件都会被关闭,我们这时候不需要调用close();范例:
int f = open("/home/killercat/Desktop/1",O_RDWR);
close(f);

使用系统调用,写一个复制文件的程序

#include <unistd.h>
#include <sys/stat.h>
#include <fcntl.h>
int main(){
int fin,fout;
char buf[1024]; // 之所以用char类型,是因为 read write 的单位是字节
fout = open("/home/killercat/Desktop/llh(2).mp3",
O_CREAT|O_WRONLY|O_TRUNC|O_EXCL,S_IRUSR|S_IWUSR);
fin = open("/home/killercat/Desktop/llh.mp3",O_RDONLY);
if(fin == -1 || fout == -1)
return -1;
int len;
while((len=read(fin,buf,sizeof(buf)))>0)
write(fout,buf,len);
close(fin);
close(fout);
return 0;
}

2) 库函数:

fopen()

声明:
#include <stdio.h>
FILE *fopen(const char *filename, const char *mode);
通过路径或者文件名字打开一个文件,打开需要设置一定的模式,返回一个FILE类型的结构体指针mode参数:
"r" // 打开文件只能用于读,文件不存在,调用就会失败,返回值为 NULL
"w" // 打开文件只能用于写,文件不存在就被创建一个新文件,文件存在就清空里面的内容,写入数据从文件开始处开始
"a" // 打开文件只能用于写,文件不存在就被创建一个新文件,写入数据从文件结束处开始
"rb","wb","ab" // 表示使用的是二进制方式打开文件,有时候,如果没有使用二进制方式打开二进制文件,会导致读到的数据被破坏
"r+" // 打开的文件可以读也可以写,文件不存,调用就会失败,返回值为 null,写文件的位置为文件开头
"w+" // 打开文件可以读也可以写,文件不存在就被创建一个新文件,文件存在就清空里面的内容,写入数据从文件开始处开始
"a+" // 打开文件可以读也可以写,文件不存在就被创建一个新文件,写入数据从文件结束处开始
"rb+" "wb+" "ab+" // 二进制方式

请参考http://www.i170.com/user/killercat/Article_35858,它大概讲述了模式中,是否有“b”造成的影响范例:
FILE* fin = fopen("/home/killercat/Desktop/1","r+");

fwrite()

声明:
#include <stdio.h>
size_t fwrite(void *ptr, size_t size, size_t nitems, FILE *stream);
把ptr数组中的数据,写入stream对应的文件中,写入数据一共有size*nitems字节。
fwrite是通过记录(record)来处理写入数据,size,表示记录的大小,nitems表示记录的个数。
返回值是成功写入数据的组数,失败返回NULL范例:
char buf[1024];
FILE* fout = fopen("/home/killercat/Desktop/1","w+");
fwrite(buf,5,2,fout);
一共写入10个字节的数据

fread()

声明:
#include <stdio.h>
size_t fread(void *ptr, size_t size, size_t nitems, FILE *stream);
把stream对应的文件中size*nitems个字节的数据写入ptr数组。
fread()也是通过记录(record)来处理数据的,size,表示记录的大小,nitems表示记录的个数。
返回值是成功读取数据的组数,失败返回NULL范例:
char buf[1024];
FILE* fin = fopen("/home/killercat/Desktop/1","w+");
fread(buf,5,2,fin);
一共读入10个字节的数据

close()

#include <stdio.h>
int fclose(FILE *fp);
关闭文件

fgetc() fputc()

int fgetc(FILE *);
fputc(int,FILE *);一个字符一个字符的读写。而内部实现并不是这么做,库函数会一块一块的读(写)文件,每次读(写)一块,它们会被放到一个缓冲中去,然后再从缓冲中读取数据,直到数据全部读完,才继续读(写)一块文件,所以即使fgetc,fputc一次只读写一个字节,也不会影响效率,fgetc()返回EOF表示结束。

使用标准函数库,写一个复制文件的程序

#include <stdio.h>
int main(){
FILE *fin,*fout;
int c;
fin = fopen("/home/killercat/Documents/Movie/天狗.rmvb","r");
fout = fopen("/home/killercat/Desktop/llh(2).mp3","w");
if(fin == NULL || fout == NULL)
return -1;
while((c=fgetc(fin)) != EOF){
fputc(c,fout);
}
fclose(fin);
fclose(fout);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: