一个很大(几个G)的文件,怎么样删除中间的某些段(几百M大小)?

时间:2022-03-04 15:47:55
不想重构建一个新文件,Windows和Linux平台下用c++分别怎么实现?谢谢诶!

18 个解决方案

#1


我只给思路。。。
可以通过操纵文件系统来实现。。。需要物理写盘。。。而且实现麻烦。。

#2


在链表型文件系统中,截断中间部分链表。。。
实现方法如此。。

#3


不知道...帮你顶!!!

#4


帮你顶。。。

#5



学习

#6


缓存,定位,截取,连接

#7


up

#8


linux的文件系统我不了解
说一下fat文件的思路
对于windows的fat32的一个文件
fat文件系统中,是几个扇区为一个簇
fat存在一个fat表,对fat32,每一个32位的地址对应该逻辑分区的一个簇,如果为空,表示未占用
如果非空,则表示改簇已经被占用,而且,这个值指向文件使用的下一个簇,如果为0xffffffff,表示该区域已经被占用,而且为文件的最后一个簇
而一个文件的存储,则存储了文件名,起始簇,文件大小,以及其他文件相关信息,
这里你应该懂得怎么做了吧
读取分区表,然后读取fat表
再读取文件目录,记得读取的时候,删除的时候,要清空这段空间,否则到时候成了文件碎片,用不了啦,还有记得要改文件大小。。。。

#9


9.1.6  改变EXT2文件系统中文件的大小
文件系统普遍存在的一个问题是碎块化。一个文件所包含的数据块遍布整个文件系统,这使得对文件数据块的顺序访问越来越慢。EXT2文件系统试图通过分配一个和当前文件数据块在物理位置上邻接或者至少位于同一个数据块组中的新块来解决这个问题。只有在这种分配策略失败时才在其它数据块组中分配空间。 
当进程准备写某文件时, Linux文件系统首先检查数据是否已经超出了文件最后一个被分配的块空间。如果是则必须为此文件分配一个新数据块。进程将一直等待到此分配完成;然后将其余数据写入此文件。EXT2块分配例程所作的第一件事是对此文件系统的EXT2超块加锁。这是因为块分配和回收将导致超块中某些域的改变,Linux文件系统不能在同一时刻为多个进程进行此类服务。如果另外一个进程需要分配更多的数据块时它必须等到此进程完成分配操作为止。 在超块上等待的进程将被挂起直到超块的控制权被其当前使用者释放。对超块的访问遵循先来先服务原则,一旦进程取得了超块的控制则它必须保持到操作结束为止。如果系统中空闲块不多则此分配的将失败,进程会释放对文件系统超块的控制。 

如果EXT2文件系统被设成预先分配数据块则我们可以从中取得一个。预先分配块实际上并不存在,它们仅仅包含在已分配块的位图中。我们试图为之分配新数据块文件所对应的VFS inode包含两个EXT2特殊域:prealloc_block和prealloc_count,它们分别代表第一个预先分配数据块的块号以及各自的数目。如果没有使用预先分配块或块预先分配数据块策略,则EXT2文件系统必须分配一个新块。它首先检查此文件最后一个块后的数据块是否空闲。从逻辑上来说这是让其顺序访问更快的最有效块分配策略。如果此块已被使用则它会在理想块周围64个块中选择一个。这个块虽然不是最理想但和此文件的其它数据块都位于同一个数据块组中。 

如果此块还是不空闲则进程将在所有其它数据块组中搜寻,直到找到一空闲块。块分配代码将在某个数据块组中寻找一个由8个空闲数据块组成的簇。如果找不到那么它将取更小的尺寸。如果使用了块预先分配则它将更新相应的prealloc_block和prealloc_count。 

找到空闲块后块分配代码将更新数据块组中的位图并在buffer cache中为它分配一个数据缓存。这个数据缓存由文件系统支撑设备的标志符以及已分配块的块号来标志。缓存中的数据被置0且缓存被标记成dirty以显示其内容还没有写入物理磁盘。最后超块也被标记为dirty以表示它已被更新并解锁了。如果有进程在等待这个超块则队列中的第一个进程将得到运行并取得对超块的独占控制。如果数据块被填满则进程的数据被写入新数据块中,以上的整个过程将重复且另一个数据块被分配。 

??

#10


不懂,帮你顶

#11


上面那段要是能用代码实现,也就基本能解决我的问题了,可是......

#12


这么大的记录型文件,最好用数据库来管理了。你的大设计出问题了!

#13


只问:你如何标识要删除的那一段?

#14


是视频文件了,加数据库根本不现实,那只会给程序加个更大的包袱!

>>只问:你如何标识要删除的那一段?
比如,删除第200,030,016~500,000,020之间的节间呀。

#15


除非直接对硬盘编程,否则你只能把文件考虑成一个大的数组而已~~~

你能把数组中间删掉一段吗?能的,代价很大而已。那么文件也能,只是代价更大~~~

#16


学习中!!

#17


我看了一下,Linux kernel中对fs的实现,在每个文件系统中,操作只是实现了open,close,read,write,seek和truncate 共6个系统调用,中间删除这么基本的操作,居然都没有实现,晕!!!!!
我看了一下,像UltraEdit之类的文本编辑程序,编辑一个200M的文件,即时中间只是删除一下字符,也要全部200M重写一遍,好几分钟呀,晕!!

我想,是不是能自己实现一个中间删除数据块的系统调用,可否现实??

#18


中间删除这么基本的操作?

说过了,中间删除要直接对硬盘编程。系统调用不难实现,但你想象一下该如何使用?直接修改FAT表示基本的操作吗?

#1


我只给思路。。。
可以通过操纵文件系统来实现。。。需要物理写盘。。。而且实现麻烦。。

#2


在链表型文件系统中,截断中间部分链表。。。
实现方法如此。。

#3


不知道...帮你顶!!!

#4


帮你顶。。。

#5



学习

#6


缓存,定位,截取,连接

#7


up

#8


linux的文件系统我不了解
说一下fat文件的思路
对于windows的fat32的一个文件
fat文件系统中,是几个扇区为一个簇
fat存在一个fat表,对fat32,每一个32位的地址对应该逻辑分区的一个簇,如果为空,表示未占用
如果非空,则表示改簇已经被占用,而且,这个值指向文件使用的下一个簇,如果为0xffffffff,表示该区域已经被占用,而且为文件的最后一个簇
而一个文件的存储,则存储了文件名,起始簇,文件大小,以及其他文件相关信息,
这里你应该懂得怎么做了吧
读取分区表,然后读取fat表
再读取文件目录,记得读取的时候,删除的时候,要清空这段空间,否则到时候成了文件碎片,用不了啦,还有记得要改文件大小。。。。

#9


9.1.6  改变EXT2文件系统中文件的大小
文件系统普遍存在的一个问题是碎块化。一个文件所包含的数据块遍布整个文件系统,这使得对文件数据块的顺序访问越来越慢。EXT2文件系统试图通过分配一个和当前文件数据块在物理位置上邻接或者至少位于同一个数据块组中的新块来解决这个问题。只有在这种分配策略失败时才在其它数据块组中分配空间。 
当进程准备写某文件时, Linux文件系统首先检查数据是否已经超出了文件最后一个被分配的块空间。如果是则必须为此文件分配一个新数据块。进程将一直等待到此分配完成;然后将其余数据写入此文件。EXT2块分配例程所作的第一件事是对此文件系统的EXT2超块加锁。这是因为块分配和回收将导致超块中某些域的改变,Linux文件系统不能在同一时刻为多个进程进行此类服务。如果另外一个进程需要分配更多的数据块时它必须等到此进程完成分配操作为止。 在超块上等待的进程将被挂起直到超块的控制权被其当前使用者释放。对超块的访问遵循先来先服务原则,一旦进程取得了超块的控制则它必须保持到操作结束为止。如果系统中空闲块不多则此分配的将失败,进程会释放对文件系统超块的控制。 

如果EXT2文件系统被设成预先分配数据块则我们可以从中取得一个。预先分配块实际上并不存在,它们仅仅包含在已分配块的位图中。我们试图为之分配新数据块文件所对应的VFS inode包含两个EXT2特殊域:prealloc_block和prealloc_count,它们分别代表第一个预先分配数据块的块号以及各自的数目。如果没有使用预先分配块或块预先分配数据块策略,则EXT2文件系统必须分配一个新块。它首先检查此文件最后一个块后的数据块是否空闲。从逻辑上来说这是让其顺序访问更快的最有效块分配策略。如果此块已被使用则它会在理想块周围64个块中选择一个。这个块虽然不是最理想但和此文件的其它数据块都位于同一个数据块组中。 

如果此块还是不空闲则进程将在所有其它数据块组中搜寻,直到找到一空闲块。块分配代码将在某个数据块组中寻找一个由8个空闲数据块组成的簇。如果找不到那么它将取更小的尺寸。如果使用了块预先分配则它将更新相应的prealloc_block和prealloc_count。 

找到空闲块后块分配代码将更新数据块组中的位图并在buffer cache中为它分配一个数据缓存。这个数据缓存由文件系统支撑设备的标志符以及已分配块的块号来标志。缓存中的数据被置0且缓存被标记成dirty以显示其内容还没有写入物理磁盘。最后超块也被标记为dirty以表示它已被更新并解锁了。如果有进程在等待这个超块则队列中的第一个进程将得到运行并取得对超块的独占控制。如果数据块被填满则进程的数据被写入新数据块中,以上的整个过程将重复且另一个数据块被分配。 

??

#10


不懂,帮你顶

#11


上面那段要是能用代码实现,也就基本能解决我的问题了,可是......

#12


这么大的记录型文件,最好用数据库来管理了。你的大设计出问题了!

#13


只问:你如何标识要删除的那一段?

#14


是视频文件了,加数据库根本不现实,那只会给程序加个更大的包袱!

>>只问:你如何标识要删除的那一段?
比如,删除第200,030,016~500,000,020之间的节间呀。

#15


除非直接对硬盘编程,否则你只能把文件考虑成一个大的数组而已~~~

你能把数组中间删掉一段吗?能的,代价很大而已。那么文件也能,只是代价更大~~~

#16


学习中!!

#17


我看了一下,Linux kernel中对fs的实现,在每个文件系统中,操作只是实现了open,close,read,write,seek和truncate 共6个系统调用,中间删除这么基本的操作,居然都没有实现,晕!!!!!
我看了一下,像UltraEdit之类的文本编辑程序,编辑一个200M的文件,即时中间只是删除一下字符,也要全部200M重写一遍,好几分钟呀,晕!!

我想,是不是能自己实现一个中间删除数据块的系统调用,可否现实??

#18


中间删除这么基本的操作?

说过了,中间删除要直接对硬盘编程。系统调用不难实现,但你想象一下该如何使用?直接修改FAT表示基本的操作吗?