CodeGym /مدونة جافا /Random-AR /طريقة الانتظار () في جافا
John Squirrels
مستوى
San Francisco

طريقة الانتظار () في جافا

نشرت في المجموعة
في هذه المقالة، سنلقي نظرة على طريقة الانتظار () للتحكم في سلسلة الرسائل، وطرق الإخطار () / notifyAll () . يتم تعريف هذه الأساليب في الفئة الأساسية java.lang.Object ، وبالتالي، توفر آليات الميراث الموجودة في Java هذه الأساليب لجميع الفئات تمامًا. أي أنه عندما تقوم بإنشاء فئة خاصة بك وكائناتها، يمكنك دائمًا استدعاء هذه الأساليب.

كيف تعمل طرق الانتظار () والإخطار ()/notifyAll ()؟

  • انتظر() . باختصار، تقوم هذه الطريقة بتحرير الشاشة وتضع مؤشر ترابط الاستدعاء في حالة انتظار حتى يستدعي مؤشر ترابط آخر طريقة الإخطار () / notifyAll () ؛
  • إعلام () . يتابع عمل الخيط الذي تم استدعاء أسلوب الانتظار الخاص به مسبقًا؛
  • تستأنف طريقة notifyAll () جميع سلاسل الرسائل التي تم استدعاء طريقة الانتظار () الخاصة بها مسبقًا.
الآن دعونا نلقي نظرة فاحصة على طريقة الانتظار () . تحتوي فئة الكائن على ثلاثة خيارات لهذه الطريقة:
  • انتظار الفراغ الأصلي العام (مهلة طويلةMillis) يلقي InterruptedException ؛ يؤدي إلى انتظار الخيط الحالي حتى يتم إيقاظه. وعادةً ما يحدث ذلك عن طريق إخطارك أو مقاطعتك، أو حتى انقضاء فترة معينة من الوقت الفعلي.

  • انتظار الفراغ النهائي العام () يلقي InterruptedException . ليس من قبيل الصدفة أننا كتبنا طريقة بدون معلمات مثل الطريقة الثانية. في الواقع، إذا نظرت إلى الكود الخاص به، فهو يشير إلى البديل الأول للطريقة، فهو يحتوي فقط على الوسيطة 0L.

  • الانتظار النهائي العام​(مهلة طويلة، int nanos) . يؤدي إلى انتظار مؤشر الترابط الحالي حتى يتم تنشيطه، عادةً عن طريق إعلامه أو مقاطعته، أو حتى انقضاء فترة معينة من الوقت الفعلي.

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

انتظر () مثال على الطريقة

لدينا هنا أحد الأمثلة الأكثر شيوعًا التي توضح كيفية عمل هذه الطريقة. لنفترض أن لدينا متجرًا ومنتجًا ومستهلكًا. تقوم الشركة المصنعة بنقل بعض منتجات الإنتاج إلى المتجر، وبعد ذلك يمكن للمستهلك أن يأخذها. دع الشركة المصنعة تنتج 8 سلع، على التوالي، يجب على المستهلك شراءها جميعا. ولكن في الوقت نفسه، لا يمكن أن يكون هناك أكثر من 6 عناصر في المستودع في نفس الوقت. لحل هذه المشكلة، نستخدم طريقتي الانتظار () والإخطار () . دعونا نحدد ثلاث فئات : السوق والشركة المصنعة والعميل . تضيف الشركة المصنعة في طريقة run() 8 منتجات إلى كائن السوق باستخدام طريقة put() الخاصة بها . يستدعي العميل في طريقة التشغيل () في حلقة طريقة الحصول على كائن السوق للحصول على هذه المنتجات. تتم مزامنة أساليب الوضع والحصول على فئة السوق . لتتبع وجود البضائع في فئة السوق ، نقوم بالتحقق من قيمة متغير السلعة. يجب أن يتم تنشيط طريقة get () للحصول على منتج فقط في حالة وجود منتج واحد على الأقل. لذلك، في طريقة الحصول، نتحقق مما إذا كان المنتج مفقودًا. إذا لم يكن العنصر متاحًا، فسيتم استدعاء طريقة الانتظار () . تقوم هذه الطريقة بتحرير شاشة كائن السوق وحظر طريقة الحصول حتى يتم استدعاء طريقة الإخطار () على نفس الشاشة. عند إضافة عنصر إلى طريقة put() واستدعاء notify() ، تحصل طريقة get() على الشاشة. بعد ذلك، يحصل عميلنا على السلعة. للقيام بذلك، يتم عرض رسالة، ويتم إنقاص قيمة العنصر. أخيرًا، يشير استدعاء أسلوب notify() إلى طريقة put() للمتابعة. في طريقة put() ، يعمل منطق مماثل، الآن فقط يجب أن تعمل طريقة put() إذا لم يكن هناك أكثر من 6 منتجات في السوق .
class Market {

   private int item = 0;

   public synchronized void get() {
       //here we use wait() method
       while (item < 1) {
           try {
               wait();
           }
           catch (InterruptedException e) {
           }
       }
       item--;
       System.out.println("A client has bought 1 item...");
       System.out.println("Items quantity in Market warehouse... " + item);
       notify();
   }

   public synchronized void put() {
       //here we use wait() method when the Warehouse is full
       while (item >= 6) {
           try {
               wait();
           }
           catch (InterruptedException e) {
           }
       }
       item ++;
       System.out.println("Manufacturer has added 1 more item...");
       System.out.println("Now there are " + item + " items in Warehouse" );
       notify();
   }
}

class Manufacturer implements Runnable {

   Market market;

   Manufacturer(Market market) {
       this.market = market;
   }


   public void run() {
       for (int i = 0; i < 8; i++) {
           market.put();
       }
   }
}

class Client implements Runnable {

   Market market;
   Client(Market market) {
       this.market = market;
   }
   public void run() {
       for (int i = 0; i < 8; i++) {
           market.get();
       }
   }
}
//wait() method test class
public class WaitTest {
   public static void main(String[] args) {

       Market market = new Market();
       Manufacturer manufacturer = new Manufacturer(market);
       Client client = new Client(market);
       new Thread(manufacturer).start();
       new Thread(client).start();
   }
}
هنا، باستخدام wait() في طريقة get() ، نحن في انتظار قيام الشركة المصنعة بإضافة عنصر جديد. وبعد الإضافة، نستدعي notify() ، وكأننا نقول أن مكانًا واحدًا أصبح مجانيًا في المستودع ، ويمكنك إضافة المزيد. في طريقة put() ، باستخدام wait() ، ننتظر تحرير المساحة في المستودع . بعد أن تصبح المساحة فارغة، نضيف العنصر، ويبدأ notify () الخيط ويمكن للعميل التقاط العنصر. هنا هو إخراج برنامجنا:
أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... الآن هناك عنصر واحد في المستودع أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... الآن يوجد عنصرين في المستودع أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... الآن هناك 3 عناصر في المستودع قامت الشركة المصنعة تمت إضافة عنصر واحد إضافي... الآن هناك 4 عناصر في المستودع أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... الآن هناك 5 عناصر في المستودع أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... يوجد الآن 6 عناصر في المستودع قام أحد العملاء بشراء 1 صنف... كمية الأصناف في مستودع السوق... 5 عميل اشترى صنف واحد... كمية الأصناف في مستودع السوق... 4 عميل اشترى 1 صنف... كمية الأصناف في مستودع السوق... 3 اشترى عميل صنفًا واحدًا... كمية الأصناف في مستودع السوق... 2 اشترى العميل صنفًا واحدًا... كمية الأصناف في مستودع السوق... 1 اشترى العميل صنفًا واحدًا... كمية العناصر في مستودع السوق ... 0 أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... الآن هناك عنصر واحد في المستودع أضافت الشركة المصنعة عنصرًا واحدًا إضافيًا... الآن يوجد عنصران في المستودع اشترى العميل عنصرًا واحدًا... كمية العناصر في مستودع السوق ... 1 قام العميل بشراء صنف واحد... كمية الأصناف في مستودع السوق... 0 انتهت العملية برمز الخروج 0
تعليقات
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION