我正在使用StreamWriter为我的程序创建日志以写入文件。我有一些看似有效的代码,但它只做它应该做的部分。
我创建了一个名为Log的简单类(下面的代码)。
public class Log
{
string path;
StreamWriter fs;
public Log(string fullPathToLogFile)
{
path = fullPathToLogFile;
fs = new StreamWriter(path);
writeLog("Starting log");
}
public void writeLog(string s)
{
fs.WriteLine(DateTime.Now.ToString("dd-MM-yyyy H:mm:ss ") + s);
}
public void closeLog()
{
writeLog("Closing log");
fs.WriteLine(); //add a blank line at the end
fs.Close();
}
}
我制作了一个完美的测试程序。它执行以下三行:
Log l = new Log(@"C:\Users\SADunkerton\Desktop\l.txt");
l.writeLog("testing log");
l.closeLog();
但是在我更大的程序中,我实际上想要使用Log类,我得到的只是一个空文件 - 里面没有文本。它的代码如下:
Log log = new Log(folderPDFs + @"\Log.txt"); //folderPDFs is a parameter of this method--it is a string that is a complete path to a destination folder.
log.writeLog("Beginning conversions");
//do some stuff, including write to the log
log.writeLog("Finished converting. Success = " + success);
有谁能告诉我为什么这段代码的程序版本不起作用?
答案 0 :(得分:3)
我会重写你的Log类以避免关闭部分 完成写入部分后,只需打开,写入和关闭
class MySimpleLog
{
private string _filename;
public MySimpleLog(string filename)
{
_filename = filename;
}
public void AppendText(string msg)
{
// Create an instance of StreamWriter to write text to a file.
// The using statement also closes the StreamWriter.
using (StreamWriter sw = new StreamWriter(_filename, true))
{
// Add some text to the file.
sw.WriteLine(msg);
}
}
}
通过这种方式,using语句将关闭流,您不必担心关闭它。实际上,如果代码中出现意外情况,关闭流可能非常麻烦。 (就像更改代码流的异常一样)。
这只是测试和验证代码的起点,但您可以按照给定的模式添加一些更复杂的逻辑。例如,你可以添加一个带有标志的构造函数来为每一行添加一个时间戳(或者添加一个分隔线的标志,或者如果存在则重新创建文件的标志......)
class MySimpleLog
{
private string _filename;
private bool _addtime;
public MySimpleLog(string filename)
{
_filename = filename;
}
public MySimpleLog(string filename, bool addtime)
{
_filename = filename;
_addtime = addtime;
}
public void AppendText(string msg)
{
// Create an instance of StreamWriter to write text to a file.
// The using statement also closes the StreamWriter.
using (StreamWriter sw = new StreamWriter(_filename, true))
{
// Add some text to the file.
msg = (_addtime ? DateTime.Now.ToString() + ": " + msg : msg);
sw.WriteLine(msg);
}
}
}
最后:请记住,专门的日志库存在经过良好测试且可以免费使用。也许你可以投入一些时间来学习它们
答案 1 :(得分:1)
1。你没有在第二个例子中关闭流 - 以及垃圾收集会发生什么我不确定。最后调用l.closeLog();
至少得到一些输出。但这不是一个好主意。如果某个方法在l.write();
和l.closeLog;
之间抛出,会发生什么。不太好的事情 - 文件将在GC处理之前保持打开状态。
2。您在每次通话时都会覆盖该文件。您可能需要的是附加数据 - http://msdn.microsoft.com/en-us/library/3zc0w663(v=vs.110).aspx甚至更好地更改您的代码以使用File.AppendText方法:
public void writeLog(string s)
{
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine(DateTime.Now.ToString("dd-MM-yyyy H:mm:ss ") + s);
}
}
并删除closeLog
方法,因为这是不必要的。
修改强>
最好的想法是使用无状态标准方法(如@leppie所指出的),不会泄漏任何资源:
如果为每个日志实例创建一个日志文件,则为File.WriteAllText:
public void writeLog(string s)
{
File.WriteAllText(path,
DateTime.Now.ToString("dd-MM-yyyy H:mm:ss ") + s);
}
或File.AppendAllText如果您需要继续现有日志:
public void writeLog(string s)
{
File.AppendAllText(path,
DateTime.Now.ToString("dd-MM-yyyy H:mm:ss ") + s);
}