c# - c# 使用 MySQL 数据库中的后台工作人员每 5 秒更新一次数据网格视图
问题描述
这是我想要实现的目标:我正在 c# (visual studio) 中以 Windows 窗体格式构建警报系统。我有一个带有数据网格视图的 Windows 窗体,需要每 5 秒从 MySQL 数据库获取信息。我正在使用 System.Threading.Timer 和后台工作人员。我为此搜索了所有线程,但似乎没有任何效果。计时器正在工作,因为我每 5 秒出现一次线程错误,所以问题一定出在后台工作代码中。这是代码:
public partial class Alerts : Form
{
private System.Threading.Timer _timerThread;
private int _period = 5000;
static BackgroundWorker bgw = new BackgroundWorker();
public Alerts()
{
InitializeComponent();
_timerThread = new System.Threading.Timer((o) =>
{
// Stop the timer;
_timerThread.Change(-1, -1);
bgw.DoWork += bgw_DoWork;
bgw.RunWorkerAsync();
// start timer again (BeginTime, Interval)
_timerThread.Change(_period, _period);
}, null, 0, _period);
}
private void bgw_DoWork(object sender, DoWorkEventArgs e)
{
string constring = "datasource=localhost;port=3306;username=root;password=*******";
MySqlConnection conDataBase = new MySqlConnection(constring);
MySqlCommand cmdDataBase = new MySqlCommand(" select * from shopmanager.alerts ;", conDataBase);
try
{
conDataBase.Open();
MySqlDataAdapter sda = new MySqlDataAdapter();
sda.SelectCommand = cmdDataBase;
DataTable dbdataset = new DataTable();
sda.Fill(dbdataset);
BindingSource bsource = new BindingSource();
bsource.DataSource = dbdataset;
dataGridView1.DataSource = bsource;
sda.Update(dbdataset);
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
conDataBase.Close();
}
static void bgw_RunWorkerCompleted(object sender,RunWorkerCompletedEventArgs e)
{
// I think this is where I should be able to update the datagridview but i'm not sure how.
}
}
我完全迷路了。请帮忙
我现在尝试了这段代码,但它无法识别 DataGridView1。我究竟做错了什么?
public partial class Alerts : Form
{
private System.Threading.Timer _timerThread;
private int _period = 5000;
static BackgroundWorker bgw = new BackgroundWorker();
private static object dbdataset;
public Alerts()
{
InitializeComponent();
_timerThread = new System.Threading.Timer((o) =>
{
// Stop the timer;
_timerThread.Change(-1, -1);
// Calls UpdateAlerts() that updates a datagridview with the mysql data
bgw.DoWork += bgw_DoWork;
bgw.RunWorkerAsync();
// start timer again (BeginTime, Interval)
_timerThread.Change(_period, _period);
}, null, 0, _period);
}
private void bgw_DoWork(object sender, DoWorkEventArgs e)
{
string constring = "datasource=localhost;port=3306;username=root;password=******";
MySqlConnection conDataBase = new MySqlConnection(constring);
MySqlCommand cmdDataBase = new MySqlCommand(" select * from shopmanager.alerts ;", conDataBase);
try
{
conDataBase.Open();
MySqlDataAdapter sda = new MySqlDataAdapter();
sda.SelectCommand = cmdDataBase;
DataTable dbdataset = new DataTable();
sda.Fill(dbdataset);
BindingSource bsource = new BindingSource();
bsource.DataSource = dbdataset;
sda.Update(dbdataset);
e.Result = dbdataset;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
conDataBase.Close();
}
static void bgw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
DataGridView1.DataSource = dbdataset;
}
}
解决方案
我将对您的代码进行许多更改:
- 使用
Timer
Windows 窗体工具箱中的而不是System.Threading.Timer
(它旨在更好地在 Windows 窗体中工作)。将其拖到表单上,然后将事件处理程序附加到其Tick
方法以获取定期更新。 - 仅附加
BackgroundWorker
一次事件处理程序。 - 将 BackgroundWorker 组件从设计器工具箱拖到表单上,以便为您管理其生命周期;不要使用字段
static
。 - 使用
using
with 语句MySqlConnection
来清理它使用的资源。 - 使用实例方法(不是
static
),以便您可以引用Alerts
类中的属性/字段。
这是一个例子:
public partial class Alerts : Form
{
public Alerts()
{
InitializeComponent();
// set up BackgroundWorker once
backgroundWorker1.DoWork += OnDoWork;
backgroundWorker1.RunWorkerCompleted += OnRunWorkerCompleted;
// set the timer and start it running
timer1.Interval = 5000;
timer1.Start();
timer1.Tick += (o, e) => backgroundWorker1.RunWorkerAsync();
}
// This method will run in the background every five seconds. It can't
// access parts of the form since it is on a background thread.
private void OnDoWork(object sender, DoWorkEventArgs e)
{
using (MySqlConnection conDataBase = new MySqlConnection(connectionString))
using (MySqlCommand cmdDataBase = new MySqlCommand(" select * from shopmanager.alerts;", conDataBase))
{
conDataBase.Open();
MySqlDataAdapter sda = new MySqlDataAdapter { SelectCommand = cmdDataBase };
DataTable dbdataset = new DataTable();
sda.Fill(dbdataset);
// return the results to the main form thread through this property
e.Result = dbdataset;
}
}
void OnRunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
// This will run on the main form thread when the background work is
// done; it connects the results to the data grid.
dataGridView1.DataSource = e.Result;
}
}
推荐阅读
- c++ - 是否可以在 C++ 中更改向量的开始位置以清除其前 n 个元素?
- javascript - Javascript 正则表达式替换
- 或者
- 标签
- 里面只有文字
- c++ - C++ 重新运行程序
- jquery - 多个模态叠加 - 转义键仅关闭底层窗口
- java - ElasticSearch Java 中的复合聚合
- powershell - 使用 powershell 命令批量安装打印机不起作用
- jquery - JQuery 动态表单创建删除现有输入字段
- java - XMLunit 只比较标签
- html - 无法在 Bootstrap 导航栏中显示图标和文本
- r - 如何求解 R 和 uniroot 函数中的非线性方程