سؤال

أفهم كيفية استخدام المندوبين لتحديث عناصر التحكم في مؤشر ترابط التحكم الرئيسي، يعمل مثل سحر. مشكلتي هنا إذا كنت أضيف كبير 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 يكشف عن أنه احتمال جيد.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top