执行操作的最佳时间:循环内或循环后

Joh*_*oft 0 java optimization performance

我正在读一个文件以便稍后解析.该文件的大小不可能超过MB,因此在这个阶段对我来说这可能不是一个至关重要的问题.但出于最佳实践原因,我想知道何时是执行操作的最佳时间.

例:

使用我从http://www.dzone.com/snippets/java-read-file-string粘贴的方法,我正在将缓冲区读入字符串.我现在想要删除所有空格.我的方法目前是这样的:

private String listRaw;

public boolean readList(String filePath) throws java.io.IOException {
    StringBuffer fileData = new StringBuffer(1024);
    BufferedReader reader = new BufferedReader(
            new FileReader(filePath));
    char[] buf = new char[1024];
    int numRead=0;
    while((numRead=reader.read(buf)) != -1){
        String readData = String.valueOf(buf, 0, numRead);
        fileData.append(readData);
        buf = new char[1024];
    }
    reader.close();
    listRaw = fileData.toString().replaceAll("\\s","");
    return true;
}
Run Code Online (Sandbox Code Playgroud)

因此,我将字符串中的所有空格从其存储中删除 - 完整地 - 转换为类变量.

对我来说,这意味着更少的处理,但更多的内存使用.出于最佳实践原因,我将它附加到变量replaceAll()上会更好吗?使用更多处理但避免传递多余的空白.readDatafileData

我想这对我正在处理的小文件影响不大,但是如果它是一个200MB的日志文件呢?

它是完全依赖于案例的,还是有共识我会更好地遵循?


感谢大家的投入.我相信你已经帮助我的思维方向成为编写Java的正确方向.

我已经更新了我的代码,以考虑提出的问题.包括Don Roby的建议,在某些时候,我可能想要保留空间.希望事情现在读得更好!

private String listRaw;

public boolean readList(String filePath) throws java.io.IOException {
    StringBuilder fileData = new StringBuilder(51200);
    BufferedReader reader = new BufferedReader(new FileReader(filePath));
    char[] buf = new char[51200];
    boolean spaced = false;
    while(reader.read(buf) != -1){
        for(int i=0;i<buf.length;i++) {
            char c = buf[i];
            if (c != '\t' && c != '\r' && c != '\n') {
                if (c == ' ') {
                    if (spaced) {
                        continue;
                    }
                    spaced = true;
                } else {
                    spaced = false;
                }

                fileData.append(c);
            }
        }
    }
    reader.close();
    listRaw = fileData.toString().trim();
    return true;
}
Run Code Online (Sandbox Code Playgroud)

JB *_*zet 7

最后,您最好只创建和应用一次regexp替换.但你会获得更多

  • 使用合理的大小初始化StringBuilder
  • 避免在循环内创建String,并将读取的字符直接附加到StringBuilder
  • 在每次迭代时,避免实例化新的char缓冲区.

为了避免不必要的长临时字符串创建,您可以通过char读取char,并且如果它不是空格,则只将char附加到StringBuilder .最后,StringBuilder只包含好的字符,你不需要任何replaceAll()调用.