تحديث غير حلقي إلى DataGridView
-
18-09-2019 - |
سؤال
أفهم كيفية استخدام المندوبين لتحديث عناصر التحكم في مؤشر ترابط التحكم الرئيسي، يعمل مثل سحر. مشكلتي هنا إذا كنت أضيف كبير DataSet
(قل 2000 عناصر) إلى حد ما DataGridView
, ، يستغرق 5-8 ثوان للشبكة لملء وخلال ذلك 5-8 ثواني، تم تأمين واجهة المستخدم الرسومية بأكملها. كيف يمكنني تحديث DataGridView
بحيث لا قفل واجهة المستخدم؟
لتكون واضحة، فإن المشكلة ليست كذلك أنا أفعل استعلام بطيء إلى قاعدة بيانات وتم حظر واجهة المستخدم على ذلك، لدي بالفعل DataSet object[]
وإضافة مجموعة الكائنات إلى BindingList<object>
التي DataGrid
لا بد أن كذلك:
BindingList<object> dataProvider = new BindingList<object>();
DataGridView gridView = new DataGridView();
gridView.DataSource = dataProvider;
// ...stuff happens...
object[] source = dataSet; //of 2000 items
foreach (object item in source) { //this foreach blocks
dataProvider.Add(item);
}
جربت أشياء مختلفة (التي عرفتها لن أعمل ولكن احسب كنت أرى) مثل إنشاء مندوب فعل ذلك dataProvider.Add()
, ، لكن هذا لم يكن الأمر نظرا لأنه لا يزال يتعين عليه الحدوث في مؤشر ترابط التحكم.
زوجين اقتراحات جيدة تدور حول بناء BindingList
أولا ثم وضع gridView.DataSource
. وبعد في حين أن هذا يعمل (يقوم بتحديث الشبكة على الفور)، فإن الطريقة الوحيدة التي أراها لإضافة المزيد من البيانات هي إنشاء جديد آخر BindingList
, ، هل gridView.DataSource.copyTo()
(للحصول على البيانات الموجودة) وإضافة البيانات الجديدة أعلى ذلك، ثم اضبط gridView.DataSource
إلى الجديد BindingList
. وبعد لن يعمل هذا بالنسبة لي منذ الكائنات الموجودة في قائمتي ليست ثابتة، فهي كل بيانات تحميل إلى خادم غير متزامن، ونسخها إلى جديد BindingList
سوف تسبب مشاكل.
المحلول
تقوم بإضافة سجلات أثناء ترتبط GridView ب DataSource. هذا يعني أنه سيتم تحديث التصميم في كل مرة.
ماذا عنك أولا ملء DataSource الخاص بك ولا يقوم فقط بتعيين خاصية DataSource؟
gridView.DataSource = null;
...stuff happens...
object[] source = dataSet; //of 2000 items
foreach (object item in source) { //this foreach blocks
dataProvider.Add(item);
}
gridView.DataSource = dataProvider;
يمكن أن تذهب حلقة Foreach إلى مؤشر ترابط آخر لكنني لا أعتقد أنك ستحتاج إلى ذلك.
نصائح أخرى
مثل نيك قال BackgroundWorker
ربما أفضل رهان الخاص بك.
هنا مثال بسيط جدا
public partial class Form1 : Form
{
BackgroundWorker b = new BackgroundWorker();
public Form1()
{
InitializeComponent();
b.RunWorkerCompleted += new RunWorkerCompletedEventHandler(b_RunWorkerCompleted);
b.DoWork += new DoWorkEventHandler(b_DoWork);
}
void b_DoWork(object sender, DoWorkEventArgs e)
{
// build dataset here and assigning it to results
e.Result = dataset;
}
void b_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
// assign the dataset you built in DoWork in the gridview and update it
dataGridView1.DataSource = e.Result;
dataGridView1.Update();
}
private void button1_Click(object sender, EventArgs e)
{
b.RunWorkerAsync();
}
}
انظر إلى استخدام مخلة. وبعد لا أعرف الكثير عنهم بنفسي، لكن البحث قليلا على Google يكشف عن أنه احتمال جيد.