-1

myCode is following:

I want to know why zhangsan and lisi are both can print : 李四9锁对象:1522503870 张三9锁对象:1522503870

public class TicketConsumer implements Runnable {
    private Integer i;

    public TicketConsumer(int i) {
        super();
        this.i = i;
    }

    @Override
    public void run() {
        while (true) {
           
            System.out.println(Thread.currentThread().getName() + i + "锁对象before:" + System.identityHashCode(i));
            
            synchronized (i) {
                System.out.println(Thread.currentThread().getName() + i + "锁对象:" + System.identityHashCode(i));
                if (i > 0) {
                    try {
                        Thread.sleep(100);    // 模拟抢票延迟
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    System.out.println(Thread.currentThread().getName() + "抢到了第" + i-- + "张票");
                } else {
                    return;
                }
            }
        }
    }

    public static void main(String[] args) {
        TicketConsumer ticket = new TicketConsumer(new Integer(10));
        Thread t1 = new Thread(ticket, "张三");
        Thread t2 = new Thread(ticket, "李四");
        t1.start();
        t2.start();
    }
}

the result is :

张三10锁对象before:1417180225
李四10锁对象before:1417180225
张三10锁对象:1417180225
张三抢到了第10张票
张三9锁对象before:1522503870
李四9锁对象:1522503870
张三9锁对象:1522503870
李四抢到了第9张票
李四8锁对象before:2045992545
李四8锁对象:2045992545
张三抢到了第9张票

I want to know why 张三 and 李四 both can get: 李四9锁对象:1522503870 张三9锁对象:1522503870

River
  • 9
  • 2
  • Because ```Integer``` is immutable. See: [synchronized-block-for-an-integer-object](https://stackoverflow.com/questions/16280699/synchronized-block-for-an-integer-object) – zysaaa Jan 14 '22 at 11:47
  • you can see that System.identityHashCode(i) changes, so another thread that was waiting outside the synchronized block can now enter it. but the most important thing,i want to know why another thread has same System.identityHashCode(i) can enter the synchronized block – River Jan 14 '22 at 12:32

1 Answers1

0

I might be wrong, but when you do i--, you can see that System.identityHashCode(i) changes, so another thread that was waiting outside the synchronized block can now enter it. Synchronizing on objects that change identity/reference is not a good idea, try synchronizing on a Stack and debug with stack.push(...): that will not change reference.

rikyeah
  • 1,896
  • 4
  • 11
  • 21
  • thank you,as you say,when you do i--, you can see that System.identityHashCode(i) changes, so another thread that was waiting outside the synchronized block can now enter it. – River Jan 14 '22 at 12:30
  • but the most important thing,i want to know why another thread has same System.identityHashCode(i) can enter the synchronized block – River Jan 14 '22 at 12:31
  • the new thread that enters the synchronized block has the **previous** value of i, and enters because the other thread that previously had a lock on it, released it. This results in 2 equal outputs. – rikyeah Jan 14 '22 at 12:34
  • the other thread that previously had a lock on it, released it. why this thread can enter synchronized block After the new thread that enters the synchronized block. – River Jan 14 '22 at 13:00