My application imports a CSV file and parses each row, turning it into an object in my code.
The speed for a 500,000 row x 68 column takes 2+ minutes to read. I've narrowed down the bottleneck to the part where the strings are being converted into their respective types using the converter I created. I need some pointers on how I can optimize my code.
This is the code I use to load:
public static void Load(object target, string[] fields, bool supressErrors)
{
Type targetType = target.GetType();
PropertyInfo[] properties = targetType.GetProperties();
foreach (PropertyInfo property in properties)
{
object[] attributes = property.GetCustomAttributes(typeof(CSVPositionAttribute), false);
if (attributes.Length > 0)
{
CSVPositionAttribute positionAttr = (CSVPositionAttribute)attributes[0];
int position = positionAttr.Position;
try
{
object data = fields[position];
if (positionAttr.DataTransform != string.Empty)
{
MethodInfo method = targetType.GetMethod(positionAttr.DataTransform);
data = method.Invoke(target, new object[] { data });
}
var prop = property.PropertyType;
//bottleneck here:
if (prop == typeof(string))
{
property.SetValue(target, CheckAndConvert.CheckString(data), null);
}
else if (prop == typeof(int))
{
property.SetValue(target, CheckAndConvert.CheckInt(data.ToString()), null);
}
else if (prop == typeof(double))
{
property.SetValue(target, CheckAndConvert.CheckDouble(data.ToString()), null);
}
else if (prop == typeof(long))
{
property.SetValue(target, CheckAndConvert.CheckLong(data.ToString()), null);
}
else if (prop == typeof(bool))
{
property.SetValue(target, CheckAndConvert.CheckBool(data.ToString()), null);
}
}
catch(Exception e)
{
if (!supressErrors)
throw;
}
}
}
}
This is part of the code I use to convert each cell:
public class CheckAndConvert
{
public static int CheckInt(string input)
{
int convertedInput = 0;
double convertedInput2 = 0;
if (int.TryParse(input, out convertedInput))
{
return convertedInput;
}
else if (double.TryParse(input, out convertedInput2))
{
return (int)convertedInput2;
}
else
{
return 0;
}
}
public static double CheckDouble(string input)
{
double convertedInput = 0;
int convertedInput2 = 0;
if (double.TryParse(input, out convertedInput))
{
return convertedInput;
}
else if (int.TryParse(input, out convertedInput2))
{
return convertedInput2;
}
else
{
return 0;
}
}
public static bool CheckBool(string input)
{
bool convertedInput = true;
if (bool.TryParse(input, out convertedInput))
{
return convertedInput;
}
else
{
return true;
}
}
public static string CheckString(object input)
{
if (input == null)
{
return "";
}
else
{
return input.ToString();
}
}
}