4-17-两个线程共享数据

文章目录
  1. 1. 共享数据(内存)关注点
    1. 1.1. 1.可见性(jmm-java内存模型解决)
    2. 1.2. 2.有序性(jmm)
    3. 1.3. 3.原子性(锁)
  2. 2. 线程同步(线程交替执行)
  3. 3. 线程互斥(只能一个线程操作)【特殊的线程同步】
  4. 4. 解决方案(同步/互斥)
    1. 4.1. 1.数据抽象成类,操作方法加synchronized(hashtable)
    2. 4.2. 2.数据抽象成类,在具体成员变量做同步和互斥(concurrenthashmap的分段锁,linkedblockingqueue的写入和读取两个锁; wait/notify/notifyall; lock.acquire/release)
    3. 4.3. 3. runnable对象作为一个类的内部类(?不知道怎么搞)
    4. 4.4.

共享数据(内存)关注点

1.可见性(jmm-java内存模型解决)

2.有序性(jmm)

3.原子性(锁)

线程同步(线程交替执行)

是指线程之间所具有的一种制约关系,一个线程的执行依赖另一个线程的消息,当它没有得到另一个线程的消息时应等待,直到消息到达时才被唤醒。

要解决线程交替执行但是又要保证共享资源安全,这需要使用到JAVA3个方法:wait()、notify()和nodifyAll()、这3个方法是Object类的成员方法,所以在任何类中都可以使用这3个方法。

线程互斥(只能一个线程操作)【特殊的线程同步】

是指对于共享的进程系统资源,在各单个线程访问时的排它性。当有若干个线程都要使用某一共享资源时,任何时刻最多只允许一个线程去使用,其它要使用该资源的线程必须等待,直到占用资源者释放该资源。线程互斥可以看成是一种特殊的线程同步(下文统称为同步)。

当多个线程需要访问同一资源时,要求在一个时间段内只能允许一个线程来操作共享资源,操作完毕后别的线程才能读取该资源,这叫线程的互斥。我们需要使用synchronized来给共享区域加锁,确保共享资源安全。

解决方案(同步/互斥)

1.数据抽象成类,操作方法加synchronized(hashtable)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
public class MyData {
private int j=0;
public synchronized void add(){
j++;
System.out.println("线程"+Thread.currentThread().getName()+"j 为:"+j);
}
public synchronized void dec(){
j--;
System.out.println("线程"+Thread.currentThread().getName()+"j 为:"+j);
}
public int getData(){
return j;
} }
public class TestThread {
public static void main(String[] args) {
final MyData data = new MyData();
for(int i=0;i<2;i++){
new Thread(new Runnable(){
public void run() {
data.add();
}
}).start();
new Thread(new Runnable(){
public void run() {
data.dec();
}
}).start();
}
} }

2.数据抽象成类,在具体成员变量做同步和互斥(concurrenthashmap的分段锁,linkedblockingqueue的写入和读取两个锁; wait/notify/notifyall; lock.acquire/release)

3. runnable对象作为一个类的内部类(?不知道怎么搞)