我正在尝试获得一些 Java 线程和共享对象同步以及执行简单锁定的经验。 我想做的是创建 Java 应用程序,它使用 2 个不同的线程将时间戳(或分钟)插入到文本文件中:一个线程仅将奇数时间戳(或分钟)插入到文件中,另一个线程将仅将偶数时间戳插入到同一文件中文件。当一个线程正在插入时,另一个线程无法插入并等待,直到收到通知。文件内容必须在进程关闭后(控制台中的 Ctrl+C)如下所示:
2013-05-10 21:37:02 2013-05-10 21:37:03 2013-05-10 21:37:04 2013-05-10 21:37:05
或
2013-05-10 21:37 2013-05-10 21:38 2013-05-10 21:39 2013-05-10 21:40
首先,我只想创建一个线程,它将在文件中插入行,但无法弄清楚出了什么问题。这是我的代码:
导入java.io.*;
公共(public)类 MyFileWriter
{
私有(private) FileWriter fwriter;
私有(private) BufferedWriter bufwriter;
公共(public) FileWriter getWriter()
{
返回 this.fwriter;
}
公共(public)无效setWriter(FileWriter pfwriter)
{
this.fwriter = pfwriter;
}
公共(public) BufferedWriter getBufWriter()
{
返回这个.bufwriter;
}
公共(public)无效setBufWriter(BufferedWriter pbfwriter)
{
this.bufwriter = pbfwriter;
}
公共(public)静态无效主(字符串[]参数)
{
MyFileWriter myfile = new MyFileWriter();
尝试
{
FileWriter fstream = new FileWriter("output.txt");
myfile.setWriter(fstream);
BufferedWriter out = new BufferedWriter(fstream);
myfile.setBufWriter(out);
}
捕获(IOException e)
{
System.out.println("错误:"+e.getMessage());
}
MyThread mt = new MyThread();
mt.setBufWriter(myfile.getBufWriter());
mt.start();
}
}
MyThread 类扩展了 Thread
{
私有(private) BufferedWriter 回合;
私有(private)整数计数 = 1;
公共(public) BufferedWriter getBufWriter()
{
返回这个。
}
公共(public)无效setBufWriter(BufferedWriter pbout)
{
this.bout = pbout;
}
公共(public)无效运行()
{
尝试
{
这个.sleep(1000);
}
捕获(InterruptedException e)
{
System.out.println("错误:"+e.getMessage());
}
尝试
{
this.bout.write("字符串#"+count);
this.bout.newLine();
}
捕获(IOException e)
{
System.out.println("错误:"+e.getMessage());
}
this.count++;
}
}
我期望在创建并启动 MyThread mt 后,线程将插入到文件“output.txt”字符串中,并且在命令提示符中执行 Ctrl+C 后,我将得到如下内容:
String #1 String #2 String #3
但是应用程序由于某种原因本身完成,我只得到空文件(有时当我启动应用程序时文件有“String #1”,但大部分是空的)。 谁能告诉我我做错了什么?
操作系统:Windows XP SP3,Java版本:
java版本“1.7.0_21” Java(TM) SE 运行时环境(版本 1.7.0_21-b11) Java HotSpot(TM) 客户端 VM(版本 23.21-b01,混合模式,共享)
最佳答案
嗯,有几件事。首先,您的 run() 方法仅打印一行,并且您仅创建一个线程,因此我不确定您认为其他行将来自哪里。 run()
将在新线程中运行一次,仅此而已。我猜您假设 run()
将在循环中调用,但事实并非如此。
其次,您使用的是 BufferedWriter,此类会在将写入流的数据发送到文件之前对其进行缓冲(保留),以便可以写入大量数据一次,为了效率。问题是,如果您不手动关闭或刷新 BufferedWriter(而且确实没有这样做),那么您的输出将永远不会写入文件。如果在每次写入 BufferedWriter
后添加对 flush()
的调用,您将看到所有输出最终都在文件中 - 尽管这确实消除了原因首先感谢使用 BufferedWriter!
更好的解决方案是等待写入线程终止(使用Thread.join()
),然后在main()
中关闭文件。
关于Java线程写入文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16511078/