لماذا يقوم FileSystemWatcher بإنشاء أحداث تغيير متعددة عندما أقوم بنسخ ملف إلى الدليل

StackOverflow https://stackoverflow.com/questions/172060

سؤال

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

نص بديل http://robinwilson.homelinux.com/FSW.png

أحصل على حدث تم إنشاؤه (كما هو متوقع)، ولكن تم تغيير حدثين (يفصل بينهما حوالي 0.7 ثانية).لماذا هذا؟قد يتسبب هذا في حدوث مشكلات كبيرة في التطبيق الذي أخطط لتطويره - حيث أحاول القيام بالأشياء مع الملف مرتين (من المفترض مرة واحدة قبل الانتهاء من كتابته!).هل هناك أي شيء يمكنني فعله لوقف حدوث ذلك؟من ما قرأته على StackOverflow وأماكن أخرى، يجب أن تحصل على حدث واحد تم تغييره بمجرد تغيير الملف ثم إغلاقه.لماذا أحصل على اثنين؟

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

المحلول

بحسب ال توثيق (انظر النقطة الأولى تحت الأحداث وأحجام المخزن المؤقت):

قد تؤدي عمليات نظام الملفات الشائعة إلى ظهور أكثر من حدث واحد. على سبيل المثال، عند نقل ملف من دليل إلى آخر، قد يتم رفع عدة أحداث OnChanged وبعض أحداث OnCreated وOnDeleted. يعد نقل ملف عملية معقدة تتكون من عدة عمليات بسيطة، وبالتالي رفع أحداث متعددة. وبالمثل، قد تتسبب بعض التطبيقات (على سبيل المثال، برامج مكافحة الفيروسات) في حدوث أحداث إضافية لنظام الملفات تم اكتشافها بواسطة FileSystemWatcher.

نصائح أخرى

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

ويمكنك تنفيذ محاولة لفتح ملف مع حقوق قراءة الحصرية، التي ينبغي أن تمنح للبرنامج الخاص بك فقط عند الانتهاء من برنامج آخر نسخ وملف مغلق. وإلا فإنك سوف تحصل IOException ويمكنك الانتظار من أجل التغيير القادم. ولكن هذا لا يعني أن عليك أن لا تتعامل مع أحداث التغيير مضاعفة. فتح ملف نصي في المفكرة وحفظه مرة واحدة في حين سوف تولد أحداث التغيير، ولكن الملف لا يكون مؤمنا في كل وقت.

وثمة نهج آخر يتمثل في جمع ملفات تطرق لفترة من الوقت، وعندما يتوقف FileSystemWatcher توليد الأحداث، ومعالجة كافة الملفات دفعة واحدة.

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