Reputation: 23
I have CSV file that has multiples columns with the same header name. I am using CsvHelper library. I want to collect their row values into one List but I am collecting first row value as many times I have header specified and not collecting from another index position. ex. COLUMN COLUMN Test1 Test2 Test3 Test4 I expect that my list has two elements first with value Test1,Test2 and second one with values Test3,Test4 but I first row has values Test1,Test1 and second Test3,Test3.
This is the mapping for this column
Map(m => m.COLUMN).ConvertUsing(row =>
(row as CsvReader)?.FieldHeaders
.Where(header => header.StartsWith("COLUMN"))
.Select(header => row.GetField<string>(header))
.Where(value => !string.IsNullOrWhiteSpace(value))
.ToList()
);
Can this be done with mapping? If I change Column names to COLUMN1 and COLUMN2 this works but that is not the solution for my problem.
Upvotes: 2
Views: 3368
Reputation: 23373
There are many ways to do this. Here is one example.
void Main()
{
using (var stream = new MemoryStream())
using (var writer = new StreamWriter(stream))
using (var reader = new StreamReader(stream))
using (var csv = new CsvReader(reader))
{
writer.WriteLine("Id,Name,List,List,List");
writer.WriteLine("1,one,a,b,c");
writer.WriteLine("1,two,d,e,f");
writer.Flush();
stream.Position = 0;
csv.Configuration.RegisterClassMap<TestMap>();
csv.GetRecords<Test>().Dump();
}
}
public class Test
{
public int Id { get; set; }
public string Name { get; set; }
public List<string> List { get; set; }
}
public sealed class TestMap : CsvClassMap<Test>
{
public TestMap()
{
Map(m => m.Id);
Map(m => m.Name);
Map(m => m.List).ConvertUsing(row =>
{
var list = new List<string>();
list.Add(row.GetField("List", 0));
list.Add(row.GetField("List", 1));
list.Add(row.GetField("List", 2));
return list;
});
}
}
Also, version 3 has mapping to enumerables built in.
Map(m => m.List).Name("List");
Upvotes: 3