我试图用c#语言一行一行地写入csv文件。这是我的函数
string first = reader[0].ToString();
string second=image.ToString();
string csv = string.Format("{0},{1}\n", first, second);
File.WriteAllText(filePath, csv);
整个函数在循环中运行,每一行都应该写入csv文件。在我的例子中,下一行覆盖了现有的行,最后,我在csv文件中只得到一条记录,这是最后一条记录。如何写入csv文件中的所有行?
下面是另一个开源库,可以轻松创建CSV文件,Cinchoo ETL
List<dynamic> objs = new List<dynamic>();
dynamic rec1 = new ExpandoObject();
rec1.Id = 10;
rec1.Name = @"Mark";
rec1.JoinedDate = new DateTime(2001, 2, 2);
rec1.IsActive = true;
rec1.Salary = new ChoCurrency(100000);
objs.Add(rec1);
dynamic rec2 = new ExpandoObject();
rec2.Id = 200;
rec2.Name = "Tom";
rec2.JoinedDate = new DateTime(1990, 10, 23);
rec2.IsActive = false;
rec2.Salary = new ChoCurrency(150000);
objs.Add(rec2);
using (var parser = new ChoCSVWriter("emp.csv").WithFirstLineHeader())
{
parser.Write(objs);
}
有关更多信息,请阅读CodeProject关于使用的文章。
下面是另一个开源库,可以轻松创建CSV文件,Cinchoo ETL
List<dynamic> objs = new List<dynamic>();
dynamic rec1 = new ExpandoObject();
rec1.Id = 10;
rec1.Name = @"Mark";
rec1.JoinedDate = new DateTime(2001, 2, 2);
rec1.IsActive = true;
rec1.Salary = new ChoCurrency(100000);
objs.Add(rec1);
dynamic rec2 = new ExpandoObject();
rec2.Id = 200;
rec2.Name = "Tom";
rec2.JoinedDate = new DateTime(1990, 10, 23);
rec2.IsActive = false;
rec2.Salary = new ChoCurrency(150000);
objs.Add(rec2);
using (var parser = new ChoCSVWriter("emp.csv").WithFirstLineHeader())
{
parser.Write(objs);
}
有关更多信息,请阅读CodeProject关于使用的文章。
更新
回到我的naïve时代,我建议手动做这件事(这是一个简单问题的简单解决方案),然而由于这变得越来越流行,我建议使用库CsvHelper来做所有的安全检查,等等。
CSV比问题/答案所暗示的要复杂得多。
原来的答案
因为你已经有了一个循环,考虑这样做:
//before your loop
var csv = new StringBuilder();
//in your loop
var first = reader[0].ToString();
var second = image.ToString();
//Suggestion made by KyleMit
var newLine = string.Format("{0},{1}", first, second);
csv.AppendLine(newLine);
//after your loop
File.WriteAllText(filePath, csv.ToString());
或者类似的东西。
我的理由是:你不需要为每一项写入文件,你只需要打开流一次,然后写入它。
你可以替换
File.WriteAllText(filePath, csv.ToString());
与
File.AppendAllText(filePath, csv.ToString());
如果您希望将CSV的以前版本保存在同一文件中
C# 6
如果您正在使用c# 6.0,那么您可以执行以下操作
var newLine = $"{first},{second}"
EDIT
这里有一个问题的链接,解释了什么环境。换行符。
可以使用库而不是重新发明轮子。CsvHelper非常适合创建和读取csv文件。它的读写操作是基于流的,因此也支持有大量数据的操作。
您可以像下面这样编写csv文件。
using(var textWriter = new StreamWriter(@"C:\mypath\myfile.csv"))
{
var writer = new CsvWriter(textWriter, CultureInfo.InvariantCulture);
writer.Configuration.Delimiter = ",";
foreach (var item in list)
{
writer.WriteField( "a" );
writer.WriteField( 2 );
writer.WriteField( true );
writer.NextRecord();
}
}
由于库正在使用反射,它将接受任何类型并直接解析它。
public class CsvRow
{
public string Column1 { get; set; }
public bool Column2 { get; set; }
public CsvRow(string column1, bool column2)
{
Column1 = column1;
Column2 = column2;
}
}
IEnumerable<CsvRow> rows = new [] {
new CsvRow("value1", true),
new CsvRow("value2", false)
};
using(var textWriter = new StreamWriter(@"C:\mypath\myfile.csv")
{
var writer = new CsvWriter(textWriter, CultureInfo.InvariantCulture);
writer.Configuration.Delimiter = ",";
writer.WriteRecords(rows);
}
value1,真切
value2,假
如果你想阅读更多关于库的配置和可能性,你可以在这里这样做。
你可以使用AppendAllText代替:
File.AppendAllText(filePath, csv);
正如WriteAllText的文档所说:
如果目标文件已经存在,那么它将被覆盖
此外,请注意您当前的代码没有使用适当的新行,例如在记事本中,您将看到它都是一个长行。将代码更改为这样,以获得正确的新行:
string csv = string.Format("{0},{1}{2}", first, image, Environment.NewLine);