Java 向加载到内存中的文件追加字符的最快/最有效的方法是什么?
我试图做的是,将整个.txt文件读入一个字符串,并在字符串中添加一个换行符。然后通过传递data_buffer.toString()创建一个新的扫描器来处理这个字符串。显然,对于非常大的文件,这个过程会占用很多时间,我只想在已读入内存的.txt文件中添加一个换行符 我知道整个想法似乎有点老套或怪异,但有没有更快的方法Java 向加载到内存中的文件追加字符的最快/最有效的方法是什么?,java,file-io,java.util.scanner,Java,File Io,Java.util.scanner,我试图做的是,将整个.txt文件读入一个字符串,并在字符串中添加一个换行符。然后通过传递data_buffer.toString()创建一个新的扫描器来处理这个字符串。显然,对于非常大的文件,这个过程会占用很多时间,我只想在已读入内存的.txt文件中添加一个换行符 我知道整个想法似乎有点老套或怪异,但有没有更快的方法 干杯:)做某事最快的方法往往是根本不做 为什么不修改解析代码,使末尾的换行符不再是必需的?如果您每次都要添加它,那么您也可以更改代码的行为,使其看起来好像它在那里,而实际上它并不在
干杯:)做某事最快的方法往往是根本不做 为什么不修改解析代码,使末尾的换行符不再是必需的?如果您每次都要添加它,那么您也可以更改代码的行为,使其看起来好像它在那里,而实际上它并不在那里 接下来,我将尝试避免逐字符创建一个巨大的字符串,因为这确实是相当昂贵的。您可以基于
输入流
创建扫描仪
,它可能比将数据读入字符串
并对其进行解析快得多。您可以重写FileInputStream
,在文件末尾返回一个虚拟换行符,从而避免粘贴字符串的出现
如果您确实必须将数据读入缓冲区,那么最好使用流中基于数组的
read()
方法读入字节数组,这比逐字节读入快得多。因为您可以预先知道文件的大小,所以可以为额外的行尾标记分配缓冲区空间,并将其插入数组中。与创建StringBuffer
并从中生成String
不同,这不需要缓冲区的完整副本。做某事的最快方法通常是根本不做
为什么不修改解析代码,使末尾的换行符不再是必需的?如果您每次都要添加它,那么您也可以更改代码的行为,使其看起来好像它在那里,而实际上它并不在那里
接下来,我将尝试避免逐字符创建一个巨大的字符串,因为这确实是相当昂贵的。您可以基于输入流
创建扫描仪
,它可能比将数据读入字符串
并对其进行解析快得多。您可以重写FileInputStream
,在文件末尾返回一个虚拟换行符,从而避免粘贴字符串的出现
如果您确实必须将数据读入缓冲区,那么最好使用流中基于数组的
read()
方法读入字节数组,这比逐字节读入快得多。因为您可以预先知道文件的大小,所以可以为额外的行尾标记分配缓冲区空间,并将其插入数组中。与创建StringBuffer
并从中生成String
不同,这不需要缓冲区的完整副本。如果您所做的只是将生成的文件传递给扫描仪,则应该为该文件创建一个可读文件并将其发送给扫描仪
以下是一个示例(未经测试):
这只读取文件一次,从不复制它(与StringBuffer不同——除非您确实需要同步StringBuffer,否则您应该使用StringBuilder)
这也不会将实际文件加载到内存中,因此也可以节省内存压力。如果您所做的只是将生成的文件传递到扫描仪,则应该为该文件创建一个可读文件并将其发送到扫描仪 以下是一个示例(未经测试): 这只读取文件一次,从不复制它(与StringBuffer不同——除非您确实需要同步StringBuffer,否则您应该使用StringBuilder)
这也不会将实际文件加载到内存中,因此也可以节省内存压力。据我所知,您实际要做的是以这样的方式读取文件,即文件在最后一行的末尾似乎总是有一个行分隔符 如果是这种情况,那么您可以通过实现一个子类型
FilterReader
,并在到达字符流末尾时,根据需要让它“插入”一个或两个额外的字符来实现这一点
执行此操作的代码不会很琐碎,但它将避免在内存中缓冲整个文件的时间和空间开销。据我所知,您实际要做的是以这样一种方式读取文件,即文件在最后一行的末尾似乎总是有一个行分隔符 如果是这种情况,那么您可以通过实现一个子类型
FilterReader
,并在到达字符流末尾时,根据需要让它“插入”一个或两个额外的字符来实现这一点
执行此操作的代码不会很琐碎,但它将避免在内存中缓冲整个文件的时间和空间开销。至少,将StringBuffer初始化为文件的长度(如果您知道的话),或者至少初始化为一个合理的大数,以最小化重新分配操作。谢谢。我发现这个链接也很好地发挥了作用,所以对于那些碰巧和我有同样想法的人来说:好吧,至少,将StringBuffer初始化为文件的长度(如果你知道的话),或者至少初始化为一个相当大的数,以最小化重新分配操作。谢谢。我发现这个链接也很好地发挥了作用,所以对于那些碰巧对我有同样想法的人来说:
read_data = new BufferedReader( new FileReader(args[0]) );
data_buffer = new StringBuffer();
int i;
while(read_data.ready())
{
while((i = read_data.read()) != -1)
{
data_buffer.append((char)i);
}
}
data_buffer.append(System.getProperty("line.separator"));
public class NLReader implements Readable {
Reader r;
boolean atEndOfReader = false;
boolean atEnd = false;
public NLReader(Reader r) {
this.r = r;
}
public int read(CharBuffer cb) throws IOException {
if (!atEndOfReader) {
int result = r.read(cb);
if (result == -1) {
atEndOfReader = true;
} else {
return result;
}
}
if (!atEnd) {
String nl = System.getProperty("line.separator");
cb.append(nl);
atEnd = true;
return nl.length();
}
return -1;
}
}