C#记录(四):放弃Stop()、Suspend()和Resume()

转:https://www.jianshu.com/p/7a123f212ca1

具体参考实例:https://mp.csdn.net/console/editor/html/105405707

一、不安全的Stop()、Suspend()和Resume()

1.即刻停止run()方法中剩余的全部工作,包括在catch或finally语句中,并抛出ThreadDeath异常(通常情况下此异常不需要显示的捕获),因此可能会导致一些清理性的工作的得不到完成,如文件,数据库等的关闭。

2.会立即释放该线程所持有的所有的锁,导致数据得不到同步的处理,出现数据不一致的问题。

public class Main{

    public static void main(String [] args) throws Exception{

        TestObject testObject = new TestObject();
        Thread t1 = new Thread(){
        public void run(){
                try {
                    testObject.print("1", "2");
                } catch (Exception e) {

                    // TODO Auto-generated catch block

                    e.printStackTrace();
                }
            }
        };

        t1.start();
        Thread.sleep(1000);
        t1.stop();
        System.out.println("first : " + testObject.getFirst() + " " + "second : " + testObject.getSecond());
    }
}


class TestObject{
    private String first = "ja";
    private String second = "va";

    public synchronized void print(String first, String second) throws Exception{
        this.first = first;
        Thread.sleep(10000);
        this.second = second;

    }

    public String getFirst() {

        return first;

    }

    public void setFirst(String first) {

        this.first = first;

    }

    public String getSecond() {

        return second;

    }

    public void setSecond(String second) {

        this.second = second;

    }
}

从上面的程序验证结果来看,stop()确实是不安全的。它的不安全主要是针对于第二点:释放该线程所持有的所有的锁。一般任何进行加锁的代码块,都是为了保护数据的一致性,如果在调用thread.stop()后导致了该线程所持有的所有锁的突然释放,那么被保护数据就有可能呈现不一致性,其他线程在使用这些被破坏的数据时,有可能导致一些很奇怪的应用程序错误。

二、suspend()和resume()必须要成对出现,否则非常容易发生死锁。

suspend()和resume()必须要成对出现,否则非常容易发生死锁。
因为suspend方法并不会释放锁,如果使用suspend的目标线程对一个重要的系统资源持有锁,那么没任何线程可以使用这个资源直到要suspend的目标线程被resumed,如果一个线程在resume目标线程之前尝试持有这个重要的系统资源锁再去resume目标线程,这两条线程就相互死锁了,也就冻结线程。

举个例子:

public class Main{

    public static void main(String [] args) throws Exception{

        TestObject testObject = new TestObject();

        Thread t1 = new Thread(){

            public void run(){

                testObject.print();
            }
        };

        t1.setName("A");

        t1.start();

        Thread.sleep(1000);

        Thread t2 = new Thread(){

            public void run(){

                System.out.println("B已启动,但进入不到print方法中");

                testObject.print();
            }

        };

        t2.setName("B");

        t2.start();
    }
}

class TestObject{

    public synchronized void print(){

        if(Thread.currentThread().getName().equals("A")){

            System.out.println("A 线程 独占该资源了");

            Thread.currentThread().suspend();
        }
    }
}

三、第三种结论:suspend和resume就是废的

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值