我有一个包含8列的csv文件,我试图用8个变量填充一个对象,每个变量都是一个列表来保存csv文件中的列。首先,我使用我的csv数据填充DataTable
。
我现在正尝试使用DataTable
DataTable d = GetDataTableFromCSVFile(file);
CoolObject l = new CoolObject();
for (int i = 0; i < d.Rows.Count; i++)
{
l.column1[i] = d.Rows[i].Field<int>("column1"); <-- error here
}
这是我的CoolObject
public class CoolObject
{
public List<int> column1 { set; get; }
protected CoolObject()
{
column1 = new List<int>();
}
}
不幸的是,我在突出显示的行上收到错误:
System.InvalidCastException: Specified cast is not valid
为什么不允许这样做?我该如何解决这个问题?
答案 0 :(得分:1)
显然你DataTable
包含string类型的列,所以在GetDataTableFromCSVFile
方法中进行整数验证,所以这个方法的使用者不需要担心它。
显然你DataTable
包含string类型的列,所以在GetDataTableFromCSVFile
方法中进行整数验证,所以这个方法的使用者不需要担心它。
private DataTable GetDataTableFromCSVFile()
{
var data = new DataTable();
data.Columns.Add("Column1", typeof(int));
// Read lines of file
// line is imaginery object which contains values of one row of csv data
foreach(var line in lines)
{
var row = data.NewRow();
int.TryParse(line.Column1Value, out int column1Value)
row.SetField("Column1", column1Value) // will set 0 if value is invalid
// other columns
}
return data;
}
然后是您的代码的另一个问题,即您通过索引向List<int>
提供新值,其中list为空
l.column1[i] = d.Rows[i].Field<int>("column1");
上面的行将抛出异常,因为空列表没有索引i
上的项目。
所以你最终会看到你的方法
DataTable d = GetDataTableFromCSVFile(file);
CoolObject l = new CoolObject();
foreach (var row in d.Rows)
{
l.column1.Add(row.Field<int>("column1"));
}
如果您使用某些第三方库从csv检索数据到DataTable
- 您可以检查该库是否可以在DataTable中验证/转换字符串值到预期类型。
答案 1 :(得分:-1)
听起来有人没有在其中一个单元格中输入数字。在读取值之前,您必须执行验证检查。
df1:
id page_ids (collect_list)
12 ['1001','1001','1002','1003']
13 ['2001','2002','2003','2004']
df2:
id page_id
12 '1002'
13 '4001'
df3 = df1 \
.join(df2,on=df1['id'] == df2['id']) \
.filter(udf(col(page_ids),col('page_id))
或者它可能是一个数字,但由于某种原因,它是以字符串形式出现的。你可以这样试试:
for (int i = 0; i < d.Rows.Count; i++)
{
object o = d.rows[i]["column1"];
if (!o is int) continue;
l.column1[i] = (int)o;
}