I am trying to convert an array of strings to a DataGridView with little success so far. The method below is called for that purpose, but it doesn't seem to return any table.
While debugging I can see that I fetch the correct values from cont.GetAllEmployee() but when the debug goes to ConvertListToDataTable(list) the debugging does not show that method which is something unusual.
This is my current code :
private DataTable ConvertListToDataTable(List<WindowsFormsApplication1.ServiceReference1.ArrayOfString> list)
{
DataTable table = new DataTable();
List<string> columnNames = list[0];
for (int i = 0; i < columnNames.Count; i++)
{
table.Columns.Add(columnNames[i].ToString());
}
foreach (var array in list)
{
table.Rows.Add(array);
}
return table;
}
List <WindowsFormsApplication1.ServiceReference1.ArrayOfString> list = cont.GetAllEmployee();
dataGridView.DataSource = ConvertListToDataTable(list);
New rows must be instanciated by DataTable.NewRow() method to obtain new DataRow with the same scheme as DataTable.
private DataTable ConvertListToDataTable(List<WindowsFormsApplication1.ServiceReference1.ArrayOfString> list)
{
DataTable table = new DataTable();
List<string> columnNames = list[0];
for (int i = 0; i < columnNames.Count; i++)
{
table.Columns.Add(columnNames[i].ToString());
}
foreach (var array in list)
{
var NewRow = table.NewRow();
for(int i = 0; i < columnNames.Count)
{
NewRow[columnNames[i]] = array[i];
}
table.Rows.Add(NewRow);
}
return table;
}
List <WindowsFormsApplication1.ServiceReference1.ArrayOfString> list = cont.GetAllEmployee();
dataGridView.DataSource = ConvertListToDataTable(list);
dataGridView.DataBind();
Related
I am new to C# programming and topic of operating with jagged array.
I have some data stored in my string[][] arrayname and want to show it in datagridview.
Will be very grateful if you could advice me on the case.
You need to create dataset, usually I use a DataTable, I have drafted a solution to your problem, but you have to using Linq:
var ListName = arrayname.ToList();
//get number of column, probalby you dont need it
int cols = ListName.Select(r => r.Length).Max();
//Create a datasource
DataTable dt = new DataTable();
//Write column, probalby you dont need it
for (int f = 0; f < cols; f++)
dt.Columns.Add("Col " + (f+1));
foreach (var row in ListName) {
//make a row
List<string> Lrow = new List<string>();
Lrow.AddRange(row);
//if row is too short add fields
if (Lrow.Count < cols)
for (int i = Lrow.Count; i < dt.Columns.Count; i++) {
Lrow.Add("");
}
//at last add row to dataTable
dt.Rows.Add(Lrow.ToArray());
}
//and set dataGridView's DataSource to DataTable
dataGridView1.DataSource = dt;
The result should be this
I'm facing a strange issue where I'm assigning a List of Strings to a GridViewData but instead of showing me the list of string, GridViewData is showing numbers.
Code is as following:
private void ShowListofObjects()
{
dgvShowObjects.DataSource = showObjects(dtMenu, dtAllActiveUsersAccessRights);
}
private List<string> showObjects(DataTable dtMenu, DataTable dtAllActiveUsersAccessRights)
{
DataTable dtFinalTable = new DataTable();
dtFinalTable.Columns.Add("Object", typeof(String));
dtFinalTable.Columns.Add("Add", typeof(String));
dtFinalTable.Columns.Add("View", typeof(String));
dtFinalTable.Columns.Add("Modify", typeof(String));
List<string> l = new List<string>();
int counter = 0;
for (int i = 0; i < dtMenu.Rows.Count; i++)
{
string obj = dtMenu.Rows[i][1].ToString(); // first item in Menu Table
for (int j = 0; j < dtAllActiveUsersAccessRights.Rows.Count; j++)
{
string s = dtAllActiveUsersAccessRights.Rows[j][1].ToString();
if (s == obj)
{
l.Add(dtAllActiveUsersAccessRights.Rows[j][1].ToString());
counter++;
}
}
}
lblCounter.Text = counter.ToString();
return l;
}
On debugging, on line return l; I can see List l populated with string values but when I'm assigning this list to GridViewData on line dgvShowObjects.DataSource = showObjects(dtMenu, dtAllActiveUsersAccessRights); and run the application, its showing a list of numbers.
Can anyone see why?
Thanks in advance.
In the code below, i'm returning data that will have a variable number of columns.
So it could return columns 'a,b,c,d,e' or it could return columns 'a,b,c,g,m,n' - the first three columns are set, but then there could be any number of additional columns. I then need to return the data as an anonymous type list. In the code below, i'm showing how i get the data, pivot it, and add the columns into ArrayList objDataColumn , and then create a datatable, which does get me close, but i'm not able to figure out how to return the data as a list.
Instead of having it return a list of datatable rows, i'd like to have it return a generic list of anonymous type like the following (in this case 'Attribute' is the only dynamic column):
{ EntitlementId = 477653184, FileSetTypeID = 146, FileTypeCode = "test", SourceSystemKey = "userkey", Entitlement = "Chg Mgrs - AppDev Sour GUI", Attribute = "Change Manager" }
////Applying linq for geting pivot output
var d = (from f in result
group f by new { f.EntitlementId, f.FileSetTypeID, f.FileTypeCode, f.SourceSystemKey, f.Entitlement }
into myGroup
where myGroup.Count() > 0
select new
{
myGroup.Key.EntitlementId,
myGroup.Key.FileSetTypeID,
myGroup.Key.FileTypeCode,
myGroup.Key.SourceSystemKey,
myGroup.Key.Entitlement,
ColumnName = myGroup.GroupBy(f => f.ColumnName).Select(m => new { Col = m.Key, Value = m.Max(c => c.Value) })
}).ToList();
//PART 2 - Distinct ColumnName
var cols = (
from a in result
select new { ColumnName = a.ColumnName }
).Distinct().ToList();
//PART 3 - Creating array for adding dynamic columns
ArrayList objDataColumn = new ArrayList();
//Fixed columns
objDataColumn.Add("FileTypeCode");
objDataColumn.Add("SourceSystemKey");
objDataColumn.Add("Entitlement");
//Add Subject Name as column in Datatable
for (int i = 0; i < cols.Count; i++)
{
objDataColumn.Add(cols[i].ColumnName);
}
//Add dynamic columns name to datatable dt
DataTable dt = new DataTable();
for (int i = 0; i < objDataColumn.Count; i++)
{
dt.Columns.Add(objDataColumn[i].ToString());
}
//PART 4 - Add data into datatable with respect to dynamic columns and dynamic data
for (int i = 0; i < d.Count; i++)
{
List<string> tempList = new List<string>();
tempList.Add(result[i].FileTypeCode.ToString());
tempList.Add(result[i].SourceSystemKey.ToString());
tempList.Add(result[i].Entitlement.ToString());
var res = d[i].ColumnName.ToList();
for (int j = 0; j < res.Count; j++)
{
tempList.Add(res[j].Value.ToString());
}
dt.Rows.Add(tempList.ToArray<string>());
}
//END PIVOT
IEnumerable<DataRow> rows = dt.AsEnumerable();
Thanks in advance, let me know if any additional info is needed, hope this isnt too confusing.
Was able to solve this using a dynamic list and the ExpandoObject class.
Here's the code, hope it helps someone else:
List<dynamic> dynList = new List<dynamic>();
for (int i = 0; i < d.Count; i++)
{
dynamic dynObj = new ExpandoObject();
((IDictionary<string, object>)dynObj).Add("FileTypeCode", result[i].FileTypeCode.ToString());
((IDictionary<string, object>)dynObj).Add("Fullname", result[i].Fullname.ToString());
((IDictionary<string, object>)dynObj).Add("Entitlement", result[i].Entitlement.ToString());
var res = d[i].ColumnName.ToList();
for (int j = 0; j < res.Count; j++)
{
((IDictionary<string, object>)dynObj).Add(res[j].Col.ToString(), res[j].Value.ToString());
}
dynList.Add(dynObj);
}
var dList = (from da in dynList select da).ToList();
return dList;
ds.Tables.Add(dt);
return ds;
In the above code snippet, how can i return my dataset but exclude all blank rows i.e blank meaning rows with null or an empty string in all their columns.
You will have to do that checking before hand and then return the DataTable something like below (an example)
for (int i = dt.Rows.Count - 1; i >= 0; i--)
{
if (dt.Rows[i]["col1"] == DBNull.Value && dt.Rows[i]["col2"] == DBNull.Value)
{
dt.Rows[i].Delete();
}
}
dt.AcceptChanges();
ds.Tables.Add(dt);
return ds;
In case anyone stumbles across this article, this is the solution I came up with:
// REMOVE ALL EMPTY ROWS
dt_Parsed.Rows.Cast<DataRow>().ToList().FindAll(Row =>
{ return String.IsNullOrEmpty(String.Join("", Row.ItemArray)); }).ForEach(Row =>
{ dt_Parsed.Rows.Remove(Row); });
Here had helper function in which pass your table that you want to delete datarow with all empty columns(Here I assumed all string are of type string then it will work)
For other type u can check datacolumn type and then can make relavant checking.
public DataTable DeleteEmptyRows(DataTable dt)
{
DataTable formattedTable = dt.Copy();
List<DataRow> drList = new List<DataRow>();
foreach (DataRow dr in formattedTable.Rows)
{
int count = dr.ItemArray.Length;
int nullcounter=0;
for (int i = 0; i < dr.ItemArray.Length; i++)
{
if (dr.ItemArray[i] == null || string.IsNullOrEmpty(Convert.ToString(dr.ItemArray[i])))
{
nullcounter++;
}
}
if (nullcounter == count)
{
drList.Add(dr);
}
}
for (int i = 0; i < drList.Count; i++)
{
formattedTable.Rows.Remove(drList[i]);
}
formattedTable.AcceptChanges();
return formattedTable;
}
You can try to loop the DataTables in DataSet with this method:
public void Clear_DataTableEmptyRows(DataTable dataTableControl)
{
for (int i = dataTableControl.Rows.Count - 1; i >= 0; i--)
{
DataRow currentRow = dataTableControl.Rows[i];
foreach (var colValue in currentRow.ItemArray)
{
if (!string.IsNullOrEmpty(colValue.ToString()))
break;
dataTableControl.Rows[i].Delete();
break;
}
}
}
I have a datatable containing over 100 columns, how ever I need to strip out all columns
except first 11 columns.
I need to retain data of 1st 11 columns.
I am doing it with following code
public DataTable validdatatable(DataTable table)
{
DataTable dt = new DataTable();
for (int i = 0; i < 11; i++)
{
DataColumn dc = new DataColumn();
dc.ColumnName = table.Columns[i].ColumnName;
dc.DataType = table.Columns[i].DataType;
dt.Columns.Add(dc);
}
for (int i = 0; i < table.Rows.Count; i++)
{
object[] ob = table.Rows[i].ItemArray;
...
...
}
return dt;
}
This methods works but is too heavy on CPU and Ram.
Is there any other method with which I can proceed?
Try this:
public DataTable validdatatable(DataTable table)
{
var dt = table.Columns.Cast<DataColumn>().Take(11);
return dt.CopyToDataTable();
}
Or Something like this. It will give you at least a way to work on it.
Note that You need to add a reference to the assembly: System.Data.DataSetExtensions.dll then you can write your function like above.
You can try this. The only difference would be instead of object[] ob = table.Rows[i].ItemArray it will just grab the first 11 columns using the index and make an array out of that (itemArray will make an array of all 100 columns). Still doubt this will solve your memory issues if you are that tight but it's probably worth a shot.
var copyDt = new DataTable();
for (var i = 0; i < 11; i++)
{
copyDt.Columns.Add(dataTable.Columns[i].ColumnName, dataTable.Columns[1].DataType);
}
copyDt.BeginLoadData();
foreach (DataRow dr in dataTable.Rows)
{
copyDt.Rows.Add(Enumerable.Range(0, 11).Select(i => dr[i]).ToArray());
}
copyDt.EndLoadData();