سؤال

VB.NET عام 2010،.صافي 4

مرحبا بكم جميعا ،

لدي النظام.توقيت.الموقت الكائن الذي يفعل بعض العمل على انقضاء الحدث:

Private Sub MasterTimer_Elapsed(ByVal sender As Object, ByVal e As System.Timers.ElapsedEventArgs) Handles MasterTimer.Elapsed
    MasterTimer.Enabled = False
    '...work...
    MasterTimer.Enabled = True
End Sub

مشكلتي هي أن العمل الذي تقوم به في بعض الأحيان يحصل عالقا.جزء من العمل هو الاتصالات التسلسلية لذلك قد يكون الحصول على عالقا في انتظار رد من شيء.لقد عدلت الاتصالات التسلسلية رمز قليلا على أمل حل المشكلة.ومع ذلك ، فإن هذا الموقت هو في الأساس ضربات القلب من مراقبة الإنتاج التطبيق و أنها سيئة للغاية إذا كان التوقف لأي سبب من الأسباب.كنت أفكر أنه قد يكون من الجميل أن يضع في آمنة من الفشل مهلة حتى إذا كان "العمل" تستغرق وقتا طويلا ، الموقت يمكن إعادة تمكين نفسها وحاول مرة أخرى.كنت أفكر في شيء من هذا القبيل:

نقل العمل إلى روتين فرعي وخلق مندوب:

Private Delegate Sub WorkDelegate()
Private Sub Work()
   '...work...
End Sub

دعوة للعمل من خلال استدعاء مندوب ومن ثم استخدام WaitOne(مهلة) على IAsyncResult إلى تحديد مهلة:

Private Sub MasterTimer_Elapsed(ByVal sender As Object, ByVal e As System.Timers.ElapsedEventArgs) Handles MasterTimer.Elapsed
    MasterTimer.Enabled = False
    Dim workDel as New WorkDelegate(AddressOf Work)
    Dim result as IAsyncResult = workDel.BeginInvoke
    result.AsyncWaitHandle.WaitOne(CInt(MasterTimer.Interval))
    MasterTimer.Enabled = True
End Sub

ولكن سؤالي هو:هل هذا يسبب مشكلة إذا كان العمل() حقا كان عالقا في مكان ما ؟ في أن إعادة إدخال روتين التي قيد التشغيل بالفعل ؟ هل هناك طريقة لتعطيل العمل() إذا لم ينته بعد مهلة?وبعبارة أخرى, فقط وقف تنفيذ العمل() إذا كانت النتيجة.IsCompleted كاذبة بعد WaitOne?

أنا حقا لا أفهم هذه الأشياء بشكل جيد جدا لذلك ، أي تعليقات سيكون موضع تقدير كبير.ربما هناك طريقة مختلفة تماما لهذا النهج الذي لا أعلم عنه ؟

شكرا جزيلا مقدما!

أود أن أضيف شيئا:

وإن كنت تنوي القيام ببعض يعيد كتابة في هانز اقتراحات كنت قد حددت يوم الاختبار إلى محاولة عزل مصدر هذا الخطأ.حتى الآن, وقد حدثت فقط عند تشغيل التطبيقات المترجمة.لقد قضيت اليوم (البارحة) في محاولة لإعادة إنتاج تجميد أثناء تشغيل في وضع التصحيح بحيث ربما يمكن إضافة بعض نقاط التوقف ومعرفة ما يجري.البرنامج حتى الآن لم المجمدة في وضع التصحيح.أنا أتساءل فقط إذا كان هناك أي شيء مختلف عن تصحيح البيئة التي قد تفسر هذا.فإنه قد يكون مجرد أن أكون "محظوظ" ، لكني كنت تشغيله ربما ثلاثة أضعاف متوسط طول الوقت وبعد البرنامج جمدت عند تشغيل الملف القابل للتنفيذ...مرة أخرى أنا جاهل جدا, ولكن هل هناك شيء فريد من نوعه حول تصحيح البيئة التي يمكن أن تفسر هذا ؟ أنا تحديث مرة أخرى إذا كان يتجمد.

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

المحلول

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

آمن واحد هو النظام.خيوط.الموقت مع فترة من الصفر لذلك عليك الحصول على واحد فقط رد.شحن الموقت مع تغيير الأسلوب ().

استدعاء مندوب BeginInvoke (طريقة) ثم حظر على الانتهاء لا معنى له.فقط اتصل الاحتجاج().يوفر لك من حرق موضوع آخر.

نعم ، إذا كان "العمل" الأسلوب لا يعود أبدا ثم لديك مشكلة.غير قابلة للحل واحد.

الكثير من هذا البؤس يمكن أن تختفي إذا كنت تجنب استخدام الاقتراع لمعرفة ما إذا كان هناك أي شيء متاح على المنفذ التسلسلي.اسمحوا أن أقول لكم أن هناك شيء جدير بالاهتمام يحدث.فإنه يثير DataReceived الحدث على threadpool الموضوع ، كلما كان هناك واحد على الأقل بايت في تلقي المخزن المؤقت.باستخدام WriteTimeout الممتلكات هو أيضا وسيلة ممتازة لتجنب الحصول على عالقة عندما يكون هناك شيء خاطئ مع بروتوكول الاتصال أو الجهاز.تخصيص موضوع واحد مما حجب قراءة المكالمات يعمل بشكل جيد جدا.

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