Displaying DataTable containing DB tables names - c#

I've been trying to get an access tables names in c#, using:
m_cnADONewConnection.ConnectionString = "Provider=Microsoft.Jet.OLEDB.4.0;Data
Source=test.mdb";
m_cnADONewConnection.Open();
DataTable userTables = m_cnADONewConnection.GetSchema("Tables");
But don't know how to show only the tables names...any help?

// Add list of table names to string list
List<string> names = new List<string>();
for (int i=0; i < userTables.Rows.Count; i++)
names.Add(userTables.Rows[i][2].ToString());
I took this from a similar question.

Related

How to query table structures from an access database?

I want to get the structure of all the tables and odbc-Datasources in an Access database with C#. So I tried this code:
string text="";
var tables = GetApp().CurrentData.AllTables;
for (int i = 0; i < tables.Count; i++)
{
var currentTable = tables.Item(i);
text = text + currentTable.FullName + Environment.NewLine;
}
MessageBox.Show(text);
This returns all the availible tablenames. But how do I get the columnnamens and types of the tables?
I tried this:
var props = currentTable.Properties;
for (int j = 0; j < props.Count; j++)
{
var prop = props.Item(j);
text = text + Environment.NewLine + prop.Name;
}
but it didnt work (An exception was thrown when I accessed the properties).
I tried to use a oleDB connection + GetSchema to get the table structure. But with this method I only received the "native" (or local) tables inside of the access-db. But there are also some ODBC-Linked-Tables which I am also interested.
So how is it possible to get the TableNames, ColumnNames and Columntypes in an ms-access database file?
You need to use CurrentDb().TableDefs if you want to access table columns. The AllTables collection doesn't offer access to the table fields.
CurrentDb().TableDefs[0].Fields[0].Name should return the name of the first column of the first table, for example.

C# Doughnut to datatable

In my MySQL database I have a table with customers, two columns are named HoursUsed & HoursAvailable. With an SQL query I get the selected customer and fill it in a datatable.
Now I want to display in the dougnut chart the HoursUsed & HoursAvailable but it fills up the whole chart with 100% instead of 2 pieces.
How can I achieve this, First I created only one Series, then I tried to add another one but I get the same result.
I tried the following code:
chartHoursCustomer.DataSource = WorkData; //Datatable
chartHoursCustomer.Series["HoursAvailable"].YValueMembers = "HoursAvailable";
chartHoursCustomer.Series["HoursUsed "].XValueMembers = "HoursUsed ";
chartHoursCustomer.DataBind();
Datatable: (Only 1 row because my SQL query is Select * FROM Customers WHERE ID = CustomerID)
HoursAvailable HoursUsed
50 44
Try this:
int ColumnCount = WorkData.Columns.Count;
string[] XPointMember = new string[ColumnCount];
int[] YPointMember = new int[ColumnCount];
for(int cnt = 0; cnt < ColumnCount; cnt++)
{
// This is assuming that you actually retrieve one row.
XPointMember[cnt] = WorkData.Rows[0][cnt].ToString();
YPointMember[cnt] = Convert.ToInt32(WorkData.Rows[0][cnt]);
}
Chart1.Series[0].Points.DataBindXY(XPointMember, YPointMember);

Merging DataTables with Condition

I would like to merge DataTables in a list using sum or average depending on conditions. For example:
private DataTable getData(List<DataTable> datas, string[] KeyColumnNames, string valueCol)
{
List<DataTable> dataTables = datas;
//if datas has 3 dataTables in it : dt1, dt2, dt3
// then I want to create another dataTable dtAll which will have the sum of
// valueCol of all three datatables for the row which will be conditioned using
// KeyColumnNames (can be multiple Primary keys)
return dataTable;
}
Consider all datatables to be exactly same but different values as they are tables from similar schemas but different data centers.
Thanks.
I would do
List<DataTable> dataTableList = dtList;
DataTable unionDataTable = new DataTable();
for(int i = 0; i < dtList.Count; i++)
unionDataTable = Union(unionDataTable, dtList[i], "UnionDataTable");
where the Union method is defined by something like the following
public static DataTable Union(DataTable First, DataTable Second, string strReturnedTableName)
{
// Result table.
DataTable table = new DataTable(strReturnedTableName);
// Build new columns.
DataColumn[] newcolumns = new DataColumn[First.Columns.Count];
for (int i = 0; i < First.Columns.Count; i++)
newcolumns[i] = new DataColumn(First.Columns[i].ColumnName, First.Columns[i].DataType);
// Add new columns to result table.
table.Columns.AddRange(newcolumns);
table.BeginLoadData();
// Load data from first table.
foreach (DataRow row in First.Rows)
table.LoadDataRow(row.ItemArray, true);
// Load data from second table.
foreach (DataRow row in Second.Rows)
table.LoadDataRow(row.ItemArray, true);
table.EndLoadData();
return table;
}
I hope this helps.
Edit. You can pass an Action in to the method and use this in the foreach blocks to do what you want.
Your question is way too vague to provide any actual code but you want to do a LINQ Join. It works about the same as a SQL join. This question shows joins in both query and method syntax How to do a join in linq to sql with method syntax? also you can look at the msdn docs here; http://msdn.microsoft.com/en-us/library/bb311040.aspx

How to insert multiple datatable data into one datatable c#

I have a function which will return multiple ItemIDs as
for (int i = 0; i < dt.Rows.Count; i++)
{
ItemID = int.Parse(dt.Rows[i]["item_Id"].ToString());
dtAtlr = prodctsDCCls.getItemIds(ItemID);
//dtItems = dtAtlr.Copy();
}
I want to keep on searching for all ItemIds from the same table and have to save all the data in one datatable.If I copy one datatable to another datatable, that is replacing the previous datatable. but I need all the data. Please anybody help me
Use DataTable.Merge to merge two data tables. So your code would be:
for (int i = 0; i < dt.Rows.Count; i++)
{
ItemID = int.Parse(dt.Rows[i]["item_Id"].ToString());
dtAtlr.Merge(prodctsDCCls.getItemIds(ItemID)); // For Merging
}
By using DataTable.Copy, your datatable dtAtlr will have the last returned DataTable against the ItemID
You can check DataTable.Merge
Merge the specified DataTable with the current DataTable.

making rows distinct and showing all the columns

In my project there are two datatables dtFail and dtFailed (dtFailed has nothing but column names declarations). dtFail has duplicate "EmployeeName" column values. so i took a dataview dvFail and did the process to make them distinct as shown in the below code:
dtFail
I tried the below code:
DataView dvFail = new DataView(dtFail);
dtFail = dvFail.ToTable(true, "EmployeeName"); //showing only one column in dtFail
dtFailed (only one column)
If i do like below
DataView dvFail = new DataView(dtFail);
dtFail = dvFail.ToTable(true, "EmployeeName","EmployeeRole","Status");
dtFailed (showing but with duplicate rows)
Then the datatable dtFailed is storing duplicate "EmployeeName" also.
Please Help
Thanks in Advance.
Try this query-
DataTable distinctTable = originalTable.DefaultView.ToTable( /*distinct*/ true);
For more info hit below link-
https://social.msdn.microsoft.com/Forums/en-US/ed9c6a6a-a93e-4bf5-a892-d8471b84aa3b/distinct-in-datatable-or-dataview?forum=adodotnetdataset
I hope this would have helped you.
SOLUTION 1:
Based on the question my understanding is, we need to consider duplicates based on EmployeeName and we need not worry about other columns. If that is the case below solution works better.
foreach(DataRow r in dtFail.AsEnumerable())
{
if (!dt1.AsEnumerable().Any(r1 => r1["EmployeeName"] == r["EmployeeName"]))
{
// if you don't want to copy entire row create new DataRow
// with required fields and add that row.
dt1.Rows.Add(r.ItemArray);
}
}
if you want you can put dt1 back to dtFail.
SOLUTION 2:
If we need to consider distinct rows I prefer below solution.
var temp = dtFail.AsEnumerable().Distinct();
dtFail = temp.CopyToDataTable();
I'm not sure it will be helpful or not. As far as I get from your question that you want EmployeeName to be distinct irrelevant to other columns. But if you do ToTable and turn on the distinct flag it will give all the distinct rows, doesn't matter how many columns are involved there. So if you mention only EmployeeName it will obviously give you distinct EmployeeNames, not all the columns associated with it.
So, thats what I did, initially select only the distinct EmployeeName columns and put it into a temp DataTable dtt.
DataTable dtt = dvFail.DefaultView.ToTable(true, "EmployeeName");
Secondly I've created another temp DataTable where we put the segregated rows from the main DataTable dtFail and set the column names manually.
DataTable TempDataTable = new DataTable();
DataTable dtFailed = new DataTable();
Prepare the columns in the dtFailed DataTable.
if (dtFailed.Columns.Count == 0)
{
dtFailed.Columns.Add("EmployeeName");
dtFailed.Columns.Add("EmployeeRole");
dtFailed.Columns.Add("Status");
dtFailed.Columns.Add("Date");
}
Loop through the distinct EmployeeName dtt DataTable and match the EmployeeName and keep that selected first row in the TempDataTable. Finally all rows transferred into the dtFailed.
for (int j = 0; j < dtt.Rows.Count; j++)
{
string EmployeeName = dtt.Rows[j]["EmployeeName"].ToString();
TempDataTable = dvFail.Select("EmployeeName = " + EmployeeName).CopyToDataTable();
dtFailed.Rows.Add(TempDataTable.Rows[0].ItemArray);
}

Categories

Resources