这是一个数据同步程序,运行在数据库服务器上面,将一个数据库中的数据同步到另一个数据库中。对每个表的同步操作,都会添加到各自的日志文件中。现在程序跑起来出现下面的错误。
下面的是示例代码,示例程序中仅仅是一个Form:
using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.IO; using System.Linq; using System.Text; using System.Threading; using System.Windows.Forms; namespace AppTest { public partial class Form1 : Form { //每隔多长时间执行一次同步操作 private static readonly int IntervalTime = 10000; public Form1() { InitializeComponent(); TableSynchro(); } # region 同步数据 private void TableSynchro() { //表1 Tablel1_Thread = new Thread(new ThreadStart(Tablel1_Synchro)); Tablel1_Thread.Start(); //表2 Tablel2_Thread = new Thread(new ThreadStart(Tablel2_Synchro)); Tablel2_Thread.Start(); //表3 Tablel3_Thread = new Thread(new ThreadStart(Tablel3_Synchro)); Tablel3_Thread.Start(); //表4 Tablel4_Thread = new Thread(new ThreadStart(Tablel4_Synchro)); Tablel4_Thread.Start(); } /*线程同步方法中,通过无限循环和Sleep让线程每隔一段时间执行一次*/ private Thread Tablel1_Thread; private void Tablel1_Synchro() { while (true) { string logTxt = ""; DateTime beginT = DateTime.Now; logTxt += "表1:" + "同步操作返结果(略)"; DateTime endT = DateTime.Now; logTxt += "操作时间:" + endT.ToString() + ",用时:" + (endT - beginT).TotalSeconds.ToString() + "秒" + Environment.NewLine; WriteLog(logTxt, "Tablel1"); Thread.Sleep(IntervalTime); } } private Thread Tablel2_Thread; private void Tablel2_Synchro() { while (true) { string logTxt = ""; DateTime beginT = DateTime.Now; logTxt += "表2:" + "同步操作返结果(略)"; DateTime endT = DateTime.Now; logTxt += "操作时间:" + endT.ToString() + ",用时:" + (endT - beginT).TotalSeconds.ToString() + "秒" + Environment.NewLine; WriteLog(logTxt, "Tablel2"); Thread.Sleep(IntervalTime); } } private Thread Tablel3_Thread; private void Tablel3_Synchro() { while (true) { string logTxt = ""; DateTime beginT = DateTime.Now; logTxt += "表3:" + "同步操作返结果(略)"; DateTime endT = DateTime.Now; logTxt += "操作时间:" + endT.ToString() + ",用时:" + (endT - beginT).TotalSeconds.ToString() + "秒" + Environment.NewLine; WriteLog(logTxt, "Tablel3"); Thread.Sleep(IntervalTime); } } private Thread Tablel4_Thread; private void Tablel4_Synchro() { while (true) { string logTxt = ""; DateTime beginT = DateTime.Now; logTxt += "表4:" + "同步操作返结果(略)"; DateTime endT = DateTime.Now; logTxt += "操作时间:" + endT.ToString() + ",用时:" + (endT - beginT).TotalSeconds.ToString() + "秒" + Environment.NewLine; WriteLog(logTxt, "Tablel4"); Thread.Sleep(IntervalTime); } } #endregion /// <summary> /// 写日志 /// </summary> /// <param name="logtxt">增加内容</param> /// <param name="fileName">表名用作文件名</param> private static void WriteLog(string logtxt, string fileName) { string directoryPath = Directory.GetCurrentDirectory() + @"\log\"; string filePath = directoryPath + fileName + ".txt"; //存放日志文件的目录是否存在 if (!Directory.Exists(directoryPath)) { Directory.CreateDirectory(directoryPath); } FileInfo file = new FileInfo(filePath); if (!file.Exists) file.Create(); StreamWriter stream = file.AppendText(); stream.Write(logtxt); stream.Flush(); stream.Close(); } } }
1.LOCK
2.第3方
3.再启个线程,专门负责写日志,所有日志ADD到一个队列中,此线程负责循环写
几个线程操作同一个文件是不行的,加个锁控制一下
最好使用NLOG这样的现有库或者微软的企业库日志处理
这种资源竞争的情况下,还是lock一下吧,不错log这一块不需要自己写,log4net就现成的。
推荐使用现有的日志组件。比如log4.net。一定要应用单例模式,
加锁,或者是用第三方的。
使用线程安全的集合,先将log信息缓存起来,再用其他线程定时输出至log文件,可以解决这个问题.