I have a Datatable and DataRows in it, and those DataRows gets the value from a XML file.
DataRow row = table.NewRow();
row["InvoiceNumber"] = xmlData.ChildNodes[2].ChildNodes[0].ChildNodes[2].ChildNodes[0].InnerText;
row["InvoiceIssueDate"] = Convert.ToDateTime(xmlData.ChildNodes[2].ChildNodes[0].ChildNodes[2].ChildNodes[1].InnerText);
row["InvoiceDeliveryDate"] = Convert.ToDateTime(xmlData.ChildNodes[2].ChildNodes[0].ChildNodes[2].ChildNodes[2].InnerText);
But when I want to add those rows to my Entity Framework table that's error comes.
Invoices invoices = new Invoices();
invoices.InvoiceNumber = table.Rows[0].ToString();
invoices.InvoiceIssueDate = table.Rows[1];
invoices.InvoiceDeliveryDate = table.Rows[2];
How should I convert them?
try this.
invoices.InvoiceIssueDate = Convert.ToDateTime(table.Rows[1]);
invoices.InvoiceDeliveryDate = Convert.ToDateTime(table.Rows[2]);
Related
Working on a windows form application that reads in data from csv files and adds the data to a Datagridview. I ran into an issue with all of the rows being added to the datable and being displayed on the datagridview. The datagridview displays the datarows from the first two if conditions and OneRow if condition only. It will not add the rows from the twoRow if condition if the datable and datagridview rows are populated with the OneRow if condition rows. But i want the rows from both OneRow and TwoRow to be displyed. Also the rows from TwoRow do populate the datatable and datagridview when I comment(/**/) out the OneRow if condition. But I need both to populate the table. Thanks in advance!
Construct.MainDataTable.Columns.Add("Date", typeof(DateTime));
Construct.MainDataTable.Columns.Add("Time");
Construct.MainDataTable.Columns.Add("Serial");
Construct.MainDataTable.Columns.Add("Type");
Construct.MainDataTable.Columns.Add("level");
Construct.MainDataTable.Columns.Add("price");
Construct.MainDataTable.Columns.Add(" Limit");
Construct.MainDataTable.Columns.Add("last Limit");
Construct.MainDataTable.Columns.Add("Data");
..........................
...............................................
DataRow oneRow = Construct.MainDataTable.NewRow();
DataRow twoRow = Construct.MainDataTable.NewRow();
dataGridView2.AllowUserToAddRows = false;
if (line.Split(',')[2].Equals("Time"))
{
time = line.Split(',')[3];
date = line.Split(',')[1];
}
if (line.Split(',')[2].Equals("Level"))
{
level = line.Split(',')[3];
}
//OneROw(IF condition)
if ((Convert.ToDecimal(line.Split(',')[8])) < (Convert.ToDecimal (line.Split(',')[12])))
{
type = line.Split(',')[1];
serial = line.Split(',')[7];
price = line.Split(',')[3];
Limit = line.Split(',')[8];
lastLimit = line.Split(',')[10];
Data = line.Split(',')[12];
oneRow["Date"] = date;
oneRow["Time"] = time;
oneRow["Serial"] = serial;
oneRow["Type"] = type;
oneRow["level"] = level;
oneRow["price"] = price;
oneRow[" Limit"] = Limit;
oneRow["last Limit"] = lastlimit;
oneRow["Data"] = Data;
Construct.MainDataTable.Rows.Add(oneRow);
}
//TwoROw(IF condition)
if ((line.Contains('"')) && ((line.Contains("NG"))))
{
price = line.Split(',')[3];
type = line.Split(',')[1];
serial = line.Split(',')[7];
Limit = line.Split('"')[7];
var valLimit = Limit.Split(',').Select(a => Convert.ToInt32(a, 16));
var limitJoin = String.Join(",", valLimit);
lastlimit = line.Split('"')[1];
var vallastLimit = lastlimit.Split(',').Select(d => Convert.ToInt32(d, 16));
var lastJoin = String.Join(",", vallastLimit);
Data = line.Split('"')[5];
var valDatas = Data.Split(',').Select(s => Convert.ToInt32(s, 16));
var dataJoin = String.Join(",", valDatas);
twoRow["Date"] = date;
twoRow["Time"] = time;
twoRow["Serial"] = serial;
twoRow["Type"] = type;
twoRow["level"] = level;
twoRow["price"] = price;
twoRow["Limit"] = limitJoin;
twoRow["last Limit"] = lastJoin;
twoRow["Data"] = dataJoin;
Construct.MainDataTable.Rows.Add(twoRow);
}
dataGridView2.DataSource = Construct.MainDataTable;
Can't add a comment because I don't have enough karma so I ask my questions here: So, if I understood your problem you can't add data from one .csv file if it have more then one row? Why are you using 2 different if conditions for row in .csv file?
If you have empty data in row never mind you can still place them to your DataTable column, so you can use loop to add data from .csv to your DataTable. Try some thing like this:
public static DataTable CsvToDataTable(string csv)
{
DataTable dt = new DataTable();
string[] lines = csv.Split(new[] { "\r\n", "\r", "\n" }, StringSplitOptions.RemoveEmptyEntries);
Regex onlyDeimiterComma = new Regex(",(?=(?:[^\"]*\"[^\"]*\")*(?![^\"]*\"))");
for (int i = 0; i < lines.Length; i++)
{
DataRow row = dt.NewRow();
string[] cells = onlyDeimiterComma.Split(lines[i]);
for (int j = 0; j < cells.Length; j++)
{
if (i == 0)
{
if (j == 0)
{
dt.Columns.Add(cells[j], typeof(DateTime));
}
else
{
dt.Columns.Add(cells[j]);
}
}
else
{
row[j] = cells[j];
}
}
dt.Rows.Add(row);
}
return dt;
}
Just call this method anywhere in your code and give it string read from your .csv file.
You can try to compile this code here and see how it works on .csv data with different data (empty columns, quoted text, quoted commas)
UPD: If you need to fill DataTable from two different .csv files you can still use code above. Just call it twice for both files and then Merge two DataTable, like this:
DataTable dt = CsvToDataTable(csvFileOne);
DataTable dtTwo = CsvToDataTable(csvFileTwo);
dt.Merge(dtTwo);
I'm trying to create a Pivot table using ClosedXML V0.91.1, but I keep getting problems with my excel file having unreadable content and then the excel workbook removing my pivot table when clicking Yes below.
Below is that shows when I hit Yes. It's removing my pivot table.
My Pivot Table is getting data from a table that is created from a history of TFS Changesets. The changesets are set into a IEnumerable<Changeset> which is then converted into a DataTable object which include the column headings.
A table is then created from the DataTable which is the source of the PivotTable. This is the code that I'm using:
public bool CreateReport(IEnumerable<Changeset> changesets)
{
workbook = new XLWorkbook();
var sumSheet= workbook.Worksheets.Add("Summary");
// Converting IEnumerable<Changeset> into DataTable
DataTable changesetTable = ConvertToDataTable(changesets);
// Table
var sumTable = sumSheet.Cell(1, 1).InsertTable(changesetTable.AsEnumerable(), "SummaryTable", true);
// Table - Formatting table
tableWithData.Column("A").Cells(firstRow, lastRow).DataType = XLDataType.Number;
tableWithData.Column("C").Cells(firstRow, lastRow).DataType = XLDataType.DateTime;
tableWithData.Column("C").Cells(firstRow, lastRow).Style.DateFormat.Format = "d-MMM-yyy";
sumSheet.Columns().AdjustToContents();
// Pivot Table
var header = sumTable.Range(1, 1, 1, 6); // A1 to F1
var range = sumTable.DataRange;
var dataRange = sumSheet.Range(header.FirstCell(), range.LastCell());
var pivotSheet = workbook.Worksheets.Add("History Report");
var pivotTable = pivotSheet.PivotTables.AddNew("PivotTable", pivotSheet.Cell(1, 1), dataRange);
// Pivot Table - Formatting table
pivotTable.ShowPropertiesInTooltips = false;
pivotTable.RepeatRowLabels = false;
pivotTable.ShowGrandTotalsColumns = false;
pivotTable.ShowGrandTotalsRows = false;
pivotTable.ShowEmptyItemsOnRows = true;
pivotTable.ShowEmptyItemsOnColumns = true;
pivotTable.ShowExpandCollapseButtons = false;
pivotTable.Layout = XLPivotLayout.Tabular;
pivotTable.RowLabels.Add("Changeset");
pivotTable.RowLabels.Add("Committer");
pivotTable.RowLabels.Add("Date");
pivotTable.RowLabels.Add("Comment");
pivotTable.RowLabels.Add("File Changes");
pivotTable.RowLabels.Add("Source");
// Go off and save the workbook.
bool saved = SaveFile();
return saved;
}
I believe the problem is with how I am selecting the dataRange for the source of the Pivot Table.
var header = sumTable.Range(1, 1, 1, 6); // A1 to F1
var range = sumTable.DataRange;
var dataRange = sumSheet.Range(header.FirstCell(), range.LastCell());
I followed the example found on their wiki, but it gives those errors with my implementation. The only difference between my problem and the example, is that I am getting my source for the Pivot Table from a DataTable, and I am only inserting values into RowLabels in my Pivot Table.
If it helps, this is how I convert the IEnumerable<Changeset> to a DataTable
private DataTable ConvertToDataTable(IEnumerable<Changeset> changesets)
{
DataTable table = new DataTable();
table.Columns.Add("Changeset", typeof(int));
table.Columns.Add("Committer", typeof(string));
table.Columns.Add("Date", typeof(DateTime));
table.Columns.Add("Comment", typeof(string));
table.Columns.Add("File Changes", typeof(string));
table.Columns.Add("Source", typeof(string));
foreach(Changeset changeset in changesets) // Loop over all changesets
{
int changesetID = changeset.ChangesetId;
string committer = changeset.CommitterDisplayName;
DateTime creationDate = changeset.CreationDate;
string comment = changeset.Comment;
foreach(Change change in changeset.Changes) // Loop over all Changes in changeset
{
string filename = change.Item.ServerItem.Substring(change.Item.ServerItem.LastIndexOf("/") + 1);
table.Rows.Add(changesetID, committer, creationDate, comment, filename, change.Item.ServerItem);
}
}
return table;
}
If I recall correctly, a pivot table in ClosedXML should have at least one value field.
pivotTable.Values.Add("somefield");
I know I am a bit late on this one, but in case anyone else tries to do this in future, my solution was as follows.
IXLPivotTable xlPvTable = TargetWorksheet.PivotTables.Add(
"PivotTable123",
TargetWorksheet.Cell(1, 1),
SourceWorksheet.Range(1, 1, MainData.Rows.Count, MainData.Columns.Count)
);
Then add the ColumnLabel and RowLabels etc..
I have a Janus GridEX and I want to add a DropDownList with images and text to a column. When I populate the ValueList of the column I pass a DataView as parameter which contain a DataTable structured in this way:
var dt = new DataTable("asd");
dt.Columns.Add("value");
dt.Columns.Add("text");
dt.Columns.Add("img", typeof(byte[]));
then I add a row which contains one row:
var row2 = dt.NewRow();
row2["value"] = 1;
row2["text"] = "A2";
row["img"] = GetBytesFromImage(resources.Icon1);
this is the GetBytesFromImage routine:
private byte[] GetBytesFromImage(Icon ico)
{
using(var ms = new MemoryStream())
{
ico.Save(ms);
return ms.ToArray()
}
}
then I populate the valuelist:
grid.......PopulateValueList(dataview, "value","text","img",Color.Red, new Size(16,16)
then I get the error. Someone know why?
I am trying to learn how to join two data tables into one using Linq. My linq query is working correctly and I can see expected values in it. However, when I loop the linq results, and assign the values to a newly created data row and add that row to a new data table, the rows come out empty.
Here is my code:
private void btnCombine_Click(object sender, EventArgs e)
{
var innerJoinQuery =
from strRow in StrDataTable.AsEnumerable()
join intRow in IntDataTable.AsEnumerable()
on strRow.Field<int>("IntID") equals intRow.Field<int>("ID")
select new {
IntOne = intRow.Field<int>("FirstNum"),
IntTwo = intRow.Field<int>("SecondNum"),
StrOne = strRow.Field<string>("FirstStr"),
StrTwo = strRow.Field<string>("SecondStr"),
StrThree = strRow.Field<string>("SecondStr")
};
DataTable newTable = new DataTable();
newTable.Columns.Add("IntOne");
newTable.Columns.Add("IntTwo");
newTable.Columns.Add("FirstStr");
newTable.Columns.Add("SecondStr");
newTable.Columns.Add("ThirdStr");
newTable.Columns["IntOne"].DataType = System.Type.GetType("System.String");
newTable.Columns["IntTwo"].DataType = System.Type.GetType("System.String");
newTable.Columns["FirstStr"].DataType = System.Type.GetType("System.String");
newTable.Columns["SecondStr"].DataType = System.Type.GetType("System.String");
newTable.Columns["ThirdStr"].DataType = System.Type.GetType("System.String");
foreach (var row in innerJoinQuery)
{
DataRow rowToAdd = newTable.NewRow();
rowToAdd.ItemArray[0] = row.IntOne.ToString();
rowToAdd.ItemArray[1] = row.IntTwo.ToString();
rowToAdd.ItemArray[2] = row.StrOne.ToString();
rowToAdd.ItemArray[3] = row.StrTwo.ToString();
rowToAdd.ItemArray[4] = row.StrThree.ToString();
newTable.Rows.Add(rowToAdd);
}
dataGridView3.DataSource = newTable;
}
Using DataRow.ItemArray property with individual values doesn't work - instead, create the object[] array and then set the whole thing to the .ItemArray property. See this MSDN page for additional examples.
foreach (var row in innerJoinQuery)
{
DataRow rowToAdd = newTable.NewRow();
object[] items = new object[] {
row.IntOne.ToString(),
row.IntTwo.ToString(),
row.StrOne.ToString(),
row.StrTwo.ToString(),
row.StrThree.ToString()
};
rowToAdd.ItemArray = items;
newTable.Rows.Add(rowToAdd);
}
Alternately, use the DataRow indexer directly, which works with individual columns:
rowToAdd[0] = row.IntOne.ToString();
rowToAdd[1] = row.IntTwo.ToString();
rowToAdd[2] = row.StrOne.ToString();
rowToAdd[3] = row.StrTwo.ToString();
rowToAdd[4] = row.StrThree.ToString();
Additionally, when creating columns, there is a constructor that takes the type which can save you some code. Your first two column types are mismatched.
newTable.Columns.Add("IntOne", typeof(int));
newTable.Columns.Add("FirstStr", typeof(string));
The first two values appear to be Integers:
IntOne = intRow.Field<int>("FirstNum"),
IntTwo = intRow.Field<int>("SecondNum"),
But the DataType you assign the columns to is String:
newTable.Columns["IntOne"].DataType = System.Type.GetType("System.String");
newTable.Columns["IntTwo"].DataType = System.Type.GetType("System.String");
Update those to int's and see if that resolves it:
newTable.Columns["IntOne"].DataType = System.Type.GetType("System.Int32");
newTable.Columns["IntTwo"].DataType = System.Type.GetType("System.Int32");
rowToAdd.ItemArray[0] = row.IntOne;
rowToAdd.ItemArray[1] = row.IntTwo;
You may also need to supply the DataPropertyName for the columns:
newTable.Columns["IntOne"].DataPropertyName = "FirstNum";
newTable.Columns["IntTwo"].DataPropertyName = "SecondNum";
...
And ensure that the AutoGenerateColumns value is set to false
dataGridView3.AutoGenerateColumns = false;
In my xml file,it has many elements and many child/sub child elements are there so i have decided to load as generic list and display in the DGView and the columns are already created/customed in DGview.
I have to edit the values in the datagridview and serialize back to the file. I would like to know,
how can i get the values from the datagrid view and serialize back to the file.
I tried using this, Dataset ds = new Dataset();ds = (Dataset) (dataGridView2.Datasource);ds.WriteXml("XML_File.xml"); i got a error message, nullRefExceptionError.
As I know the DataSet ds is null, thats why I'm getting this error.
I don't want to use the dataset for binding.I want to bind the xml file directly to the datagridview. IS it possible with my approach???
This approach is good but it's not saving the xml file as like the original xml file:
DataTable dt = new DataTable("Rules");
for (int i = 0; i < dataGridView4.ColumnCount; i++)
{
dt.Columns.Add(dataGridView4.Columns[i].Name, typeof(System.String));
}
DataRow myrow;
int icols = dataGridView4.Columns.Count;
foreach (DataGridViewRow drow in this.dataGridView4.Rows)
{
myrow = dt.NewRow();
for (int i = 0; i <= icols - 1; i++)
{
myrow[i] = drow.Cells[i].Value;
}
dt.Rows.Add(myrow);
}
dt.WriteXml(#"C:\test\items.xml");
Any help for me to serilaize/write the values from datagridview.
I have adapted this approach for my problem & it works.
List<Test>laneConfigs = new List<Test>();//From a class
foreach (DataGridViewRow dr in dataGridView1.Rows)
{
int bbbBorder = 0;
Int32.TryParse(dr.Cells["BBor"].Value.ToString(), out bbbBorder );
int eeee= 0;
Int32.TryParse(dr.Cells["EBor"].Value.ToString(), out eee);
LaneConfig laneConfig = new LaneConfig(
dr.Cells["ID"].Value.ToString(),
(TrafficLaneType)Enum.Parse(typeof(TrafficLaneType), dr.Cells["Type"].Value.ToString()),
new ValueWithUnit<int>(bbbBorder, "mm"),
new ValueWithUnit<int>(eee, "mm"));
laneConfigs.Add(llaneConfig);
}