มีสองวิธีในการสร้างเธรดใน Java คือการสืบทอดคลาสเธรดและใช้อินเทอร์เฟซ Runnable
มรดก
คลาสสาธารณะ MyThread ขยายเธรด {Public MyThread (ชื่อสตริง) {Super (ชื่อ); } int i; โมฆะสาธารณะเรียกใช้ () {สำหรับ (i = 0; i <5; i ++) {system.out.println (getName ()+"-"+i); }} โมฆะคงที่สาธารณะหลัก (สตริง [] agrs) {ใหม่ mythread ("thread1"). start (); ใหม่ MyThread ("Thread2") เริ่มต้น (); }} /*เธรด 1-0THREAD 1-1THREAD 1-2 เธรด 1-3THREAD 1-4THREAD 2-0THREAD 2-1THREAD 2-2 Thread 2-3THREAD 2-4* / / /ดังที่ได้กล่าวไว้ข้างต้นวัตถุเธรดใน Java จะต้องถูกสร้างขึ้นในรูปแบบของคลาสและวิธีการเรียกใช้ () ของคลาสพื้นฐานจะต้องถูกแทนที่ในคลาสนี้ วิธีนี้เป็นจริงการดำเนินการของเธรด เรียกวิธีการเริ่มต้นของอินสแตนซ์คลาสนี้โดยปริยายเรียกวิธีการเรียกใช้
ไม่ยากที่จะเห็นว่าเนื่องจากตำนานของมรดกเป็นสองครั้งตัวอย่างของสองครั้งแตกต่างกันนั่นคือแต่ละคนมีตัวแปร I ของตัวเองซึ่งเป็นอิสระจากกัน
อินเทอร์เฟซ Runnable
ชั้นเรียนสาธารณะ Myrunnable ใช้งานได้ {int i; โมฆะสาธารณะเรียกใช้ () {สำหรับ (i = 0; i <50; i ++) {system.out.println (thread.currentthread (). getName ()+"-"+i); // this.getName () ไม่สามารถใช้โดยตรง}} เธรดใหม่ (Myrun, "Thread1"). Start (); เธรดใหม่ (Myrun, "Thread2"). Start (); }} /*เธรด 1-0THREAD 1-1THREAD 2-0THREAD 2-3THREAD 2-4THREAD 2-5THREAD 2-6THREAD 2-7THREAD 2-8th เธรด 2-9TH 2-9th เธรด 2-10th เธรด 2-18th 2-18th 2-12th Thread 2-18th 2-12th 2-22th เธรด 2-23th เธรด 2-24th เธรด 1-17th เธรด 2--25 เธรด 1--26 เธรด 2--27 เธรด 1--28 เธรด 1--30 เธรด 2--29 เธรด 1--31 เธรด 2--32 เธรด 2-34 เธรด 2--35 2--40 เธรด 1--42 เธรด 1--44 เธรด 1--45 เธรด 2--43 เธรด 1--46 เธรด 2--47 เธรด 2--49 เธรด 1--48*/จะเห็นได้ว่าเนื่องจากวิธีนี้คือการโหลดวัตถุลงในคลาสเธรดเป็นเป้าหมายแม้ว่าจะมีวัตถุเธรดจำนวนมากในใหม่ตราบใดที่เป้าหมายเป็นวัตถุอ้างอิงเดียวกันวิธีการเรียกใช้ของวัตถุเรียกว่าและเธรดทั้งหมดจะแบ่งปันทรัพยากรของวัตถุเป้าหมาย ดังนั้นคุณจะเห็นว่าเธรด 1 และเธรด 2 เอาต์พุตทั้งหมด 51 ครั้งและสองเธรดได้เสร็จสิ้นเอาต์พุตจาก i จาก 0 ถึง 49 และไม่เอาต์พุต 5 เท่าตามลำดับ สำหรับสาเหตุที่ 51 เป็นเอาท์พุทเธรดทั้งสองเข้าสู่สถานะพร้อมเกือบในเวลาเดียวกัน (วิธีการเริ่มต้นเพียงแค่ให้เธรดเข้าสู่สถานะพร้อม) มันไม่ยากที่จะพบว่าเมื่อฉันเท่ากับ 0, เธรด 1 และเธรด 2 เป็นทั้งในสถานะการทำงานในเวลาเดียวกันทำให้เกิดปรากฏการณ์พร้อมกัน หลังจากนั้น CPU จะสลับเธรดอย่างต่อเนื่องเพื่อให้มีเพียงหนึ่งเธรดที่ถูกส่งออกในเวลาเดียวกัน
สถานะด้าย
หัวข้อแบ่งออกเป็น 4 รัฐ
ready state: โทรหาวิธีเริ่มต้นและป้อนสถานะพร้อม
สถานะการรัน: เธรดในสถานะพร้อมจะถูกกำหนดโดย JVM และกลายเป็นสถานะการทำงาน
การปิดกั้นสถานะ: หากวิธีการซิงโครไนซ์บางอย่างไม่ส่งคืนผลลัพธ์สถานะการปิดกั้นจะเกิดขึ้นหรือการนอนหลับและ yeild
สถานะความตาย: ร่างกายวิธีการถูกดำเนินการหรือเธรดถูกบังคับให้หยุด
การดำเนินการขั้นพื้นฐานของเธรด
เข้าร่วม () ผสานเธรด: หลังจากเธรดปัจจุบันเรียกวิธีการเข้าร่วมของเธรดมันจะรอให้เธรดดำเนินการเสร็จสิ้นก่อนที่เธรดจะดำเนินการต่อ
การนอนหลับ (มิลลิวินาทียาว) ด้ายสลีป: บล็อกเธรดปัจจุบันและมันจะดำเนินต่อไปเมื่อเวลาปิดกั้นขึ้น เมื่อบล็อกอีกครั้งการเป็นเจ้าของ CPU จะถูกส่งไปยังเธรดอื่นดังนั้นการนอนหลับ (1) มักจะใช้เพื่อสลับเธรด
** ผลตอบแทน () เธรดสัมปทาน: ** yeild คล้ายกับการนอนหลับ แต่จะมีเพียงสัมปทานกับเธรดอื่น ๆ ในระดับที่สูงขึ้นหรือในระดับเดียวกัน หากไม่มีเธรดอื่นต่ำกว่าระดับของพวกเขาเธรดจะถูกดำเนินการอีกครั้ง
เธรดพื้นหลัง
หลังจากโปรแกรมดำเนินการโดยระบบปฏิบัติการจะมีกระบวนการและกระบวนการมีอย่างน้อยหนึ่งเธรด (เธรดหลัก) เธรดหลักไม่มีคุณสมบัติพิเศษมากไปกว่าเธรดอื่น ๆ เพียงเพราะเป็นเธรดแรกสุดที่จะดำเนินการเธรดอื่น ๆ จะถูกสร้างขึ้นในเธรดหลัก หากไม่ได้ระบุเธรดเบื้องหน้า (รวมถึงเธรดหลัก) จะถูกสร้างขึ้นโดยค่าเริ่มต้น หากเรียกว่า setdaemon (true) เธรดจะถูกตั้งค่าเป็นเธรดพื้นหลังอย่างชัดเจน เธรดพื้นหลังเป็นด้าย daemon อย่างที่คุณเห็นจากชื่อฟังก์ชั่นหลักของมันคือการให้ฟังก์ชั่นผู้พิทักษ์และบริการสำหรับเธรดอื่น ๆ เมื่อเธรดเบื้องหน้าทั้งหมดสิ้นสุดเธรดพื้นหลังจะถูกบังคับให้สิ้นสุดเพราะมันไม่มีความหมายที่จะมีอยู่ในเวลานี้
ด้ายเบื้องหน้า
คลาสสาธารณะ ForeandBackThread ขยายเธรด {Public ForeandBackThread (ชื่อสตริง) {super (ชื่อ); } public void run () {int i; สำหรับ (i = 0; i <9999; i ++) {system.out.println (this.getName ()+"-"+i); }} โมฆะคงที่สาธารณะหลัก (สตริง [] args) {foreandbackThread th = ใหม่ foreandbackThread ("เธรด A"); //th.setdaemon(true); Th.Start (); int J; สำหรับ (j = 0; j <3; j ++) {system.out.println (thread.currentthread (). getName ()+"-"+j); -เธรดลูกที่สมบูรณ์ของโปรแกรมคือ 0 ถึง 9998; หมายความว่าเธรดหลักไม่ได้พิเศษและจุดสิ้นสุดจะไม่ส่งผลกระทบต่อการทำงานของด้ายเบื้องหน้าอื่น ๆ
เธรดพื้นหลัง
คลาสสาธารณะ ForeandBackThread ขยายเธรด {Public ForeandBackThread (ชื่อสตริง) {super (ชื่อ); } public void run () {int i; สำหรับ (i = 0; i <9999; i ++) {system.out.println (this.getName ()+"-"+i); }} โมฆะคงที่สาธารณะหลัก (สตริง [] args) {foreandbackThread th = ใหม่ foreandbackThread ("เธรด A"); th.setdaemon (จริง); Th.Start (); int J; สำหรับ (j = 0; j <3; j ++) {system.out.println (thread.currentthread (). getName ()+"-"+j); -โปรแกรมไม่สามารถส่งออก 0-9998 อย่างเต็มรูปแบบและออกแสดงว่าหลังจากด้ายหลักของส่วนหน้าสิ้นสุดลง JVM บังคับให้เธรดพื้นหลังสิ้นสุด
สรุป
ข้างต้นคือทั้งหมดที่เกี่ยวกับการวิเคราะห์ตัวอย่างพื้นฐานของกระทู้ Java ในบทความนี้ฉันหวังว่ามันจะเป็นประโยชน์กับทุกคน เพื่อนที่สนใจสามารถอ้างถึงหัวข้ออื่น ๆ ที่เกี่ยวข้องในเว็บไซต์นี้ต่อไป หากมีข้อบกพร่องใด ๆ โปรดฝากข้อความไว้เพื่อชี้ให้เห็น ขอบคุณเพื่อนที่ให้การสนับสนุนเว็บไซต์นี้!