การซิงโครไนซ์ใน Java: อะไรอย่างไรและทำไม

บทความเกี่ยวกับการซิงโครไนซ์ใน Java นี้จะช่วยแนะนำวิธีการเรียนรู้เกี่ยวกับการซิงโครไนซ์โปรแกรมแบบมัลติเธรด

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



ฉันจะพูดถึงหัวข้อตามลำดับนี้:

มาเริ่มกันเลย!

เหตุใดจึงใช้การซิงโครไนซ์ใน Java



หากคุณเริ่มต้นด้วยเธรดอย่างน้อยสองเธรดภายในโปรแกรมอาจมีโอกาสที่เธรดหลายเธรดพยายามเข้าถึงทรัพยากรเดียวกัน มันยังสามารถสร้างผลลัพธ์ที่ไม่คาดคิดเนื่องจากปัญหาการเกิดพร้อมกัน

ไวยากรณ์ :

ซิงโครไนซ์ (objectidentifier) ​​{// เข้าถึงตัวแปรที่แชร์และทรัพยากรที่ใช้ร่วมกันอื่น ๆ }

ตัวอย่างเช่น, พยายามเขียนภายในไฟล์ที่เทียบเท่า ซึ่งอาจทำให้ข้อมูลเสียหายเนื่องจากเธรดหนึ่งสามารถแทนที่ข้อมูลหรือเมื่อเธรดกำลังเปิดไฟล์ไฟล์เดียวกันในเวลาเดียวกันเธรดอื่นอาจปิดไฟล์เดียวกันจำเป็นต้องซิงโครไนซ์การทำงานของเธรดหลายชุด สิ่งนี้สามารถดำเนินการได้โดยใช้แนวคิดที่เรียกว่า onitors .



  • แต่ละ เชื่อมโยงกับจอภาพซึ่งเธรดสามารถล็อกหรือปลดล็อกได้
  • ครั้งละหนึ่งเธรดเท่านั้นที่สามารถล็อคจอภาพได้
  • Java ภาษาการเขียนโปรแกรมเป็นวิธีที่สะดวกมากในการสร้างเธรดและซิงโครไนซ์งานโดยใช้ ซิงโครไนซ์แล้ว บล็อก
  • นอกจากนี้ยังเก็บทรัพยากรที่ใช้ร่วมกันไว้ภายในบล็อกนี้โดยเฉพาะ

บล็อกที่ซิงโครไนซ์ใน Java ถูกทำเครื่องหมายด้วย ซิงโครไนซ์แล้ว คำสำคัญ. บล็อกนี้ใน Java จะซิงโครไนซ์กับวัตถุบางอย่างบล็อกทั้งหมดที่ซิงโครไนซ์บนออบเจ็กต์เดียวกันสามารถมีเธรดเดียวที่ดำเนินการภายในทีละรายการ เธรดอื่น ๆ ทั้งหมดที่พยายามเข้าสู่บล็อกที่ซิงโครไนซ์จะถูกบล็อกจนกว่าเธรดภายในบล็อกที่ซิงโครไนซ์จะออกจากบล็อก

ประเภทของการซิงโครไนซ์

โดยทั่วไปมีการซิงโครไนซ์สองประเภท พวกเขาคือ:

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

อย่าเข้าไปดูรายละเอียดของประเภทเหล่านี้และพยายามทำความเข้าใจว่ามีอะไรบ้าง .

ล็อคใน Java

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

จาก Java 5 แพ็กเกจ java.util.concurrent.locks มีการใช้งานการล็อกจำนวนมาก

iso 9000 เทียบกับ six sigma

นี่คือลักษณะของล็อค:

ล็อคคลาสสาธารณะ {private boolean isLocked = false public synchronized void lock () พ่น InterruptedException {while (isLocked) {wait ()} isLocked = true} public synchronized void unlock () {isLocked = false inform ()}}

เมธอด lock () จะล็อกอินสแตนซ์ Lock เพื่อให้เธรดทั้งหมดที่โทร lock () ถูกบล็อกจนกว่าจะดำเนินการ Unlock ()

มัลติเธรดโดยไม่ต้องซิงโครไนซ์

นี่คือตัวอย่างง่ายๆที่พิมพ์ค่าตัวนับตามลำดับและทุกครั้งที่เราเรียกใช้มันจะสร้างผลลัพธ์ที่แตกต่างกันตามความพร้อมใช้งานของ CPU ต่อเธรด ลองดู!

คลาสมัลติเธรด {โมฆะสาธารณะ printCount () {ลอง {สำหรับ (int i = 5 i<0 i--) { System.out.println('Counter --- ' + i ) } } catch (Exception e) { System.out.println('Thread interrupted.') } } } class Thread extends Multithread { private Thread t private String threadName Multithread MT Thread( String name, Multithread mt) { threadName = name MT= mt } public void run() { MT.printCount() System.out.println('Thread ' + threadName + ' exiting.') } public void start () { System.out.println('Starting ' + threadName ) if (t == null) { t = new Thread (this, threadName) t.start () } } } public class TestThread { public static void main(String args[]) { Multithread MT = new Multithread() Thread t = new Thread( 'Thread - 1 ', MT) Thread t1 = new Thread( 'Thread - 2 ', MT) t.start() t1.start() // wait for threads to end try { t.join() t1.join() } catch ( Exception e) { System.out.println('Interrupted') } } }

ผลลัพธ์ของโปรแกรมข้างต้นในสิ่งนี้:

เอาท์พุท - การซิงโครไนซ์ใน Java- Edureka

มัลติเธรดพร้อมการซิงโครไนซ์

นี่เป็นตัวอย่างเดียวกับด้านบน แต่จะพิมพ์ค่าตัวนับตามลำดับ ทุกครั้งที่เราเรียกใช้มันจะให้ผลลัพธ์เดียวกัน

class Multithread {public void printCount () {try {for (int i = 5 i> 0 i--) {System.out.println ('Counter ---' + i)}} catch (Exception e) {System. out.println ('Thread interrupted.')}}} class Thread ขยาย Multithread {private Thread t private String threadName Multithread MT Thread (String name, Multithread mt) {threadName = name MT = mt} public void run () {synchronized ( MT) {MT.printCount ()} System.out.println ('เธรด' + threadName + 'exiting.')} โมฆะสาธารณะ start () {System.out.println ('เริ่มต้น' + threadName) if (t == null) {t = new Thread (this, threadName) t.start ()}}} คลาสสาธารณะ TestThread {public static void main (String args []) {Multithread MT = new Multithread () Thread T = new Thread ('Thread - 1 ', MT) เธรด T1 = เธรดใหม่ (' เธรด - 2 ', MT) T.start () T1.start () // รอให้เธรดสิ้นสุดการลอง {T.join () T1.join ()} จับ (ข้อยกเว้นจ) {System.out.println ('Interrupted')}}

ผลลัพธ์เป็นภาพด้านล่าง:

ตัดแต่ง () ใน java

คีย์เวิร์ดที่ซิงโครไนซ์

คำหลักที่ซิงโครไนซ์ ทำเครื่องหมายบล็อกหรือวิธีการเป็นส่วนสำคัญ ส่วนที่สำคัญคือการที่เธรดเดียวเท่านั้นที่ดำเนินการในแต่ละครั้งและเธรดจะยึดล็อกสำหรับส่วนที่ซิงโครไนซ์ นี้ ซิงโครไนซ์ คำหลักช่วยในการเขียน พร้อมกัน ส่วนของแอปพลิเคชันใด ๆ นอกจากนี้ยังปกป้องทรัพยากรที่ใช้ร่วมกันภายในบล็อก

คำหลักที่ซิงโครไนซ์สามารถใช้กับ:

เราจะมาพูดถึงบล็อกโค้ด

คำหลักที่ซิงโครไนซ์: บล็อกรหัส

ไวยากรณ์

ไวยากรณ์ทั่วไปสำหรับการเขียนบล็อกซิงโครไนซ์คือ:

ซิงโครไนซ์ (lockObject) {// synchronized statement}

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

บันทึก :

  • หากด้ายเข้าสู่โหมดสลีป (โดยใช้ นอน() วิธีการ) จากนั้นจะไม่คลายล็อก ในช่วงเวลาสลีปนี้จะไม่มีเธรดใดที่ดำเนินการคำสั่งบล็อกที่ซิงโครไนซ์
  • การซิงโครไนซ์ Java จะโยน NullPointerException หากใช้วัตถุล็อคใน ' ซิงโครไนซ์ (ล็อค) ‘เป็นโมฆะ

ตอนนี้เรามาดูวิธีการกัน

คำหลักที่ซิงโครไนซ์: วิธีการ

ไวยากรณ์

ไวยากรณ์ทั่วไปสำหรับการเขียน a วิธีการซิงโครไนซ์ คือ:

วิธีการซิงโครไนซ์ (พารามิเตอร์) {// รหัสที่ซิงโครไนซ์}

ที่นี่ lockObject เป็นเพียงการอ้างอิงถึงวัตถุที่มีการล็อคเชื่อมโยงกับจอภาพซึ่งแสดงถึงคำสั่งที่ซิงโครไนซ์

เช่นเดียวกับบล็อกที่ซิงโครไนซ์เธรดจะต้องได้รับการล็อกบนอ็อบเจ็กต์มอนิเตอร์ที่เชื่อมต่อด้วยวิธีการซิงโครไนซ์ ในกรณีของวิธีการซิงโครไนซ์วัตถุล็อคคือ:

  • วัตถุ '.class' - ถ้าวิธีการที่กำหนดคือ คงที่ .
  • วัตถุ 'this' - ถ้าเป็นวิธีการ ไม่คงที่ . 'this' คือการอ้างอิงถึงวัตถุปัจจุบันที่มีการเรียกใช้วิธีการซิงโครไนซ์

คีย์เวิร์ดที่ซิงโครไนซ์ Java คือ re-entrant ในธรรมชาติ. หมายความว่าหากวิธีการซิงโครไนซ์เรียกใช้วิธีการซิงโครไนซ์อื่นซึ่งต้องใช้การล็อกเดียวกันเธรดปัจจุบันที่ถือล็อกจะสามารถเข้าสู่วิธีการนั้นได้โดยไม่ต้องรับการล็อก

ให้เราไปที่หัวข้อสุดท้ายของบทความนี้และชี้ให้เห็นความแตกต่างที่สำคัญระหว่างคำหลักที่ซิงโครไนซ์และบล็อกการซิงโครไนซ์

ความแตกต่างระหว่างคีย์เวิร์ดที่ซิงโครไนซ์และบล็อกซิงโครไนซ์

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

สิ่งนี้นำเราไปสู่ตอนท้ายของบทความนี้ซึ่งเราได้พูดคุยกันว่าการซิงโครไนซ์ใน Java ทำงานอย่างไร หวังว่าคุณจะชัดเจนกับทุกสิ่งที่แบ่งปันกับคุณในบทช่วยสอนนี้

ตรวจสอบไฟล์ โดย Edureka บริษัท การเรียนรู้ออนไลน์ที่เชื่อถือได้ซึ่งมีเครือข่ายผู้เรียนที่พึงพอใจมากกว่า 250,000 คนกระจายอยู่ทั่วโลก เราพร้อมที่จะช่วยเหลือคุณในทุกขั้นตอนในการเดินทางของคุณสำหรับการเป็นนอกเหนือจากคำถามสัมภาษณ์ java นี้เรามาพร้อมกับหลักสูตรที่ออกแบบมาสำหรับนักเรียนและมืออาชีพที่ต้องการเป็น Java Developer

มีคำถามสำหรับเรา? โปรดระบุไว้ในส่วนความคิดเห็นของ 'การซิงโครไนซ์ใน Java ' บทความและเราจะติดต่อกลับโดยเร็วที่สุด