سؤال

أحاول فهم بعض الكود. إنه برنامج صغير يطبع بيانات السجل. يتم ذلك عن طريق إنشاء نموذج باستخدام DataGridView الذي يتم ملؤه بواسطة DataTable. يحتوي فئة النموذج أيضًا على وظيفة تحديث (تحديث التحديث). تقوم فئة BusinessLogic بالعمل الفعلي لتحديث DataTable واستدعاء وظيفة التحديث في النموذج. لذلك أنا أفهم إلى حد كبير الوظيفة ، ولكن ليس لماذا يتم تنظيم البرنامج كما هو.

  1. لماذا يتم تشغيل BusinessLogic.Dowork كخيط بدلاً من مجرد استدعاء طريقة عادية؟
  2. هل يمكن لأحد أن يشرح وظيفة التحديث بالنسبة لي؟ (BeginInvoke والمندوب)
  3. هل هي فكرة/ممارسة جيدة تمرير الأداء الرئيسي كمعلمة إلى BusinessLogic؟

هذه هي نقطة الدخول الرئيسية للتطبيق.

public class Program
    {
        [STAThread]
        static void Main()
        {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new MainForm());            
        }
    }

هذا هو الجزء ذي الصلة من النموذج.

public partial class MainForm : Form
{
    private BusinessLogic businessLogic;
    private DataTable viewDataTable;

    public MainForm()
    {
        InitializeComponent();

        businessLogic = new BusinessLogic(this);
        Thread t = new Thread(new ThreadStart(businessLogic.DoWork));
        t.Start();
    }

    public delegate void RefreshPresentationDelegate(DataTable dataTable);

    public void RefreshPresentation(DataTable dataTable)
   {
        if (this.InvokeRequired)
        {
            this.BeginInvoke(new RefreshPresentationDelegate(RefreshPresentation), new object[] { dataTable });
            return;
        }
...

هذا هو منطق العمل.

internal class BusinessLogic
    {
        private MainForm form;
        private Logging.DAL.Logger loggerDAL;
        private int lastId;

        internal DataTable DataTable { get; private set; }
        internal bool IsRunning { get; set; }

        public BusinessLogic(MainForm form)
        {
            this.form = form;
            this.loggerDAL = new Logging.DAL.Logger();
            this.IsRunning = true;
            DataTable = new DataTable();
        }

        public void DoWork()
        {
            while (this.IsRunning)
            {
                // Get new log messages.
                if (DataTable.Rows.Count > 0)
                    this.lastId = (int)DataTable.Rows[DataTable.Rows.Count - 1]["Id"];

                this.DataTable = loggerDAL.GetLogMessagesSinceLastQuery(lastId);

                // Callback to GUI for update.
                form.RefreshPresentation(this.DataTable);

                // Wait for next refresh.
                Thread.Sleep(1000);
            }
        }

    }
هل كانت مفيدة؟

المحلول

Q1.Why why businesslogic.dowork تشغيل كخيط بدلاً من مجرد استدعاء طريقة عادية؟

A1. يجب أن يكون Dowork في مؤشر ترابط منفصل ، ثم مؤشر ترابط واجهة المستخدم الرسومية الرئيسية ، نظرًا لأن مؤشر ترابط واجهة المستخدم الرسومية الرئيسية يجب أن يكون حرًا لضخ قائمة انتظار الرسائل (التي تسمح له بإعادة رسم نفسها ، والتعامل مع أحداث واجهة المستخدم الرسومية المختلفة ، وما إلى ذلك) ، حاول إنشاء برنامج واجهة المستخدم الرسومية البسيطة هذا لديه بعض الوقت (صحيح) في الخيط الرئيسي ويرى أن واجهة المستخدم الرسومية تتعثر ولا يعيد رسم نفسه.

س. (BeginInvoke والمندوب)

A2. على الرغم من أن Dowork يجب أن يتم على موضوع آخر حتى لا يمنع مؤشر ترابط واجهة المستخدم الرسومية ، إلا أنه يجب أن يتم تحديث واجهة المستخدم الرسومية دائمًا من مؤشر ترابط واجهة المستخدم الرسومية. من أجل تحقيق ذلك ، يمكنك استدعاء BeginInvoke ، والتي تنشر رسالة إلى قائمة انتظار الرسائل وتسبب تنفيذ مندوبك على مؤشر ترابط واجهة المستخدم الرسومية.

س.

A3. لا. Google "MVC" لمزيد من المعلومات حول فصل واجهة المستخدم الرسومية عن منطق العمل.

نصائح أخرى

1) يشبه BusinessLogic يقوم ببعض الأعمال الطويلة. للحفاظ على مستجيب واجهة المستخدم أثناء هذه المعالجة ، يتم تنفيذها في موضوع مختلف.

2) RefreshPresentation() هي طريقة مسؤولة عن تحديث/تحديث واجهة المستخدم أثناء معالجة مؤشر ترابط الخلفية للحفاظ على تحديث واجهة المستخدم. نظرًا لأنه لا يمكن تغيير واجهة المستخدم من مؤشر ترابط إلى جانب موضوع واجهة المستخدم نفسه ، فأنت بحاجة إلى استخدام Invoke()/BeginInvoke() طرق إرسال هذا الرمز المراد تنفيذه على مؤشر ترابط واجهة المستخدم.

3) أنا شخصياً أعتقد أنها فكرة سيئة وبدلاً من ذلك يجب أن يتعرض حدث BusinessLogic فئة لإعلام تغيير البيانات.

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