مشخصات مقاله
-
1142
-
0.0
-
2708
-
0
-
0
آموزش Java - استفاده از static synchronization در Java multithreading
آموزش Java - استفاده از static synchronization در Java multithreading
اگر یک متد را static synchronized تعریف کنید، lock بر آبجکت کلاس اعمال نمی شود بلکه بر روی خود کلاس اعمال می شود و در واقع آن متد در سطح کلاس، نه در سطح نمونه ی کلاس synchronized می باشد. به عبارت دیگر متد مربوطه از آبجکت های ساخته شده از روی کلاس پس از علامت گذاری با کلیدواژگان static synchronized نمی توانند همزمان در دسترس چند thread قرار گیرند.
مشکلاتی که در صورت عدم استفاده از static synchronization رخ می دهد
مشکلاتی که در صورت عدم استفاده از static synchronization رخ می دهد
مثال کاربردی از static synchronization
در این مثال، در تعریف متد static کلیدواژه ی synchronized را اعمال کرده و متد مورد نظر را در سطح کلاس (نه سطح آبجکت های کلاس) synchronized کرده ایم به طوری که در آن واحد تنها یک thread بتواند این متد را فراخوانی کند.
class Table{
synchronized static void printTable(int n){
for(int i=1;i<=10;i++){
System.out.println(n*i);
try{
Thread.sleep(400);
}catch(Exception e){}
}
}
}
class MyThread1 extends Thread{
public void run(){
Table.printTable(1);
}
}
class MyThread2 extends Thread{
public void run(){
Table.printTable(10);
}
}
class MyThread3 extends Thread{
public void run(){
Table.printTable(100);
}
}
class MyThread4 extends Thread{
public void run(){
Table.printTable(1000);
}
}
public class TestSynchronization4{
public static void main(String t[]){
MyThread1 t1=new MyThread1();
MyThread2 t2=new MyThread2();
MyThread3 t3=new MyThread3();
MyThread4 t4=new MyThread4();
t1.start();
t2.start();
t3.start();
t4.start();
}
}
خروجی:
2
3
4
5
6
7
8
9
10
10
20
30
40
50
60
70
80
90
100
100
200
300
400
500
600
700
800
900
1000
1000
2000
3000
4000
5000
6000
7000
8000
9000
10000
حال همین مثال را با بهره گیری از امکان کلاس های فاقد نام (anonymous class) برای ساخت آبجکت های thread و کدنویسی کمتر بار دیگر پیاده سازی می کنیم:
class Table{
synchronized static void printTable(int n){
for(int i=1;i<=10;i++){
System.out.println(n*i);
try{
Thread.sleep(400);
}catch(Exception e){}
}
}
}
public class TestSynchronization5 {
public static void main(String[] args) {
Thread t1=new Thread(){
public void run(){
Table.printTable(1);
}
};
Thread t2=new Thread(){
public void run(){
Table.printTable(10);
}
};
Thread t3=new Thread(){
public void run(){
Table.printTable(100);
}
};
Thread t4=new Thread(){
public void run(){
Table.printTable(1000);
}
};
t1.start();
t2.start();
t3.start();
t4.start();
}
}
خروجی:
1 2 3 4 5 6 7 8 9 10 10 20 30 40 50 60 70 80 90 100 100 200 300 400 500 600 700 800 900 1000 1000 2000 3000 4000 5000 6000 7000 8000 9000 10000
استفاده از قطعه کد synchronized برای پیاده سازی static synchronization و اعمال قفل بر روی متد در سطح کلاس (Synchronized block on a class lock)/synchronize کردن بخشی از متد
قطعه کد synchronized یک آبجکت از کلاس به عنوان قفل/lock در قالب پارامتر دریافت کرده و بر روی بخشی از متد printTable در سطح کلاس Table قفل اعمال می کند. .class در کد زیر به قفل متناظر آبجکت کلاس Table اشاره دارد. متد printTable(int n) که با کلیدواژگان static synchronized در سطح کلاس Table علامت گذاری شده است، معادل تعریف زیر می باشد:
static void printTable(int n) {
synchronized (Table.class) { // Synchronized block on class A
// ...
}
}