一.Linux目录结构以及文件操作

📅 发布时间:2026/7/4 8:41:16 👁️ 浏览次数:
一.Linux目录结构以及文件操作
目录常用的Linux指令vi文件名用vi打开/创建某个文本文件1.open函数2.close函数3.Linux文件权限4.write函数5.Read函数6.lseek函数光标的偏移量7.fopen函数8.fclose函数8.fread函数9.fwrite函数10.fseek函数11.三类读写函数常用的Linux指令cd文件夹名字访问某个文件夹cd..切换到上级目录cd-返回上次操作的目录ls显示当前目录的文件touch文件名创建文件rm文件名删除文件mkdir目录名创建目录rm-rf目录名删除目录TAB键补全sudo命令用管理员权限执行命令pwd显示当前目录的绝对路径vi文件名用vi打开/创建某个文本文件与touch的区别touch是纯创建 / 更新文件的工具只生成空文件或改文件时间戳不打开编辑界面一步完成执行touch test.c就生成空文件vi是文本编辑器创建文件的同时直接打开编辑界面核心用途是写 / 改文件内容。多步1. 执行vi test.c进入编辑界面2. 按i进入编辑模式写内容3. 按Esc:wq保存退出文件才生效vi常用的两种模式命令行模式按ESC进入,在这个状态下可以输入命令常用命令: 行号跳转到某一行G跳转到文本末尾yy: 复制某一行复制的位置由光标所在位置决定yx复制若干行x代表行数输入2就是复制当前行和它下面的两行总共三行复制的位置由光标所在位置决定。p把刚刚复制的内容进行粘贴粘贴的位置由光标所在位置决定:wq 保存文本并退出:q 正常退出文本:q! 强制退出文本:set nu 程序显示行号dd 删除一行ESC: ggG 自动整理代码文本输入模式按i进入进入文本输入模式即可编辑代码注意只能键盘操作 鼠标不行。1.open函数man 1是普通的shell命令比如ls。man 2是系统调用函数比如openwrite说明。如何打开man 1 lsman 2 open在Linux系统库的定义int open(const char *pathname, intflags); /* 比较常用*/ int open(const char *pathname, intflags, mode_tmode); //包含的头文件 #include sys/types.h//这里提供类型pid_t和size_t的定义 #include sys/stat.h #include fcntl.h成功返回句柄我们后面对于文件的读写关闭等都通过句柄来操作。失败返回-1。O_APPEND 表示追加如果原来文件里面有内容则这次写入会写在文件的最末尾。0x00002000O_CREAT 表示如果指定文件不存在则创建这个文件 0x0000 0100O_EXCL 表示如果要创建的文件已存在则出错同时返回-1并且修改errno 的值。O_TRUNC 表示截断如果文件存在并且以只写、读写方式打开则将其长度截断为0。O_NOCTTY 如果路径名指向终端设备不要把这个设备用作控制终端2.close函数参数说明在Linux系统库的定义int close(int fd);包含的头文件#include unistd.h3.Linux文件权限Linux 系统中采用三位十进制数表示权限如0755 0644.7 1245 145 14ABCDA- 0 表示十进制B用户C组用户D其他用户‐‐‐ ‐ 0 (no excute , nowrite ,no read)‐‐x ‐ 1 excute, (nowrite, no read)‐w‐ ‐ 2 writer‐‐ ‐ 4 read‐wx ‐ 3 write, excuter‐x ‐ 5 read, excuterw‐ ‐ 6 read, writerwx ‐ 7 read, write , excute例如07550十进制文件7124用户拥有读写可操作的权限514组用户拥有可读可操作权限514其他用户拥有可读可操作权限例子#include stdio.h #include sys/types.h #include sys/stat.h #include fcntl.h #include unistd.h int main() { int fd; //file describe fd open(MM1,O_RDONLY|O_CREAT0755); if(fd -1) { printf(open failed!\n); return -1; } printf(success!\n); close(fd); return 0; }这里的fd是文件标识符可以用RTOS中的句柄来理解文件的读写和关闭等都是通过操作fd来完成。dapeiubuntu:~$ ls -l 总用量 60 -rwxrwxr-x 1 dapei dapei 8384 3月 8 05:12 demo -rwxrwxr-x 1 dapei dapei 8384 3月 5 06:01 hello -rw-rw-r-- 1 dapei dapei 300 3月 8 05:11 hello.c -rw-rw-r-- 1 dapei dapei 0 3月 5 05:22 mm -rwxr-xr-x 1 dapei dapei 0 3月 8 05:12 MM1 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 公共的 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 模板 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 视频 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 图片 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 文档 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 下载 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 音乐 drwxr-xr-x 2 dapei dapei 4096 3月 5 02:14 桌面rwx即读写可操作的权限r-x即读和可操作权限以此类推。创建的MM1文件权限也是与0755一一对应。4.write函数write()会把参数buf所指的内存写入count个字节到参数fd所指的文件内。ssize_twrite (int fd,const void * buf, size_t count);fd: 文件描述符*buf: 写入的数据的首地址count: 写入数据个数返回值如果顺利write()会返回实际写入的字节数len。当有错误发生时则返回-1错误代码存入errno中#include stdio.h #include sys/types.h #include sys/stat.h #include fcntl.h #include unistd.h //ssize_t write(int fd, const void *buf, size_t count); int main() { int fd; //file describe char writebuff[]hello world\n; fd open(MM2,O_RDWR|O_CREAT,0755); if(fd -1) { printf(open failed!\n); return -1; } printf(success!\n); write(fd,writebuff[0],sizeof(writebuff)); close(fd); return 0; }5.Read函数从打开的fd设备或文件中读取count个字节到buf中ssize_tread(int fd,void * buf, size_t count);fd: 文件描述符*buf: 读入数据的首地址count: 读入数据的个数返回值成功返回读取的字节数出错返回-1并设置errno如果在调read之前已到达文件末尾则这次read返回0使用方法与write函数相同。main函数参数int main(int argc,char *argv[]) { return 0; }C语言规定了main函数的参数只能有两个一个是argc,一个是argv。并且argc只能是整数第二个必须是指向字符串的指针数组。argc: 参数表示命令行中参数的个数注意 文本名本身也是一个参数argc的值是在输入命令行时由系统按实际参数的个数自动赋予的。argv 参数是字符串指针数组其各元素值为命令行中各字符串(参数均按字符串处理)的首地址。 指针数组的长度即为参数个数。数组元素初值由系统自动赋予。实现cp指令流程src 源文件des目标文件打开源文件srcopen打开目标文件des open写入目标文件 write读取src文件到缓存数组 read关闭目标文件和源文件 close./a.out src.c des.c例子#include stdio.h #include sys/types.h #include sys/stat.h #include fcntl.h #include unistd.h #include string.h int main(int argc,char *argv[]) { int src_fd; int des_fd; char readbuff[512] {0}; int readnum; if(argc ! 3) { printf(error\n); return -1; //返回值非0主动中止程序 } src_fd open(argv[1],O_RDWR); readnum read(src_fd,readbuff,512); des_fd open(argv[2],O_RDWR|O_CREAT); write(des_fd,readbuff,readnum); close(src_fd); close(des_fd); return 0; }6.lseek函数光标的偏移量off_t lseek(int fd, off_t offset, int whence);fd : 文件描述符Offset 偏移量Whence :SEEK_SET: 参数offset即为新的读写位置SEEK_CUR: 以目前的读写位置往后增加offset个偏移量SEEK_END: 将读写位置指向文件尾后再增加offset个位移量当whence值为SEEK_CUR或SEEK_END时参数offset允许负值的出现。返回值 文件读写距离文件开头的字节大小出错返回 -1#include stdio.h #include sys/types.h #include sys/stat.h #include fcntl.h #include unistd.h #include string.h int main() { int fd; char buff[32] {0}; off_t pos; // 存储lseek返回的指针位置 // 1. 创建并打开文件读写模式清空旧内容 fd open(lseek_demo.txt, O_RDWR | O_CREAT | O_TRUNC, 0755); if (fd -1) { perror(open failed); return 1; } // 2. 写入初始内容hello world 12345 char *content hello world 12345; write(fd, content, strlen(content)); printf(初始写入内容%s\n, content); // 3. 用lseek将指针移到文件开头写入后指针在末尾直接读会空 pos lseek(fd, 0, SEEK_SET); printf(指针移到开头当前位置%ld\n, pos); // 4. 读取前5个字符hello read(fd, buff, 5); printf(读取前5字符%s\n, buff); memset(buff, 0, sizeof(buff)); // 清空缓冲区 // 5. 用lseek从当前位置5往后移6位 → 位置11指向1 pos lseek(fd, 6, SEEK_CUR); printf(指针后移6位当前位置%ld\n, pos); // 6. 读取从位置11开始的5个字符12345 read(fd, buff, 5); printf(读取偏移后字符%s\n, buff); // 7. 用lseek从末尾往前移5位 → 指向1验证SEEK_END pos lseek(fd, -5, SEEK_END); printf(指针从末尾前移5位当前位置%ld\n, pos); memset(buff, 0, sizeof(buff)); read(fd, buff, 5); printf(读取末尾前5字符%s\n, buff); // 8. 关闭文件 close(fd); return 0; }运行得到初始写入内容hello world 12345指针移到开头当前位置0读取前5字符hello指针后移6位当前位置11读取偏移后字符12345指针从末尾前移5位当前位置11读取末尾前5字符123457.fopen函数fopen fwrite fread fclose 属于标准C库include stdio.h standard io libopen close write read 属于Linux系统调用。可移植性fopen 强过于 openfopen 在用户态是缓存的。open 在用户态是没有缓存的函数原型FILE * fopen(constchar *path , cost char *mode) /* * description : 打开一个文件 * param ‐ path : 指定文件路径,如./test.txt * param ‐ mode 指定文件的打开方式 * return : 成功返回指向该文件的文件指针; 若失败返回 NULL */参数说明第一个参数为欲打开文件的文件路径及文件名第二个参数表示对文件的打开方式。注mode有以下值r只读方式打开文件必须存在r可读写文件必须存在rb打开二进制文件可以读写rt:打开文本文件可读写w:只写文件存在则文件长度清0文件不存在则建立该文件w:可读写文件存在则文件长度清0文件不存在则建立该文件a:附加方式打开只写不存在建立该文件存在写入的数据加到文件尾EOF符保留a附加方式打开可读写不存在建立该文件存在写入的数据加到文件尾EOF符不保留wb打开二进制文件只写 wb:打开或建立二进制文件可读写wt:打开或建立文本文件可读写at:打开文本文件可读写写的数据加在文本末尾 ab:打开二进制文件可读写写的数据加在文件末尾由mode字符可知上述如r、w、a在其后都可以加一个b表示以二进制形式打开文件8.fclose函数关闭一个文件流使用fclose就可以把缓冲区内最后剩余的数据输出到磁盘文件中并释放文件指针和有关的缓冲区。函数原型int fcloseFILE*stream /* * description :关闭一个已打开的流 * param ‐ stream :文件指针流 * return : 成功返回0; 若失败返回EOF */例子#include stdio.h int main() { FILE *fp NULL; int f_cl 0; fp fopen(fopen,w); if(fp NULL) { printf(open failed!\n); return -1; } printf(success\n); f_cl fclose(fp); if(f_cl) { printf(close failed!\n); return -2; } printf(close success!\n); return 0; }如代码所示生成一个“fopen”文件权限w只写8.fread函数从文件中读入数据到指定的地址中函数原型:size_t fread(void*buff , size_t size, size_t count , FILE* stream) /* * description :对已打开的流进行数据读取 * param ‐ ptr 指向 数据块的指针 * param ‐ size 指定读取的每个数据项的字节数 * param ‐ nmemb : 指定要读取的数据项的个数 * param ‐ stream 要读取的文件流 * return : 返回实际读取数据项的个数; */9.fwrite函数从指定的地址中写入数据到文件中函数原型:int fwrite(void*bufferintsizeintcountFILE*fp) /* * description :对已打开的流进行写入数据块 * param ‐ ptr 指向 数据块的指针 * param ‐ size 指定写入的每个数据项的字节数如调用sizeof(char) * param ‐ nmemb :指定写入的数据项的个数 * param ‐ stream 要写入的文件流 * return : 返回实际写入的数据项的个数 */10.fseek函数函数原型:int fseek(FILE *stream,long offset,int framewhere)参数第一个为文件指针第二个是指针的偏移量第三个是指针偏移起始位置返回值重定位成功返回0否则返回非零值说明执行成功则stream指向以fromwhere为基准偏移offset个字节的位置。执行失败(比方说offset偏移的位置超出了文件大小)则保留原来stream的位置不变分别用3个宏SEEK_SET 既0 文件开头SEEK_CUR 既1 文件当前位置SEEK_END 既2 文件结尾例如1. fseek(fp,100L,SEEK_SET);把fp指针移动到离文件开头100字节处2. fseek(fp,100L,SEEK_CUR);把fp指针移动到离文件当前位置100字节处3. fseek(fp,100L,SEEK_END);把fp指针退回到离文件结尾100字节处。11.三类读写函数一类行缓存 遇到换新行\n或者写满缓存时即调用系统调用函数读fgets,gets,printf,fprintf,sprintf写fputs,puts,scanf二类无缓存 只要用户调这个函数就会将其内容写到内核中stderr三类全缓存 只有写满缓存再调用系统调用函数读fread写fwrite以及刷新缓存函数把库函数中的缓存内容强制写到内核中ffluashFIFE *fp特别说明经常发现使用printf的时候没有\n以及没写满缓存依旧打印出信息这是因为程序执行完main函数后会自动刷新所有缓存把没输出的内容一次性打印出来。包括fclose函数也可以把缓冲区内最后剩余的数据输出到磁盘文件中并释放文件指针和有关的缓冲区。#include stdio.h #include unistd.h // 用于 sleep 函数 int main() { printf(hello); // 行缓存没有\n也没满数据暂存缓存 sleep(5); // 程序暂停5秒不退出 printf(\n); // 遇到\n刷新缓存打印hello return 0; }此时程序暂停的5秒是不会输出打印信息的。行缓存的读写函数fgets和fputschar *fgets (char *s, int size,FILE *stream)第一个参数缓存即读到哪里去第二个参数读多少个字节第三个参数从什么地方读返回值若成功则为s缓存的地址若已处文件尾端或出错则为nullint fputs(const char *s,FILE *stream);第一个参数缓存即写什么内容第二个参数写到哪里去若成功则为非负值若出错则为EOF -1 。关于fprintf、printf、sprintf 行缓存的函数区别fprintf 指定文件 / 流如文件、stderr直接给用户看的控制台输出printf 标准输出stdout / 屏幕输出到文件 / 错误日志intsprintf 内存字符串字符数组把格式化内容存到内存里#include stdio.h #include string.h int main() { char buff[100] {0}; // 存放sprintf结果的缓冲区 int num 123; char str[] test; // 1. printf输出到屏幕stdout printf( printf 输出到屏幕 \n); printf(数字%d字符串%s\n, num, str); // 2. fprintf输出到文件也可输出到stderr printf(\n fprintf 输出到文件 \n); FILE *fp fopen(test.txt, w); if (fp ! NULL) { // 输出到test.txt文件 fprintf(fp, 数字%d字符串%s\n, num, str); // 输出到标准错误屏幕无缓存立刻显示 fprintf(stderr, 提示fprintf已写入文件\n); fclose(fp); } // 3. sprintf输出到内存缓冲区buff数组 printf(\n sprintf 输出到内存 \n); sprintf(buff, 数字%d字符串%s, num, str); // 打印缓冲区内容验证结果 printf(buff里的内容%s\n, buff); return 0; }