我已经声明了2个字符串变量:
string fname;
string lname;
当我在phpMyAdmin数据库中编写MySQL查询时:
SELECT workers.FNAME, workers.LNAME FROM project1.workers INNER JOIN
project1.order_status ON workers.ID_WORKER = order_status.ID_WORKER
INNER JOIN project1.orders ON orders.ID_ORDER = order_status.ID_ORDER
WHERE orders.ORDER_NUMBER = 'TEST' GROUP BY workers.FNAME, workers.LNAME
我有2位工作人员:
-“亚当·加克斯”和
“安德鲁·沃尔姆(Andrew Worm)”
然后,我想存储此查询中的对象并将该数据加载到datagridview:
string query1 = string.Format("SELECT workers.FNAME, workers.LNAME FROM project1.workers INNER JOIN project1.order_status " +
"ON workers.ID_WORKER = order_status.ID_WORKER INNER JOIN project1.orders ON orders.ID_ORDER = order_status.ID_ORDER " +
"WHERE orders.ORDER_NUMBER = '"+ NrOrder +"' GROUP BY workers.FNAME, workers.LNAME");
SQLdata.connection.Open();
using (var command = new MySqlCommand(query1, SQLdata.connection))
{
using (var reader1 = command.ExecuteReader())
{
while (reader1.Read())
{
fname = Convert.ToString(reader1[0]);
lname = Convert.ToString(reader1[1]);
}
}
}
我在while循环中使用了代码行中的断点,并读取了所有FNAME和LNAME。然后,它将正确加载所有数据。接下来,我要将它们加载到datagridview。
SQLdata.connection.Close();
sick_leaves x = new sick_leaves();
x.FNAME = fname;
x.LNAME = lname;
return x;
并像这样绑定它们:
sick_leaves a = calculate_sickness_leaves(txt_NrOrder.Text);
cu = calculate_sickness_leaves(txt_NrOrder.Text);
var source = new BindingSource();
source.DataSource = cu;
dataGridView2.DataSource = source;
然后使用Orders.cs文件中的数据:
public class sick_leaves
{
public string FNAME { get; set; }
public string LNAME { get; set; }
}
在datagridview中编译之后,我仅加载了1个Worker:“ Andrew Worm”。那应该是2个工作程序,所以它没有从sql查询中加载所有数据。
现在:如何将所有数据从sql查询加载到datagridview?有任何想法吗? 警告!我需要桌面应用程序方面的帮助
我的代码:
GenerateOrder.cs:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using MySql.Data.MySqlClient;
using System.Windows.Forms.DataVisualization.Charting;
using iTextSharp.text;
using iTextSharp.text.pdf;
using System.IO;
using System.Diagnostics;
namespace ControlDataBase
{
public partial class GenerateChartsOfOrders : Form
{
string fname;
string lname;
sick_leaves cu = new sick_leaves();
public GenerateChartsOfOrders()
{
InitializeComponent();
}
public void loaddata2()
{
string connect = "datasource=localhost;port=3306;username=root;password=";
MySqlConnection connection = new MySqlConnection(connect);
connection.Open();
sick_leaves a = calculate_sickness_leaves(txt_NrOrder.Text);
cu = calculate_sickness_leaves(txt_NrOrder.Text);
var source = new BindingSource();
source.DataSource = cu;
dataGridView2.DataSource = source;
connection.Close();
}
private sick_leaves calculate_sickness_leaves(string NrOrder)
{
string query1 = string.Format("SELECT workers.FNAME, workers.LNAME FROM project1.workers INNER JOIN project1.order_status " +
"ON workers.ID_WORKER = order_status.ID_WORKER INNER JOIN project1.orders ON orders.ID_ORDER = order_status.ID_ORDER " +
"WHERE orders.ORDER_NUMBER = '"+ NrOrder +"' GROUP BY workers.FNAME, workers.LNAME");
SQLdata.connection.Open();
using (var command = new MySqlCommand(query1, SQLdata.connection))
{
using (var reader1 = command.ExecuteReader())
{
while (reader1.Read())
{
fname = Convert.ToString(reader1[0]);
lname = Convert.ToString(reader1[1]);
}
}
}
SQLdata.connection.Close();
sick_leaves x = new sick_leaves();
x.FNAME = fname;
x.LNAME = lname;
return x;
}
}
}
Orders.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ControlDataBase
{
public class sick_leaves
{
public string FNAME { get; set; }
public string LNAME { get; set; }
}
}
SQLData.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using MySql;
using MySql.Data.MySqlClient;
namespace ControlDataBase
{
class SQLdata
{
public static MySqlConnection connection = new MySqlConnection
("datasource=localhost;port=3306;username=root;password=");
}
}
答案 0 :(得分:7)
代码中存在一些问题:
fname
和lname
定义为表单字段。 calculate_sickness_leaves
中,您可以在while(reader1.Read())
中设置这些字段的值sick_leaves
返回一个calculate_sickness_leaves
对象。因此,基本上fname
和lname
将始终包含表的最后一行的名字和姓氏,因为1和2。
由于3,您的DataGridView
将始终显示一条记录。
要解决此问题:
fname
和lname
,因为您不需要它们。calculate_sickness_leaves
的输出类型更改为IEnumerable<sick_leaves>
。sick_leaves
yield的新实例。旁注
using
语句。示例
您可以找到许多有关将数据加载到DataTable
或使用DataReader
的示例。无论如何,我将在这里再分享两个示例,向您展示如何从MySql获取数据并将其转换为特定类型的列表。
在以下示例中,我假设您有一个Employee
类,如下所示:
public class Employee
{
public string FirstName { get; set; }
public string LastName { get; set; }
}
示例1-使用DataAdapter,DataTable和Select扩展方法
public IEnumerable<Employee> GetEmployees()
{
string connectionString = "CONNECTION STRING";
string commandText = "COMMAND TEXT";
DataTable table = new DataTable();
using (var adapter = new MySqlDataAdapter(commandText , connectionString))
adapter.Fill(table);
return table.AsEnumerable().Select(x => new Employee()
{
FirstName = x.Field<string>("FirstName"),
LastName = x.Field<string>("LastName")
});
}
示例2-使用DataReader并产生新雇员的回报
public IEnumerable<Employee> GetEmployees()
{
string connectionString = "CONNECTION STRING";
string commandText = "COMMAND TEXT";
using (var connection = new MySqlConnection(connectionString))
{
connection.Open();
using (var command = new MySqlCommand(commandText, connection))
{
using (var reader = command.ExecuteReader())
{
while (reader.Read())
{
yield return new Employee()
{
FirstName = reader.GetFieldValue<string>(0),
LastName = reader.GetFieldValue<string>(1)
};
}
}
}
}
}
您可以使用上述任一方法:
bindingSource.DataSource = GetEmployees();
dataGridView.DataSource = bindingSource;
答案 1 :(得分:0)
当从SQL数据库下载数据并在DataGridView中对其进行预置时,此代码对我有用:
string connectionString;
String sql = "";
SqlConnection cnn;
sql = "SELECT workers.FNAME, workers.LNAME FROM project1.workers INNER JOIN project1.order_status " +
"ON workers.ID_WORKER = order_status.ID_WORKER INNER JOIN project1.orders ON orders.ID_ORDER = order_status.ID_ORDER " +
"WHERE orders.ORDER_NUMBER = '"+ NrOrder +"' GROUP BY workers.FNAME, workers.LNAME"";
connectionString = @"datasource=localhost;port=3306;username=root;password=";
cnn = new SqlConnection(connectionString);
cnn.Open();
SqlDataAdapter dataadapter = new SqlDataAdapter(sql, cnn);
DataSet ds = new DataSet();
dataadapter.Fill(ds, "workers");
dataGridView1.DataSource = ds;
dataGridView1.DataMember = "workers";
cnn.Close();
答案 2 :(得分:0)
这可能有帮助
private void GetData(string selectCommand)
{
try
{
// Specify a connection string.
// Replace <SQL Server> with the SQL Server for your Northwind sample database.
// Replace "Integrated Security=True" with user login information if necessary.
String connectionString =
"Data Source=<SQL Server>;Initial Catalog=Northwind;" +
"Integrated Security=True";
// Create a new data adapter based on the specified query.
dataAdapter = new SqlDataAdapter(selectCommand, connectionString);
// Create a command builder to generate SQL update, insert, and
// delete commands based on selectCommand.
SqlCommandBuilder commandBuilder = new SqlCommandBuilder(dataAdapter);
// Populate a new data table and bind it to the BindingSource.
DataTable table = new DataTable
{
Locale = CultureInfo.InvariantCulture
};
dataAdapter.Fill(table);
bindingSource1.DataSource = table;
// Resize the DataGridView columns to fit the newly loaded content.
dataGridView1.AutoResizeColumns(
DataGridViewAutoSizeColumnsMode.AllCellsExceptHeader);
}
catch (SqlException)
{
MessageBox.Show("To run this example, replace the value of the " +
"connectionString variable with a connection string that is " +
"valid for your system.");
}
}
答案 3 :(得分:0)
C#数据访问层(此示例中DAl.cs中只有1个子对象的简化示例):
Using System.Data.SqlClient;
Public Class DAL
{
Public Static void GetQueryResults(String cmdText)
{
SqlConnection oConn = New SqlConnection();
oConn.ConnectionString = MainW.MyConnection; // get connection string
SqlCommand cmd = New SqlCommand(cmdText, oConn);
DataSet ds = New DataSet();
SqlDataAdapter da = New SqlDataAdapter(cmd);
Try
{
oConn.Open();
da.Fill(ds); // retrive data
oConn.Close();
}
Catch (Exception ex)
{
SysErrScreen errform = New SysErrScreen();
errform.ChybaText.Text = ex.Message + Constants.vbCrLf + Constants.vbCrLf + cmdText;
errform.ShowDialog();
oConn.Close();
}
Return ds;
}
}
与VB.NET中的相同:
Imports System.Data.SqlClient
Public Class DAL
Public Shared Function GetQueryResults(cmdText As String)
Dim oConn As New SqlConnection
oConn.ConnectionString = MainW.MyConnection ' get connection string
Dim cmd As New SqlCommand(cmdText, oConn)
Dim ds As New DataSet()
Dim da As New SqlDataAdapter(cmd)
Try
oConn.Open()
da.Fill(ds) ' retrive data
oConn.Close()
Catch ex As Exception
Dim errform As New SysErrScreen
errform.ChybaText.Text = ex.Message & vbCrLf & vbCrLf & cmdText
errform.ShowDialog()
oConn.Close()
End Try
Return ds
End Function
End Class
请注意,我在其他地方(MainW.MyConnection)定义了一个ConnectionString
,您可以在其中为所有应用程序设置它。通常在启动过程中会从某些设置(文件,应用程序变量)中检索它。
然后我很容易一遍又一遍地使用它(C#):
Private void FillDGV()
{
String cmdText = "SELECT workers.FNAME, workers.LNAME FROM project1.workers INNER JOIN project1.order_status " +
"ON workers.ID_WORKER = order_status.ID_WORKER INNER JOIN project1.orders ON orders.ID_ORDER = order_status.ID_ORDER " +
"WHERE orders.ORDER_NUMBER = '" + NrOrder + "' GROUP BY workers.FNAME, workers.LNAME\"; ";
DataSet ds;
ds = DAL.GetQueryResults(cmdText);
DataTable dt;
if (ds.Tables.Count > 0)
{
dt = ds.Tables(0);
this.DataGridView1.DataSource = dt; // fill DataGridView
}
}
VB.NET:
Private Sub FillDGV()
Dim cmdText As String = "SELECT workers.FNAME, workers.LNAME FROM project1.workers INNER JOIN project1.order_status " +
"ON workers.ID_WORKER = order_status.ID_WORKER INNER JOIN project1.orders ON orders.ID_ORDER = order_status.ID_ORDER " +
"WHERE orders.ORDER_NUMBER = '" & NrOrder & "' GROUP BY workers.FNAME, workers.LNAME""; "
Dim ds As DataSet
ds = DAL.GetQueryResults(cmdText)
Dim dt As DataTable
If ds.Tables.Count > 0 Then
dt = ds.Tables(0)
Me.DataGridView1.DataSource = dt ' fill DataGridView
End If
End Sub
请注意,我在DataTable
和DataSet
之间使用DataGridView
作为数据对象。出于多种原因,养成使用它的习惯是很好的(除非使用其他更高级的方法)。一个主要的问题是,如果DataGridView
表恰好为空,它将不会获取您的DataSet
GUI定义的列。您还可以在DataTable
上然后在DataGridView
上更高效,更可靠地执行客户端数据操作。
一个人还可以考虑是否应该使用BindingSource
,而不是DataTable
。它的实现与DataTable的工作原理非常相似,因此,如果使本示例正常工作,则可以根据需要切换到BindingSource
。
另一个考虑因素是使用参数查询。如果您(您的用户)在封闭环境中操作桌面应用程序,则可以。但是,对于公开的应用程序,您可以确定会受到一些 SQL注入攻击。