“สวัสดี อามีโก้!

"ทุกอย่างใหม่เป็นเพียงสิ่งเก่าที่เราลืมไปแล้ว วันนี้ฉันจะพูดถึงการหยุดเธรด ฉันหวังว่าคุณจะลืมแล้วว่าวิธีขัดจังหวะ () ทำงานอย่างไร"

“ใช่ เอลลี่ ฉันลืมไปหมดแล้ว”

"เยี่ยมมาก แล้วฉันจะเตือนคุณ"

"ใน Java ถ้ามีใครต้องการหยุดเธรดที่กำลังทำงานอยู่ เขาสามารถส่งสัญญาณนี้ไปยังเธรดได้ ในการทำเช่นนี้ คุณต้องตั้งค่าตัวแปร isInterruptedที่ซ่อนอยู่ของวัตถุเธรดเป็น true"

"แต่ละเธรดมีเมธอดอินเตอร์รัปต์ () ซึ่งใช้เพื่อตั้งค่าแฟล็กนี้ เมื่อเมธอดอินเตอร์รัปต์ () ถูกเรียกใช้ ตัวแปร isInterruptedภายในอ็อบเจกต์เธรดจะถูกตั้งค่าเป็นจริง"

"และเมื่อเมธอด Thread.sleep() หรือ join() ถูกเรียกบนเธรด เมธอดจะตรวจสอบว่าแฟล็ก isInterrupted ถูกตั้งค่าสำหรับเธรดปัจจุบันหรือไม่ หากแฟล็กนี้ถูกตั้งค่า (ตัวแปร isInterrupted เท่ากับจริง) ดังนั้นเมธอด โยนInterruptedException "

"ต่อไปนี้ ฉันจะเตือนคุณถึงตัวอย่างเก่า:"

รหัส คำอธิบาย
class Clock implements Runnable
{
public void run()
{
Thread current = Thread.currentThread();

while (!current.isInterrupted())
{
Thread.sleep(1000);
System.out.println("Tik");
}
}
}
วิธีการเรียกใช้นาฬิกาได้รับวัตถุเธรดสำหรับเธรดปัจจุบัน

คลาส Clock เขียนคำว่า "Tick" ลงในคอนโซลหนึ่งครั้งต่อวินาที ตราบใดที่ตัวแปร isInterrupt ของเธรดปัจจุบันเป็นเท็จ

เมื่อ isInterrupt กลายเป็นจริง วิธีการรันจะสิ้นสุดลง

public static void main(String[] args)
{
Clock clock = new Clock();
Thread clockThread = new Thread(clock);
clockThread.start();

Thread.sleep(10000);
clockThread.interrupt();
}
เธรดหลักเริ่มต้นเธรดย่อย (นาฬิกา) ที่ควรทำงานตลอดไป

รอ 10 วินาที และยกเลิกงานโดยเรียกวิธีการขัดจังหวะ

เธรดหลักเสร็จสิ้นการทำงาน

เธรดนาฬิกาเสร็จสิ้นการทำงาน

"ในที่นี้ เราใช้ วิธี sleepเป็นส่วนหนึ่งของการวนซ้ำไม่สิ้นสุดในเมธอดrunในลูป ตัวแปร isInterruptจะถูกตรวจสอบโดยอัตโนมัติ หากเธรดเรียกเมธอดsleepเมธอดจะตรวจสอบก่อนว่าisInterruptเป็นจริงสำหรับเธรดนั้นหรือไม่ ( วิธีที่เรียกว่า sleep method) หากเป็นจริง method จะไม่ sleep แต่จะโยน InterruptedException แทน "

"แต่ในตัวอย่างนี้ เราตรวจสอบตัวแปร isInterrupted อย่างต่อเนื่องในเงื่อนไขของลูป"

"ฉันจำได้ว่ามีเหตุผลบางอย่างที่เราไม่สามารถใช้วิธีนี้ได้ คุณช่วยเตือนฉันได้ไหม"

" อย่างแรกเมธอดrunไม่มีการวนซ้ำเสมอ เมธอดอาจประกอบด้วยการเรียกใช้เมธอดอื่นๆ สองสามโหล ในกรณีนี้ คุณจะต้องเพิ่มการตรวจสอบ isInterrupted ก่อนเรียกเมธอดแต่ละครั้ง"

" ประการที่สองวิธีการบางอย่างที่เกี่ยวข้องกับการดำเนินการต่างๆ มากมาย อาจใช้เวลานานมากในการดำเนินการ"

" ประการที่สามการโยนข้อยกเว้นไม่ได้แทนที่การตรวจสอบ isInterrupted เป็นเพียงการเพิ่มเติมที่สะดวก ข้อยกเว้นที่ส่งกลับทำให้คุณสามารถคลาย call stack กลับไปยังวิธีการเรียกใช้ได้ อย่างรวดเร็ว "

" ประการที่สี่วิธีสลีปถูกใช้มาก ปรากฎว่าวิธีการที่เป็นประโยชน์นี้ได้รับการปรับปรุงโดยการตรวจสอบโดยปริยายซึ่งมีประโยชน์ไม่น้อย  ราวกับว่าไม่มีใครเพิ่มการตรวจสอบโดยเฉพาะ แต่มีอยู่ สิ่ง  นี้มีค่ามากเมื่อคุณ 'กำลังใช้รหัสของคนอื่น และคุณไม่สามารถเพิ่มเช็คได้ด้วยตัวเอง"

" ประการที่ห้าการตรวจสอบเพิ่มเติมไม่ได้ทำให้ประสิทธิภาพลดลง การเรียกใช้เมธอด sleep หมายความว่าเธรดไม่ควรทำอะไรเลย (ยกเว้นโหมดสลีป) ดังนั้นงานพิเศษจะไม่รบกวนใคร"

“นั่นคือสิ่งที่คุณพูดก่อนหน้านี้”

"แล้วคำพูดของคุณล่ะ « ไม่มีใครรับประกันได้ว่าเธรดจะหยุดทำงาน มีเพียงเธรดเท่านั้นที่สามารถหยุดตัวเองได้ » คุณช่วยอธิบายได้ไหม"

"แน่นอน."

"ก่อนหน้านี้ ในเวอร์ชันแรกๆ ของ Java เธรดมีเมธอด stop() และเมื่อคุณเรียกมัน JVM จะหยุดเธรด แต่ถ้าเธรดกำลังทำบางสิ่งนอก JVM (เช่น การเขียนไปยังไฟล์หรือการเรียก ฟังก์ชัน OS) เมื่อถูกขัดจังหวะด้วยวิธีนี้ การขัดจังหวะทำให้เกิดปัญหามากมาย เช่น ไฟล์ที่ไม่ได้ปิด ทรัพยากรระบบที่ไม่ได้เผยแพร่ ฯลฯ"

"ที่ประชุมใหญ่ของผู้สร้าง Java ตัดสินใจที่จะลบวิธีการบังคับหยุดเธรด ตอนนี้สิ่งที่เราทำได้คือตั้งค่าสถานะ (isInterrupted) และหวังว่าโค้ดเธรดจะถูกเขียนอย่างถูกต้อง เพื่อให้แฟล็กนี้ได้รับการประมวลผล แฟล็กนี้ ก็เหมือนสัญญาณที่บอกว่า 'หยุดด้าย หยุดเถอะ สำคัญมาก!' แต่จะหยุดหรือไม่ก็เรื่องของมัน"

"แล้ว InterruptedException ล่ะ"

"จะเกิดอะไรขึ้นถ้าโค้ดที่รันบนเธรดนี้มีบล็อก try-catch จำนวนมาก แม้ว่า InterruptedException จะเกิดขึ้นที่ไหนสักแห่ง ก็ไม่มีการรับประกันว่า try-catch บางตัวจะจับไม่ได้และลืมมันไป ดังนั้นจึงไม่มีการรับประกันว่า ด้ายจะหยุด"

"อีกสิ่งหนึ่งคือเธรดได้รับการพิจารณาว่าเป็นการเขียนโปรแกรมระดับต่ำอยู่แล้ว แต่ฉันจะบอกคุณเกี่ยวกับเรื่องนี้ในครั้งต่อไป"

“คุณไม่ใช่ Ellie คุณคือ Scheherazade!”

"เอาล่ะ Amigo! ทุกอย่างในบทเรียนปัจจุบันชัดเจนหรือไม่"

"ใช่."

"ตกลงดี."