第一个问题,也是主要问题,c 语言的FILE结构是怎么实现的。经过网上查了一下说是通过调用系统AP

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了第一个问题,也是主要问题,c 语言的FILE结构是怎么实现的。经过网上查了一下说是通过调用系统AP相关的知识,希望对你有一定的参考价值。

第一个问题,也是主要问题,c 语言的FILE结构是怎么实现的。经过网上查了一下说是通过调用系统API 动态连接库来实现的,这又引发下一个问题,都说 windows 是 c 语言写出来的。那么 windows 系统又是如何实现文件操作的。这又引发另一个问题,那么最初的 c 语言是什么,它是如何完成文件操作的。

现在说一下我个人思路,首先人类研究出了第一套编程高级语言 c,接着人类使用 c语言,开发出了系统,最后再对 c 语言封装,弄出了更多的高级语言。如果这个思路正确的话,windows 是c 语言的超大型工程,问文件 操作也是基于 c 语言来实现的,那么 c 语言又是如何实现 文件操作的,?我们使用的都是标准库文件里的函数,就像圆周率一样,π 这个东西你如果不知道它是基于 直径的三倍规律而得到的,那么永远只能用 2πr 就知道是周长,却不知道这个周长是怎么得到的

在C之前也有系统 其它语言写的
C之后 系统一般就是C写的了。
至于文件操作,调用系统的文件系统接口执行的。
他们之间的关系错综复杂

举个例子吧,C语言的编译器是C语言写的,但是它可以编译C语言。
C语言的发展反过来也会促进这些功能模块,这些功能模块的新需求同样会反过来促进C的进步。追问

那么 c 语言的标准函数裤也是人写出来的,它是否是对什么进行封装了吗,或者是上一个封装进行下一个封装。例如,我们可以自己写一个函数来实现字符串分隔来代替标准的字符串分隔函数,但却不知道如何自己实现操作文件。例如我想搜索一个文件,我只能间接的调用函数得到文件列表,然后自己再进行匹配。

如果不掉用函数,我就无法得到文件的句柄来操作文件

对了还问你一个问题,学习单片机开发,是否有助于了解到 windows 的部分 API 的实现原理

追答

第一个,C语言的标准函数,有些是到库函数就到底了,比如字符串处理这类的,和其他的没什么关系

有些是和外部有关的,比如操作系统,文件系统等等。像你说的文件操作,还有常用的打印函数什么的,这些都是上下封装的。对于这部分,其实是可以绕过库函数的,直接调用操作系统接口。不过不推荐,因为那样对于移植会带来麻烦,不同系统,接口是不一样的。
比如说,如果是单片机,那么可能你用printf可以打印,用uart_write也可以实现同样的功能。

至于单片机,可以了解一些吧,不过不会太多。毕竟单片机太小了,和windows差距太大。而且不同操作系统的操作方式也有区别,只是理念近似而已,差别还是不小的。
所以,对这方面还是不要抱太大希望的好。

追问

而且匹配首先就是要得到一个文件夹里有多少个文件,然后文件的名字是什么,才能进行匹配,匹配不到,再换目录,直到搜索完 e :\\\\bat 里的所有目录个文件。

所以我又不知道文件夹有多少个,一个文件夹里文件有多少个,所以我使用了列表框来得到这些名字,再通过读取列表框,但是一个目录下也许还有另一个目录。

这是我的界面,右上角就是搜索功能。

难道必须要自己写一个文件系统管理吗,把用户创建文件夹个数和文件个数进行进行管理吗,然后每次都根据管理的路径来搜索?

通过获取路径来进行搜索条件不够。所以我才想到最上面那些复杂问题的。

增删改查功能都实现了,就差个搜索文件,其实最主要的也是这个功能。便于以后搜索一些自己做的一些笔记。

左上角就是创建文件夹。

在列表框里单击目录就会跳转到子目录,单击文件就能在编辑框显示。单击上一级就是后退,下一级就是前进。唯独差个搜索。

追答

搜索文件,在windows下面没做过,之前在linux下面做过类似的。
先是一个打开dir的函数,获取一个dir句柄,然后循环获取该文件夹下面的所有节点,如果是文件,进行对比,如果是目录,递归调用查找函数。
当时做的是找到的时候打印出来,加到列表里也差不多吧。
搜索的时候需要注意,把两个特殊节点,点和点点,就是"."和".."这两个排除掉,不然就死循环了。
这个不是太难。
windows上应该有类似的函数的。

追问

哎兄弟,麻烦你给我支个招,我昨天找了好久,都是一些打开文件的函数,操作文件夹的标准函数也就是建立,删除,定位,获取,不知道要如何进行搜索匹配

没有找到跟你说的类似的函数

这是我制定的一个方案

上面使用递归来每次搜索一个目录

问题就在下面那个更换目录的函数

首先搜索根目录下是否有文件,没有,就要进入第一个子目录,如果第一个子目录没有找到,就要判断该目录是否还有子目录,如果有就还要进入,没有就要返回一个目录。这么搞起来是挺复杂的

最后还要重新回到根目录下的第二个文件夹进行搜索,搜索不到还判断该目录是否有子目录,有就又要进入。

追答

不要用C库函数,你找下windows相关的接口。
C库函数没有windows的函数好用。
另外,尽量不要更换工作目录,而是通过递归的方式,每次增加相对目录。
比如 你要找的是test 下面有个fol文件夹
那检查fol的时候,就打开test\\\\fol

追问

谢谢你了,我昨晚网上找到了FindFirstFile函数

参考技术A FILE 是 C 语言中的一个结构体,定义为:
typedef struct
char *fpos; /* 文件指针当前位置的绝对地址 */
void *base; /* 指针,指向文件的 基 */
unsigned short handle; /* 文件句柄 */
short flags; /* 标志 */
short unget; /* 1字节缓冲器,用于ungetc (第15位为1表示非空) */
unsigned long alloc; /* 现给文件分配的字节数 */
unsigned short buffincrement; /* 每次增加分配的字节数增量 */
FILE;
它被定义在头文件 stdio.h 里。
这同我们自己写程序时定义一个结构的语法一样,例如:
typedef struct float x; float y; float z; point_3d; //3维空间点。
没有你说的 那样复杂。
C 语言是较新开发的计算机语言。比它老的高级语言不少。例如 五十年代到六十年代初就有 ALGOL 58,ALGOL 60,GOGOL, VALGOL, FORTRAN 语言。就算 BASIC等语言,也比 c 开发得早。c的作者在学习那些语言基础上,再搞出来的。
计算机是靠指令和数据工作的。人给指令,给数据叫计算工作。为了提高效率,人们 发明了 高级语言,通过相应语言编译器,把用高级语言写的东西变指令而已。
高级语言的高,不是现代人说的高大上的高,而是近人的这端叫高,近计算机端的叫低。例如汇编语言属低。追问

那我再问你问题吧,假设现在要打开一个文件,我们使用 fopen ,现在我们知道 FILE 是一个结构体,如何写一个结构体来实现文件操作?都说最终是调用系统的 API,又都说 windows 是用 c 语言写的,那么写一个 API 首先就是调用 fopen吗? 那么 fopen 又是怎么实现的?

追答

"又都说 windows 是用 c 语言写的" -- 大错。
c 语言是开发 unix 系统的产物,与视窗风马牛毫不相干。
windows 是DOS系统基础上的产物,用8080指令及后来的8086,windows NT 时有个跃变,然后稳定下来,直到win-7用64位指令。
某些东西用 VB 写的。
API 是 applications, 是应用程序,不是操作系统,是 MS VC++ c/c++ 程序。
你对文件读写有性趣,自己反汇编一下,去读一下指令即可。MS VC++ 里带了 反汇编,一句命令就有结果了。这里不能给你开课,因为内行看门道,一看就知道深浅。

参考技术B 最初的C语言是B语言发现来的,追问

b语言?

追答

对啊,B语言不断完善才有了C语言

c语言结构体的问题,存储空间大小?

win32
4字节对齐
变量内存的起始地址的边界是跟它类型一致的
比如int类型,可以认为它存在4的倍数的地址,short存在2字节倍数开始的地址,char存在1字节开始的地址,即任意地址
因此,回过头来看
第一个结构
假设int
a;///4字节倍数地
short
b;//推理a的末尾是4字节倍数地址也是2字节倍数地址,所以b是挨着a存的
char
c;//任意其实地址,挨着b存放
看起来7个字节就放下了,但是需要兼顾4字节对齐的原则,在末尾补了一个字节
第二个结构也类似
结构体与普通类型并无大区别,存储区域也一样的
参考技术A 一样的啊
结构体的存储空间就是里面每个元素存储空间的总和
这2个结构体都是1个int,1个short和1个char,这2个结构体的存储空间都=(int的存储空间+short的存储空间+char的存储空间),所以是一样的
参考技术B 编译器为优化一般会将结构体4字节对齐,题中的结构体大小相同。
若int在中间,那么会更高。
关于结构体存储:
定义存在只读数据区
变量根据需要分别存在于数据区、堆栈区等。
地址,一般按4字节对齐
参考技术C 结构体长度求法:
a.成员都相同时(或含数组且数组数据类型同结构体其他成员数据类型):
结构体长度=成员数据类型长度×成员个数(各成员长度之和);
结构体中数组长度=数组数据类型长度×数组元素个数;
b
成员不同且不含其它结构体时;
(1).分析各个成员长度;
(2).找出最大长度的成员长度M(结构体的长度一定是该成员的整数倍);
(3).并按最大成员长度出现的位置将结构体分为若干部分;
(4).各个部分长度一次相加,求出大于该和的最小M的整数倍即为该部分长度
(5).将各个部分长度相加之和即为结构体长度
c含有其他结构体时:
(1).分析各个成员长度;
(2).对是结构体的成员,其长度按b来分析,且不会随着位置的变化而变化;
(3).分析各个成员的长度(成员为结构体的分析其成员长度),求出最大值;
(4).若长度最大成员在为结构体的成员中,则按结构体成员为分界点分界;
其他成员中有最大长度的成员,则该成员为分界点;
求出各段长度,求出大于该和的最小M的整数倍即为该部分长度
(5).将各个部分长度相加之和即为结构体长度

以上是关于第一个问题,也是主要问题,c 语言的FILE结构是怎么实现的。经过网上查了一下说是通过调用系统AP的主要内容,如果未能解决你的问题,请参考以下文章

c语言第二次作业

C语言,结构体

C语言中如何在多个文件中引用同一个结构体

Go语言文件操作

Go语言文件操作

C语言文件操作,请高手指点