Linux中文件的理解

news2024/12/23 10:03:59

✨前言✨

📘 博客主页:to Keep博客主页
🙆欢迎关注,👍点赞,📝留言评论
⏳首发时间:2024年10月16日
📨 博主码云地址:渣渣C
📕参考书籍:C语言程序与设计 和 数据结构(C语言版)
📢编程练习:牛客网+力扣网

Linux中文件的理解

  • 一 系统调用接口
    • 1 open函数(打开操作)
      • 1.1 flag标志位
      • 1.2 文件权限
    • 2 write函数(写入操作)
    • 3 read函数(读取文件)
    • 4 close函数(关闭文件)
    • 5 文件描述符
    • 6 dup2函数(重定向)
  • 二 缓冲区
  • 三 文件系统
  • 四 软硬链接

         ~~~~~~~~          对于文件我们都知道,文件=文件内容+文件属性!我们都知道要对文件进行操作,我们第一步就是要打开文件,根据我们之前提及的冯诺依曼体系结构,该文件就必须加载到内存当中,也就是说是对应的进程打开文件的,而文件我们一般可以分为两种,一种就是被加载到内存中的,一种是位于磁盘上的!我们先来学习内存文件,在C语言中,也提供了一系列的库函数来对文件进行操作!

读写操作
在这里插入图片描述
打开操作
在这里插入图片描述
关闭操作
在这里插入图片描述
我们主要介绍以下三种打开文件的模式:
在这里插入图片描述
以w方式打开文件时候,在对文件进行写入操作的时候,是会覆盖掉原文件有的内容的,相当于我们之前说过的重定向!而使用a方式打开文件,在对文件写入操作就可以在原文件有内容的基础上增加内容的,也就是我们所说的追加重定向!

一 系统调用接口

实际上,C语言层面上的一系列对文件的操作函数底层其实都是封装了系统调用函数,来针对文件进行操作!

1 open函数(打开操作)

在这里插入图片描述
pathname:指的就是文件所在的路径(通常就是以绝对路径给出,如果设置了对应的环境变量,也可以相对路径),默认就是我们当前进程创建时的路径!
flag:是一个标志位,可以用来标识我们打开文件的模式,下面会详细介绍!
mode:创建文件时,给文件设置的权限
返回值:文件描述符

1.1 flag标志位

实际上,标志位就是一个位图,用32位来标识不同的模式,如下图所示:
在这里插入图片描述
原理如下图所示,通过与操作,确定哪一个模式,然后执行对应的功能!
在这里插入图片描述

1.2 文件权限

在使用open函数的时候,如果对权限不做处理就创建文件,那么文件的权限就会乱掉,我们就来复习一下Linux中的权限,在Linux中的权限中,我们就知道,目录的默认权限是777,文件的默认权限是666!而我们Linux系统中默认的权限掩码是002,所以就可以得到下表的内容:
在这里插入图片描述
计算规则为:最终权限=默认权限 & (~umask)
在使用open函数,如果我们对文件掩码不进行设置,那么文件的权限可能就会乱掉!所以我们一般采用第二个open函数,设置自己想要的文件权限!如下图所示:
在这里插入图片描述
我们一般结合umask函数与自己设置的权限结合得到该文件的权限!如果不使用umask,默认就会使用Linux系统中默认的掩码!

2 write函数(写入操作)

在这里插入图片描述
fd:文件描述符
buf:要写入文件的内容
count:要写入内容的长度

3 read函数(读取文件)

在这里插入图片描述
fd:文件描述符
buf:将文件中读取的内容存放在buf中
count:选择读取的长度

4 close函数(关闭文件)

在这里插入图片描述
fd:文件描述符

5 文件描述符

从上述系统调用接口中的参数,我们就可以发现其实文件描述符就是一个整数!其实在C语言中,FILE是一个结构体,里面其实也必须包含文件描述符!如下图所示:
在这里插入图片描述
那么文件描述符既然是一个数字,哪我们怎么知道哪个数字是对应哪个文件的呢?事实上,文件加载到内存中,就会被管理起来,和我们的进程一样,用链表形式管理起来,我们会用一个文件描述符表(相当于一个数组)记录下文件所在的位置,而我们的进程就会指向这个文件描述符表!如下图所示:
在这里插入图片描述

而每一个文件被加载到内存中,C语言会默认的打开三个文件,那就是标准输入,标准输出,标准错误!对应的文件描述符默认值分别就是0,1,2!

6 dup2函数(重定向)

简单了解了文件描述符的原理,并且知道了在C语言中,会默认打开三个文件,这样我们就可以知道输出重定向(追加重定向)的原理了,就是利用上层C语言在标准输入,标准输出,标准错误三个文件结构体中,给文件描述符默认值就是0,1,2。那么我们利用系统调用函数(底层可以直接改变文件描述符的函数)就可以关闭标准输出这个文件,然后最新打开的文件(加载到内存中的文件)就会被文件描述符表中的1所指向了(因为文件描述符表的原则就是将最小的并且没有被使用的数组下标,会分配给最新打开的文件)!但是在C语言上层并没有改变,他的标准输出文件描述符还是在1,所以向显示器输出,转而向文件输出了!从而实现了输出重定向(输入重定向的原理也类似,就是关闭文件描述符0)!
dup2函数的原理就不用关闭这么麻烦,上述只是为了让我们更好的理解什么是重定向!dup2函数可以将一个已存在的文件描述符复制到另一个文件描述符上,并且可以自定义新文件描述符的编号。具体的可以参考dup2函数的原理,如下图所示(本来是向显示器写入的,结果向文件写入了):
在这里插入图片描述

二 缓冲区

从上面我们就了解到了加载到内存中的文件我们是如何操作的!并且内存中文件的本质其实就是数组下标!对我们操作过的文件是如何刷新到磁盘上的呢?这就不得不提到C语言中的缓冲区了!它本质也就是一块内存区域!为什么会要有缓冲区呢?我们都知道,调用系统调用是有系统开销的!如果我们频繁的去使用系统调用,就会导致我们的对于文件的操作效率就会下降!这是我们不希望的!这里我就简单说下缓冲区大概一个原理(如下图所示):
在这里插入图片描述
我们对文件操作,使用fwrite函数等,并没有立即调用系统调用函数刷新到操作系统中的缓冲区!而是要满足一定的条件!具体可以概括为以下三种情况:

1️⃣无刷新,无缓冲!直接调用底层的系统调用
2️⃣行刷新,遇到\n就刷新数据
3️⃣全缓冲,全刷新。等缓冲区满了就刷新!

当然我们也可以手动调用系统调用函数采用强制刷新,或者进程退出后会进行自动的刷新数据!一般遇到第二种或者第三种情况比较多,这就是缓冲区的一个大致原理!

三 文件系统

在了解完内存中文件的操作,以及是通过缓冲区刷新到磁盘上的!我们在来了解一下对于磁盘上的文件我们是如何管理的!实际上,磁盘上的文件就是利用文件系统来进行管理的!简单来说,就是我们操作系统会对磁盘进行分区,分区之后在进行分组,然后在对分组进行管理,从而实现对文件系统的管理!文件系统的原理图如下所示:
在这里插入图片描述

在介绍分组中的参数前,我们还需要了解一样东西,就是文件的inode编号,我们操作系统对于文件的增删查改都是基于这个inode编号来实现了,它在当前分区下是唯一的但是在分组里面并不是唯一的(这是因为进入分组之后,我们都要用文件的inode编号减去分组中的第一个inode编号,也就是意味着,在每一个分组中,inode bitmap中的都是从1开始计数的)!inode结构的伪代码如下所示(所占空间大小固定为128字节,该内容是保存在inode Table中的):

struct inode
{
  权限
  类型
  大小
  ......
  inode编号
  int blcok[15]
}

在Xshell中我们也可以查看到文件的inode
在这里插入图片描述

1️⃣BootBlock:启动块,一般是在第一个分区的第一个扇区上,也就是我们C盘独有的一个数据块!
2️⃣inode Bitmap:用来标记有那些inode还没有被占用
3️⃣Block Bitmap:用来标记那些数据块是空闲的,可以放数据。
4️⃣Data Block:存放数据(也就是文件内容)。
5️⃣inode Table:存放inode有关信息(也就是文件属性)。
6️⃣Group Descriptor Table:用来标识当前组inode与数据块的空闲等的使用情况。
7️⃣Super Block:用来标识该分区的inode与数据块的空闲等的整体使用情况,并不是每一个分组都有,而是某些组里面有!

倘若我们要创建一个文件然后写入数据,我们首先就是根据操作系统给文件分配inode编号,找到它所分配到的组,然后inode bitmap找到一个空位然后改为1(表示被占用),然后根据的文件属性,初始化inode结构体,然后保存到inode table对应的位置!然后根据block bitmap找到空闲的数据块改为1,然后将文件内容写入到Data block中!如果要删除文件,那就简单了,根据inode编号将对应的文件的inode bitmap与block bitmap对应的位置置为0,表示数据可以被覆盖就表示删除了!
总的来说,对文件系统就是将Super Block加载到内存中,从而实现对磁盘上的文件管理!所以,每一个分区是可以使用不同的文件系统进行管理的!只是在Linux是采用了Super Block这种方式进行管理!

四 软硬链接

软链接命令:

ln -s 被链接文件 链接之后取的文件名字

在这里插入图片描述

硬链接命令:
ln 被链接文件 链接之后取的文件名字

在这里插入图片描述

我们在来看看,通过软硬链接之后,查看一下文件的inode编号
在这里插入图片描述

可以发现,软连接是新创建了一个文件,那是因为与原来的文件的inode编号不一样,而硬链接inode编号是与原先的文件一致!并且硬链接数变成了2,软链接的硬链接数还是1。这是因为软链接里面放的内容是目标文件的路径,硬链接就是在其目录文件上(因为目录也是文件,目录的文件内容就是保存里面文件的文件名与文件的inode的映射关系),增加了文件名与新文件名的映射关系,然后让inode的引用计数++!在这里需要说一下的一个小常识就是,我们看一个目录里面有多少个子目录可以用硬链接数-2。
原理就是在我们默认创建的目录中,硬链接数就是2,一个就是目录文件名本身,另一个就是目录文件中包含的隐藏文件目录.

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2216682.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

如何使用Nessus软件

Nessus(Win2022虚拟机已安装) [ root root ] 访问https://127.0.0.1:8834 如果出现以下问题 解决方法: 1.在地址栏输入:about:config 2.在搜索框 输入:security.enterprise_roots.enabled 将值切换为true即可。…

Java算法竞赛之getOrDefault()--哈希表最常用API!

解释: for (char ch : magazine.toCharArray()) { charCount.put(ch, charCount.getOrDefault(ch, 0) 1); } 在Java中,HashMap 是一个用于存储键值对的数据结构,其中每个键都是唯一的。put 方法用于将指定的键与值放入 Has…

AI控制工业机器人入门教程

简介 AI控制的工业机器人正在改变现代制造业的面貌。与传统的编程控制不同,AI使机器人能够通过感知环境、自主决策和学习不断优化自身的操作。这篇教程将介绍实现AI控制工业机器人的必要知识和技能,帮助读者从基础开始构建起AI控制机器人的理解和能力。…

TypeScript新手学习教程--接口

TypeScript 也支持接口,跟Java类似,这对于学习过java,c#,php语言的人更容易上手,虽然类似,但是也有不同,下面开始学习。 1、 接口声明 TypeScript的核心原则之一是对值所具有的结构进行类型检…

anaconda(jupyter)安装教程

目录 一、下载anaconda安装包 二、安装程序 三、怎么使用 四、把jupyter界面语言修改成中文 一、下载anaconda安装包 anaconda官网:下载 Anaconda Distribution |蟒蛇 清华大学开源软件镜像站官网:清华大学开源软件镜像站 | Tsinghua Open Source M…

Linux服务部署,遇到的各种问题之一(测试篇)

最近服务器需要搬迁,所有的服务都需要迁移,从初始化数据盘,到服务部署的各种细节,下面我们一一来说 初始化数据盘就不用说了,大概率,作为测试接触不到。 今天来说是ubuntu显示的中文文件乱码问题如何解决…

SpringBoot集成Mongodb实现增删改查操作

目录 一、Mongodb概念 二、SpingBoot集成Mongodb 三、实现增删改查操作 一、Mongodb概念 MongoDB是一个开源的文档型数据库,属于NoSQL数据库中的一种。它使用BSON(类似于JSON)格式存储数据,具有高性能、高可用性和易于扩展的特…

QT--文本框 QLineEdit、qtextedit

在Qt中,文本框(QLineEdit 或 QTextEdit)和标签(QLabel)是两种不同的部件(widget),它们的主要区别在于用途和功能: QLabel(标签) 用途&#xff1…

JVM(HotSpot):直接内存及其使用建议

文章目录 一、什么是直接内存?二、特点三、使用案例四、直接内存的管理 一、什么是直接内存? Direct Memory:系统内存 普通IO,运行原理图 磁盘到系统内存,系统内存到jvm内存。 NIO,运行原理图 划分了一块…

『Mysql集群』Mysql高可用集群之主从复制 (一)

Mysql主从复制模式 主从复制有一主一从、主主复制、一主多从、多主一从等多种模式. 我们可以根据它们的优缺点选择适合自身企业情况的主从复制模式进行搭建 . 一主一从 主主复制 (互为主从模式): 实现Mysql多活部署 一主多从: 提高整个集群的读能力 多主一从: 提高整个集群的…

等级保护测评师练习卷31

等级保护初级测评师试题31 姓名: 成绩: 一、判断题(10110分) 1.等级测评采用基本方法是访谈、测试、验证()访谈、核查、测试 2.等级保护对象是由…

HarmonyOS 应用级状态管理(LocalStorage、AppStorage、PersistentStorage)

HarmonyOS 应用级状态管理 1. LocalStorage:页面级UI状态存储 1.1 概念 LocalStorage是页面级的UI状态存储,通过Entry装饰器接收的参数可以在页面内共享同一个LocalStorage实例。LocalStorage也可以在UIAbility内,页面间共享状态。 应用程…

【Linux】Linux下的Makefile基本操作

1.Makefile与 make介绍 在Linux中, Makefile 是⼀个⽂件, 令会在当前⽬录下找 make 是⼀个指令,当使⽤ Makefile ⽂件从⽽执⾏内部的内容 2.创建第一个 Makefile并使用make ⾸先,在当前⽬录下创建⼀个makefile文件 接下来在同级…

动态规划一>珠宝的最高价值

1.题目: 2.解析: 代码: /**1.创建dp表2.初始化3.填表4.返回*/public int jewelleryValue(int[][] frame) {int m frame.length, n frame[0].length;int[][] dp new int[m1][n1];//虚拟节点的值直接为0满足条件,已经初始化好…

字典树 计数问题(含 2022 icpc杭州 K)

//最近学了字典树,补一下 1.概念和实现 首先,字典树是一棵树(废话),边表示字母,从根到叶子节点所有边的顺序组合表示字目排列顺序。 看一下图明白很多: 例如:abc这个字母排序&am…

MybatisWebApp

如何构建一个有关Mybatis的Web&#xff1f; 在这里给出我自己的一些配置。我的TomCat版本&#xff1a;10.1.28 &#xff0c;IDEA版本&#xff1a;2024.1.4 Pom.XML文件 <project xmlns"http://maven.apache.org/POM/4.0.0"xmlns:xsi"http://www.w3.org/200…

Linux platform子系统和设备树

1 Linux platform子系统 在Linux 2.6内核中&#xff0c;提出了总线、设备、驱动的架构&#xff0c;目的是让我们写出来的驱动通用性更强。 arm核内部总线结构&#xff1a; 1.1 核心思想 将设备的信息从驱动中分离出来&#xff0c;我们需要在操作系统中&#xff0c;添加设备…

【H2O2|全栈】JS入门知识(二)

目录 JS 前言 准备工作 运算符 算数运算符 比较运算符 自增、自减运算符 逻辑运算符 运算符的优先级 分支语句 if-else语句 switch语句 三元表达式 结束语 JS 前言 本系列博客主要分享JavaScript的基础语法知识&#xff0c;本期为第二期&#xff0c;包含一些简…

平时使用Xshell能连接虚拟机,现在突然连接不上

问题&#xff1a;平时使用Xshell能连接虚拟机&#xff0c;现在突然连接不上&#xff0c;使用ip addr 命令查看ip地址 ens33 接口状态为 DOWN&#xff0c;没有分配IP地址&#xff0c;这通常意味着该网络接口未激活或存在配置问题。&#xff08;因为平时能连接&#xff0c;就说明…

mysql 09 独立表空间结构

表空间中的页实在是太多了&#xff0c;为了更好的管理这些页面&#xff0c;设计 InnoDB 的大叔们提出了 区 &#xff08;英文名&#xff1a; extent &#xff09;的概念。对于16KB的页来说&#xff0c;连续的64个页就是一个 区 &#xff0c;也就是说一个区默认占用1MB空间大小。…