为什么在开始和结束字符串之间删除在java中无法正常工作?

时间:2015-12-08 13:24:09

标签: java

我有以下代表书籍的文件

Book: ISBN=3
title=english1
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john]
-------------------------
Book: ISBN=5
title=english2
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john2]
-------------------------
Book: ISBN=6
title=english3
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john3]
-------------------------

我尝试使用此功能从文件中删除第二本书: 功能:

public static void removeLineFromFile(String file, String start, String end) {
    try {

      File inFile = new File(file);

      //Construct the new file that will later be renamed to the original filename.
      File tempFile = new File(inFile.getAbsolutePath() + ".tmp");

      BufferedReader br = new BufferedReader(new FileReader(file));
      PrintWriter pw = new PrintWriter(new FileWriter(tempFile));    
      String line = null;
      Boolean flag=true;
      //Read from the original file and write to the new
      //unless content matches data to be removed.
      while ((line = br.readLine()) != null) {

        if (line.trim().equals(start)) {
         flag=false;  

        }
        if(line.trim().equals(end)){
         flag=true; 
        }

        if (flag && !(line.trim().equals(end))){
        pw.println(line);
        pw.flush();
        }

      }
      pw.close();
      br.close();

      //Delete the original file
      if (!inFile.delete()) {
        System.out.println("Could not delete file");
        return;
      }

      //Rename the new file to the filename the original file had.
      if (!tempFile.renameTo(inFile))
        System.out.println("Could not rename file");

    }
    catch (FileNotFoundException ex) {
      ex.printStackTrace();
    }
    catch (IOException ex) {
      ex.printStackTrace();
    }
}

函数调用:

public static void main(String[] args) {
       removeLineFromFile("E:\\file.txt", "Book: ISBN=5","-------------------------")
}

这本书被删除了但是另一本" -------------------------"分隔符也被删除 `

Book: ISBN=3
title=english1
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john]
Book: ISBN=6
title=english3
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john3]

我应该怎样做才能获得以下结果:

Book: ISBN=3
title=english1
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john]
-------------------------
Book: ISBN=6
title=english3
publishDate=1/12/2015
pageCount=200
authors=[12, 11, john3]
-------------------------

7 个答案:

答案 0 :(得分:7)

这是我能提出的最简单的解决方案:

ZZ1

问题是你过早地设置了旗帜,因此没有打印出来。

答案 1 :(得分:4)

你的第一个问题是这一行:

if (flag && !(line.trim().equals(end)))

由于您已经检查过当前行是否等于结束字符串并将标志更改为true,因此对于每次出现的结束字符串,此整个语句将始终为true。这就是为什么每条-------------------------行都不在输出中 如果删除此if语句中的第二部分意味着将其更改为:if(flag){...},您将实现结束字符串的每个出现都将在输出中。
这导致了代码的第二个问题:订单。您可以使用标志作为输入输入的阀门。当你找到起始字符串时,你用你的标志发信号来关闭输出写入。然后检查是否要发出输出写入的开启信号。只有这样你才能根据旗帜进行写作 您需要在此处更改顺序以获得有意义的数据流 考虑两个州

标志为TRUE表示您的流应该流

  1. 检查开始字符串
  2. 写入数据
  3. 标志为FALSE表示您的流不应流

    1. 不写数据
    2. 检查结束字符串
    3. 使用此while循环可以实现所需的行为。

      while ((line = br.readLine()) != null) {
      
          if (line.trim().equals(start)) {
              flag=false;  
          }
      
          if (flag){
              pw.println(line);
              pw.flush();
          }
      
          if(line.trim().equals(end)){
              flag=true; 
          }
      }
      

答案 2 :(得分:3)

这个表达的第二部分是你的" -------------------------"被删除(你永远不会打印"结束"行):

(flag && !(line.trim().equals(end)))

答案 3 :(得分:3)

因此。

if(line.trim().equals(end)){
    flag=true; 
}

if (flag && !(line.trim().equals(end))){
    pw.println(line);
    pw.flush();
}

在第一个if中,flag设置为true,但是对于循环中的此运行,行line.trim().equals(end)也是如此,因此当行等于变量{时,将永远不会访问第二个if已达到{1}}。在这种情况下,它是end

如果你的文件看起来总是一样,你可以把循环更改为“当你找到-------------------时,删除接下来的5行”,这不是真正的美学,或者你必须将一个新的循环嵌入到第一个start

嵌套循环可能如下所示:

if

第二次会直到找到结束并继续下去。

答案 4 :(得分:3)

从模式方面看问题 - 您是否处于复制模式。如果要复制,则除非找到开始模式,否则将输入复制到输出。如果找到了开始模式,则切换到非复制模式。

在非复印模式下,只需在切换到复印模式时查找结束图案。

在代码方面,这变为

  Boolean copyMode=true;
  while ((line = br.readLine()) != null) {
    if(copyMode) {
        // Check for signal to stop copying
        if(line.trim().equals(start)) {
            copyMode = false;
            continue;
        }
        // Just copy to output file
        pw.println(line);
    } else {
        // Check for signal to restart copying
        if(line.trim().equals(end)) {
            copyMode = true;
        }
    }
}

答案 5 :(得分:1)

以下是此

的更新代码
public static void removeLineFromFile(String file, String start, String end) {
    try {

      File inFile = new File(file);

      //Construct the new file that will later be renamed to the original filename.
      File tempFile = new File(inFile.getAbsolutePath() + ".tmp");

      BufferedReader br = new BufferedReader(new FileReader(file));
      PrintWriter pw = new PrintWriter(new FileWriter(tempFile));    
      String line = null;
      Boolean flag=false;
      Boolean skip=false;

      //Read from the original file and write to the new
      //unless content matches data to be removed.
      while ((line = br.readLine()) != null) {

        if (flag || line.trim().equals(start)) {
         flag=true;
         skip =true;

        }

            if (!skip) {
                pw.println(line);
                pw.flush();
            }

        if(flag && line.trim().equals(end)){
            flag=false;
            skip=false;
        }

      }
      pw.close();
      br.close();

      //Delete the original file
      if (!inFile.delete()) {
        System.out.println("Could not delete file");
        return;
      }

      //Rename the new file to the filename the original file had.
      if (!tempFile.renameTo(inFile))
        System.out.println("Could not rename file");

    }
    catch (FileNotFoundException ex) {
      ex.printStackTrace();
    }
    catch (IOException ex) {
      ex.printStackTrace();
    }
}

请注意引入新标志跳过这有助于将内容从“开始”字符串排除到“结束字符串”。

答案 6 :(得分:1)

这是一个简单的解决方案,我想出来它将删除所有东西b / w开始和结束字符串,但仅在开始字符串匹配时。

time

请注意引入新的flag1和flag2而不是flag。这将有助于将内容从Start字符串排除到End string。