编辑
2025-02-05
C# 应用
00
请注意,本文编写于 122 天前,最后修改于 122 天前,其中某些信息可能已经过时。

目录

安装
基本用法
读取CSV文件
写入CSV文件
高级用法
自定义映射
忽略某些字段
处理日期时间
处理枚举
性能优化
结论

CsvHelper是一个用于读写CSV(逗号分隔值)文件的开源.NET库。它提供了简单而强大的API,使得处理CSV文件变得轻而易举。本文将详细介绍CsvHelper的使用方法,并提供多个实用的例子。

安装

首先,通过NuGet包管理器安装CsvHelper:

C#
Install-Package CsvHelper

image.png

基本用法

读取CSV文件

假设我们有一个名为people.csv的文件,内容如下:

text
Name,Age,City John Doe,30,New York Jane Smith,25,London Mike Johnson,35,Paris

我们可以使用以下代码读取这个文件:

C#
using System; using System.Globalization; using System.IO; using CsvHelper; public class Person { public string Name { get; set; } public int Age { get; set; } public string City { get; set; } } class Program { static void Main(string[] args) { using (var reader = new StreamReader("people.csv")) using (var csv = new CsvReader(reader, CultureInfo.InvariantCulture)) { var records = csv.GetRecords<Person>(); foreach (var record in records) { Console.WriteLine($"{record.Name} is {record.Age} years old and lives in {record.City}."); } } } }

image.png

写入CSV文件

现在,让我们创建一个新的CSV文件:

C#
using System.Collections.Generic; using System.Globalization; using System.IO; using CsvHelper; public class Product { public string Name { get; set; } public decimal Price { get; set; } public int Quantity { get; set; } } class Program { static void Main(string[] args) { var products = new List<Product> { new Product { Name = "Apple", Price = 0.5m, Quantity = 100 }, new Product { Name = "Banana", Price = 0.3m, Quantity = 150 }, new Product { Name = "Orange", Price = 0.4m, Quantity = 80 } }; using (var writer = new StreamWriter("products.csv")) using (var csv = new CsvWriter(writer, CultureInfo.InvariantCulture)) { csv.WriteRecords(products); } } }

高级用法

自定义映射

有时,CSV文件的列名可能与我们的类属性名不匹配。我们可以使用自定义映射来解决这个问题:

C#
using CsvHelper; using CsvHelper.Configuration; using System; using System.Globalization; using System.IO; using System.Collections.Generic; public class Person { public string Name { get; set; } public int Age { get; set; } public string City { get; set; } } public class PersonMap : ClassMap<Person> { public PersonMap() { Map(m => m.Name).Name("FullName"); Map(m => m.Age).Name("YearsOld"); Map(m => m.City).Name("Location"); } } class Program { static void Main(string[] args) { string filePath = "people_custom.csv"; // 首先创建一些示例数据并写入CSV文件 CreateSampleCsvFile(filePath); // 然后读取CSV文件 List<Person> people = ReadCsvFile(filePath); // 打印读取的数据 foreach (var person in people) { Console.WriteLine($"Name: {person.Name}, Age: {person.Age}, City: {person.City}"); } } static void CreateSampleCsvFile(string filePath) { var records = new List<Person> { new Person { Name = "John Doe", Age = 30, City = "New York" }, new Person { Name = "Jane Smith", Age = 25, City = "Los Angeles" }, new Person { Name = "Bob Johnson", Age = 45, City = "Chicago" } }; using (var writer = new StreamWriter(filePath)) using (var csv = new CsvWriter(writer, CultureInfo.InvariantCulture)) { csv.Context.RegisterClassMap<PersonMap>(); csv.WriteRecords(records); } Console.WriteLine("Sample CSV file created."); } static List<Person> ReadCsvFile(string filePath) { using (var reader = new StreamReader(filePath)) using (var csv = new CsvReader(reader, CultureInfo.InvariantCulture)) { csv.Context.RegisterClassMap<PersonMap>(); return csv.GetRecords<Person>().ToList(); } } }

image.png

忽略某些字段

如果我们只想读取或写入特定的字段,可以使用Ignore()方法:

C#
public class PersonMap : ClassMap<Person> { public PersonMap() { Map(m => m.Name); Map(m => m.Age); Map(m => m.City).Ignore(); } }

处理日期时间

CsvHelper可以自动处理日期时间的转换,但有时我们可能需要指定特定的格式:

C#
using CsvHelper; using CsvHelper.Configuration; using System; using System.Collections.Generic; using System.Globalization; using System.IO; public class Event { public string Name { get; set; } public DateTime Date { get; set; } } public class EventMap : ClassMap<Event> { public EventMap() { Map(m => m.Name); Map(m => m.Date).TypeConverterOption.Format("yyyy-MM-dd"); } } class Program { static void Main(string[] args) { string filePath = "events.csv"; // 写入CSV文件 WriteEventsToCSV(filePath); // 读取CSV文件 List<Event> events = ReadEventsFromCSV(filePath); // 打印读取的数据 foreach (var evt in events) { Console.WriteLine($"Event: {evt.Name}, Date: {evt.Date:yyyy-MM-dd}"); } } static void WriteEventsToCSV(string filePath) { using (var writer = new StreamWriter(filePath)) using (var csv = new CsvWriter(writer, CultureInfo.InvariantCulture)) { csv.Context.RegisterClassMap<EventMap>(); csv.WriteRecords(new List<Event> { new Event { Name = "Conference", Date = new DateTime(2023, 5, 15) }, new Event { Name = "Workshop", Date = new DateTime(2023, 6, 1) } }); } Console.WriteLine("CSV file written successfully."); } static List<Event> ReadEventsFromCSV(string filePath) { using (var reader = new StreamReader(filePath)) using (var csv = new CsvReader(reader, CultureInfo.InvariantCulture)) { csv.Context.RegisterClassMap<EventMap>(); return csv.GetRecords<Event>().ToList(); } } }

image.png

处理枚举

CsvHelper可以很好地处理枚举类型:

C#
public enum Category { Food, Electronics, Clothing } public class Product { public string Name { get; set; } public Category Category { get; set; } } class Program { static void Main(string[] args) { var products = new List<Product> { new Product { Name = "Apple", Category = Category.Food }, new Product { Name = "Laptop", Category = Category.Electronics }, new Product { Name = "T-Shirt", Category = Category.Clothing } }; using (var writer = new StreamWriter("products_with_category.csv")) using (var csv = new CsvWriter(writer, CultureInfo.InvariantCulture)) { csv.WriteRecords(products); } } }

性能优化

对于大型CSV文件,我们可以使用GetRecords<T>()方法的延迟执行特性来提高性能:

C#
using (var reader = new StreamReader("large_file.csv")) using (var csv = new CsvReader(reader, CultureInfo.InvariantCulture)) { foreach (var record in csv.GetRecords<Person>()) { // 处理每条记录,而不是一次性加载所有记录到内存 ProcessRecord(record); } }

结论

CsvHelper是一个功能强大且灵活的库,可以大大简化CSV文件的处理过程。通过本文提供的示例,你应该能够处理大多数常见的CSV相关任务。无论是简单的读写操作,还是复杂的自定义映射和类型转换,CsvHelper都能够胜任。在处理数据导入导出、日志分析等涉及CSV格式的场景时,CsvHelper是一个值得考虑的工具。

希望这篇文章对你有所帮助,祝你在C#开发中使用CsvHelper愉快!

本文作者:rick

本文链接:

版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!