文件操作

C库函数与系统函数

虚拟地址空间

Linux每一个运行的程序(进程), 操作系统都会为其飞培一个0~4G(32位操作系统)的地址空间(虚拟地址空间)

open/close

#include <unistd.h>

int close(int fd);
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>

int open(const char *pathname, int flags);
int open(const char *pathname, int flags, mode_t mode);

flags
  必选: O_RDONLY, O_WRONLY, or O_RDWR
  可选:
    O_CREAT: 创建文件时检测文件是否存在: O_EXCL, 如果存在则返回-1, 必须如O_CREAT一起使用
    O_APPEND: 追加文件
    O_TRUNC: 文件截断
    O_NONBLOCK: 设置非阻塞
mode: 权限并不是传进去的值, 而是mode & ~umask, 创建文件未指定时会随机指定一个数(垃圾值)

zyb@server:~/dir_test_1$ cat open.c 
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdio.h>


int main(int argc, const char *argv[]) {
	int fd = open("haha", O_RDWR | O_CREAT, 0777);
	if (fd == -1) {
		printf("打开失败\n");
	}
 
	close(fd);

	return 0;
}
zyb@server:~/dir_test_1$ gcc open.c -o open
zyb@server:~/dir_test_1$ ./open 
zyb@server:~/dir_test_1$ ll
total 24
drwxrwxr-x  2 zyb zyb 4096 4月  10 17:12 ./
drwxr-xr-x 20 zyb zyb 4096 4月  10 17:12 ../
-rwxrwxr-x  1 zyb zyb    0 4月  10 17:12 haha*
-rwxrwxr-x  1 zyb zyb 8704 4月  10 17:12 open*
-rw-rw-r--  1 zyb zyb  269 4月  10 17:12 open.c

read

#include <unistd.h>
ssize_t read(int fd, void *buf, size_t count);

参数:
  fd: open的返回值
  buf: 缓冲区, 存储要读取的数据
  count: 缓冲区能存储的最大字节数sizeof(buf)
返回值:
  失败: -1
  成功: >0读出的字节数; =0文件读完了

write

#include <unistd.h>
ssize_t write(int fd, const void *buf, size_t count);

参数:
  fd:
  buf: 要写到文件的数据
  count: strlen(buf), 文件数的有效字节数
返回值:
  失败: -1
  成功: >0写入到文件的字节数

zyb@server:~/dir_test_2$ cat read_write.c 
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <fcntl.h>

int main(int argc, char const *argv[])
{
	// 打开一个文件
	int fd1 = open("haha.txt", O_RDWR);
	printf("fd1 = %d\n", fd1);

	// 打开另外一个文件, 写操作
	int fd2 = open("hehe.txt", O_WRONLY | O_CREAT, 0664);
	printf("fd2 = %d\n", fd2);

	char buf[4096];
	int len = read(fd1, buf, sizeof(buf));

	while (len > 0) {
		// 写入数据
		int ret = write(fd2, buf, len);		// 不是能用strlen(buf), strlen以\0为标志来判断字符串
		printf("ret = %d\n", ret);
		// read
		len = read(fd1, buf, sizeof(buf));
	}

	close(fd1);
	close(fd2);

	return 0;
}
zyb@server:~/dir_test_2$ ls
haha.txt  read_write.c
zyb@server:~/dir_test_2$ gcc read_write.c -o app
zyb@server:~/dir_test_2$ ./app
fd1 = 3
fd2 = 4
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 4096
ret = 3603
zyb@server:~/dir_test_2$ ll
total 120
drwxrwxr-x  2 zyb zyb  4096 4月  10 21:57 ./
drwxr-xr-x 21 zyb zyb  4096 4月  10 21:55 ../
-rwxrwxr-x  1 zyb zyb  8872 4月  10 21:56 app*
-rw-rw-r--  1 zyb zyb 48659 4月  10 21:54 haha.txt
-rw-rw-r--  1 zyb zyb 48659 4月  10 21:57 hehe.txt
-rw-rw-r--  1 zyb zyb   647 4月  10 21:55 read_write.c

lseek

#include <sys/types.h>
#include <unistd.h>
off_t lseek(int fd, off_t offset, int whence);

SEEK_SET
SEEK_CUR
SEEK_END

文件指针移动到头部: lseek(fd, 0, SEEK_SET);
获取文件指针当前位置: int len = lseek(fd, 0, SEEK_CUR);
获取文件长度: int len = lseek(fd, 0, SEEK_END);
文件拓展需要两步骤: 执行步骤1并不改变文件的大小
  1. lseek(fd, 1000, SEEK_END);
  2. 要有一次写操作write(fd, "a", 1);

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <fcntl.h>

int main(int argc, char const *argv[])
{
    // 打开一个文件
    int fd1 = open("haha.txt", O_RDWR);
    printf("fd1 = %d\n", fd1);
    if (fd1 == -1) {
        perror("open");
    }   

    int len = lseek(fd1, 1000, SEEK_END);
    printf("len = %d\n", len);

    write(fd1, "a", 1);

    close(fd1);

    return 0;
}

perror

errno不同值对应不同的错误信息
perror("错误信息")

posted @ 2019-04-10 23:44  张飘扬  阅读(177)  评论(0编辑  收藏  举报