站内搜索: 请输入搜索关键词

当前页面: 开发资料首页J2SE 专题高分帖:一个2G的文本文件,如何实现所有内容的完全颠倒?

高分帖:一个2G的文本文件,如何实现所有内容的完全颠倒?

摘要: 高分帖:一个2G的文本文件,如何实现所有内容的完全颠倒?


一个2G的文本文件,要求不使用中间临时文件,如何实现所有内容的完全颠倒?(行也颠倒过来,每行字符都颠倒过来)

比如文件内容如下:

abcde
12345
你们好

实现内容完全颠倒后:

好们你
54321
edcba

不使用中间文件,就是说只能在内存中读写该文件,但是文件有2G,超过一般内存。如何实现之?请使用Java或C++解答。谢谢!


用RandomAccessFile直接seek到文件尾开始往前读。


用C吧,应该会快点
方法跟楼上说的类似


如何往前读呢?二楼能给出代码吗?

请给出关键代码


都说那么明白了,还要什么关键代码,楼主够懒



循环『
读一个
移动到文件开头
写入』


我突然想到二楼说的倒着读是什么意思了,做个循环,逐字节读取。但是这样没有考虑到内存的。2G的文件不能全部先读到内存,然后一次写入文件的。

我个人的思路是每行作为一个字符串实现颠倒(比如abcd -> dcba),这个我已经能实现了。然后实现行交换,比如1行和n行交换,2行和n-1行交换...,但是我没能搞定。求教!


shenpipi(皮皮)

我不是懒,而是二楼说的没实现要求,所以一时发蒙没明白。呵呵


先不考虑双字节字问题,假设全是单字节文字:
RandomAccessFile raf = new RandomAccessFile("C://big.txt","r");
long fLen = raf.length();
for (long n=fLen-1; n>=0; n--) {
raf.seek(n);
byte b = raf.readByte();
// write b to new file
}

上面是基本方式,然后你还要考虑双字节问题,以及效率问题(按buffer读,不一个个byte读)。
如此。明白了没?



楼主,你是真糊涂了吧?
谁让你从文件末尾倒着一次把文件读到内存中的?你不会读一个字节写一个字节吗?
当然,要想提高效率肯定要使用buffer的,这点楼上很有经验,但是,对于java来说,是没有必要考虑双字节字符问题的,嘿嘿,楼主又可以省事了。


哦,似乎得考虑一下回车的问题.


皮皮,
我的确糊涂了。边读边写(因为是同一个文件),用randomAccessFile指针要跳来跳去?
期待有更好的方法。


要写到同一个文件里面啊?真是折腾人啊。
这是某人出的考试题啊?还是客户需求啊?


不过同一个文件以上方法也能实现,指针确实要象你说的那样跳来跳去了。把buffer定义的大一点就是了。



是考题

要求不使用中间文件。文件有2G大,完全在内存里面操作也行不通。



"rw"方式打开,然后从两头开始,分别读一段到内存,颠倒内存内容后换位写入,不断循环直到在文件中间会合。
估计还是得考虑双字节问题。
反正就是seek来seek去了。
不知道同时开2个RandomAccessFile,2者同时读写一个文件会不会有lock问题。自己试试看吧。


好题,留个记号


up!!


调用操作系统API,映射到内存,再颠倒。具体实现,我不会……


开辟一个固定大小的缓冲,每次只写这么大的缓冲到头或者尾。
单个字符的写入速度太慢了。
需要考虑的情况是,换行的位置。
极端情况是:整个文件文件就是一行。 



里有这样的例子,他的调用windows的api 跟楼主的要求一样


同意楼上的,在windows下最好的最有效的办法就是使用file map


(*_*)


使用内存映射文件,把文件映射成可以操作的内存地址,再按照字符串进行操作就可以了。完全不需要缓冲区,不要临时文件。

--------------------------
国内专业的ACE网络编程、开发论坛开通:
www.acejoy.com
www.acedevelop.com
涉及ACE使用和开发,中间件、服务器端软件的设计,P2P技术,
socket网络编程、应用开发等内容。
欢迎加入,大家一起交流、学习成长!



循环『
读一个
移动到文件开头
写入』
//------------------------------------
真牛


反正我知道,打开一个2G的文本文件,我机器就死了,用程序也试过,没有成功····



关注


hehe ,楼上说的好
真么大的文本,一个好算法是很重要的


把显示器倒过来不就得了...^_^


建议用内存映射文件,否则这么大的文本文件,根本打不开!

═══════════════════
 免费的源码、工具网站,欢迎大家访问!
 http://www.j2soft.cn/
═══════════════════


把显示器倒过来是个逆天级的好办法


啊,my god,2G
还没试过能不能打开
估计倒成了,也不知道有没有成功


新建个临时文件,用RandomAccessFile直接seek到文件尾,按行写倒临时文件,倒读完后,删除此文件,把临时文件改名为此文件


新建个临时文件,用RandomAccessFile直接seek到文件尾,按行写倒临时文件,倒读完后,删除此文件,把临时文件改名为此文件
------------------------
要求不使用临时文件的
要不然谁都会了


开2个线程,第一个线程从文件头读取buf个字符,然后对buf做颠倒,这个楼主已经实现,颠倒完成后往文件尾前buf个字符的地方开始写。另一个线程从文件尾读取buf个字符,然后颠倒,颠倒完成写文件头。这个要注意的是线程同步问题,在线程1/2未完成字符读取的时候,线程2/1不能写文件。就这两个线程交替,直到转换完


(*_*)


本人 的 想法和gongzhy(2369) 的相同


写个专门读文件的底层系统
凡是读这个文件的
就倒着读
......
可能最快了吧


我觉得可以在内存当中设置两个同样大小的缓冲区,比如是16k,第一次从开头读取一页,并颠倒,然后从结尾读取一页并颠倒,然后将颠倒好的开头一页写入结尾,并从结尾往上移动一页在读取并颠倒一页,之后跳转到开头,每次都是读取一页,并写入前一页,这样文件当中跳转的次数会降低一些,性能会好些


1.4新增的NEWIO里面有操作大文件的类,比如RandomAccessFile,建议楼主看看文档应该不能解决


这个的确要用到内存映射文件来处理,在《windows核心编程》里面找到答案了。凡是提到这个的都可以得分。

比较遗憾的是我说了那么多,很多朋友没有看懂题目就开始回答问题,呵呵,希望大家都有所提高。


关注!




读到内存里面,不大可能(做虚拟内存太慢了)利用块排序处理我觉得比较可能,关键看你的cpu如何,呵呵!
这样不管是c++还是java都很好做到,要知道jvm会爆的


这个的确要用到内存映射文件来处理,在《windows核心编程》里面找到答案了。凡是提到这个的都可以得分。

比较遗憾的是我说了那么多,很多朋友没有看懂题目就开始回答问题,呵呵,希望大家都有所提高。

你是用JAVA的么,用JAVA还用WINDOWS核心编程的东西么?用那个还到JAVA问干吗啊


嗯,不错,好题


严重同意把显示器倒 过来


我晕,楼主去看看Thinking Java中的IO部分吧。
里面的 内存映射文件 就可以满足楼主的要求。


学习了


能不能在文件的一行上作文章,
读一行,推一行/
菜鸟想滴


标记一下


linux 下如何搞?


↑返回目录
前一篇: 关于getText()与equals()的问题
后一篇: 定时器问题,更改系统时间后定时器停止触发?