啥也别说了,换这个类就OK了也不用你自己同步了。ConcurrentHashMap<K, V>

解决方案 »

  1.   

    针对第一个问题,我想你已经有答案了,既然你都知道时间片这玩意了。
    除非你用synchronized关键字修饰这个function,那么才会出现你前面说的等待执行。
      

  2.   

    1. 如果m声明时前面没有加synchronized,那么会得到调度;如果加了,那么依次运行。
    2. 如果并发调用了HashTable的synchronized方法,会出现等待。如果a中使用了迭代器,迭代时b修改了内容,那么a会抛出异常。不知道1楼的办法能不能解决这个问题,不过synchronized(ht) {}里面进行操作就不会有并发问题了。
      

  3.   

    针对方法2,你要明白,Java对象内,有一个隐含的锁,
    这样看你操作的HashTable 的get和put两个方法,是不是synchronized修饰的,或者内部使用了synchronized关键字。
    如果两个都是,那么是等待的效果,如果只有一个是,或者没有一个是,那么可能出现所谓的不安全的情况。
      

  4.   

    1.是等待还是切换调用看m是否为同步方法,为同步方法,则线程2需等待线程1,不为同步方法,则不等待。
    2.不等待,如果这时线程2还在修改ht,cpu又转到线程1执行,线程1往下执行,要执行读取ht的时候,发现ht已被其它线程占领,这时才等待。
      

  5.   

    1问题现在明白了,但是又牵扯另一个问题:
    假如说现在有一个
    public void a(String userName){
         User user = new User();
         user.setUserName(userName);
        for(int i= 0;i<10000000;i++){
           
        }
        System.out.println(user.getUserName());
    }此时有两个线程1,2当1线程(传入“111”)将要执行完for循环的时候,
    2线程(传入“222”)执行了 user.setUserName(userName);此时1线程打印什么内容
    请详细说下原理,谢谢
    是否User user = new User();两个线程new出的user对象被分别存在1,2线程中(threadLocal)
      

  6.   

    user是一个局部变量,你有两个线程,就有两个这样的局部变量,指向了两个堆对象。
    是不会乱的。
      

  7.   

    我的看法是,2个线程调用a,生成的方法内的对象都在各个线程自己的stack里面。线程1和2生成了2个User对象,username分别是"111"和"222"。但是println不是原子的,"111""222"里面那个char先print是不确定的。
      

  8.   

    第一个问题应该是切换调用,虽然是单例模式但是并没有锁定,所以会切换调用但是使用会是一个对象
    第二个问题应该是等待,因为hashtable是同步集合