精华内容
下载资源
问答
  • Java判断线程是否结束

    千次阅读 2019-03-10 08:35:14
    JAVA判断线程是否结束应用场景主要方法实现代码 应用场景 程序中需要等待多线程任务全部执行完毕后,再执行后续操作。 主要方法 使用方法 1、确定了你开启的线程数,那么在主程序运行前。 CountDownLatch ...

    JAVA判断多线程是否结束

    应用场景

    程序中需要等待多线程任务全部执行完毕后,再执行后续操作。

    主要方法

    使用方法
    1、确定了你开启的线程数,那么在主程序运行前。
    CountDownLatch countdown = new CountDownLatch(10);//这里的10就是你的子线程数。

    2、在每个子线程结束后,调用 countdown.countDown();
    当前线程调用此方法,则计数减一

    3、在主线程里启动多线程的方法后面添加:countdown.await();//这里进行同步等待
    调用此方法会一直阻塞当前线程,直到计时器的值为0。

    4、等所有子线程结束后,执行 countdown.await()后面的代码。

    实现代码

    public class CountDownLatchDemo { 
        final static SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); 
        public static void main(String[] args) throws InterruptedException {
       		//步骤1:确定开启的线程数,声明CountDownLatch对象 ,对象需要作为入参,传给多线程的构造函数
            CountDownLatch latch=new CountDownLatch(2);
            Worker worker1=new Worker("zhang san", 5000, latch); 
            Worker worker2=new Worker("li si", 8000, latch); 
            worker1.start();// 
            worker2.start();// 
            //步骤3、4、调用await放过,等待所有线程完成工作 
            latch.await();
            System.out.println("全部线程执行完毕!可以开始后续操作:" + sdf.format(new Date())); 
        } 
    
        static class Worker extends Thread{ 
            String workerName;   
            int workTime; 
            CountDownLatch latch; 
            public Worker(String workerName ,int workTime ,CountDownLatch latch){ 
                 this.workerName=workerName; 
                 this.workTime=workTime; 
                 this.latch=latch; 
            } 
            public void run(){ 
                System.out.println("Worker "+workerName+" do work begin at "+sdf.format(new Date())); 
                doWork();//工作了 
                System.out.println("Worker "+workerName+" do work complete at "+sdf.format(new Date())); 
                //步骤2、每个线程run方法完成工作后,将计数器减一 
                latch.countDown();
     
            } 
                 
            private void doWork(){ 
                try { 
                    Thread.sleep(workTime); 
                } catch (InterruptedException e) { 
                    e.printStackTrace(); 
                } 
            } 
        } 
    } 
    
    展开全文
  • 如何判断 Java 线程并发的安全性

    千次阅读 2014-11-14 10:09:03
    现在给你一段代码,你如何判断是否线程安全的?又如何改进呢?在这里,我们简单介绍一下Java内部是如果保证线程安全的。一切的关键就在: 高效利用并发,同时也必须保证JMM三大特性的有序性。只有保证了...

    前言

    在高并发的时代中,如何写出高质量的并发程序一直是一个令人头疼的事情。现在给你一段代码,你如何判断它是否是线程安全的?又如何改进呢?在这里,我们简单介绍一下Java内部是如果保证线程安全的。一切的关键就在:

    高效利用并发,同时也必须保证JMM三大特性的有序性。只有保证了有序性,才能在代码正确执行的前提下去求追更高的效率。而这个王牌就是:先行发生原则

    想一想,如果Java中所有的同步操作都交给synchronized或者volatile来做,那将是很麻烦的。考虑你要写一个并发环境下的程序,你得花费大半的精力来实现并发的线程安全性。而这对于新手来说,几乎是不可能完成的任务。所以Java定义了一些规则,使得Java会自动判断数据是否存在竞争,线程是否安全等。通过这个先行并发原则,Java可以一揽子解决并发环境下两个操作之间是否可能存在冲突的所有问题。那么,什么是先行发生呢?

    一、先行发生原则

    离散数学中曾经定义了“偏序”的概念,在Java中正是使用了这个概念。偏序通俗的来理解就是拓扑结构,一个DAG。如果操作A先行发生于B,那么B将能观察到A所做的所有事情(包括修改变量、发送消息、调用方法等)。这个可以用例子来说明:

    1 //线程A
    2 i = 1;
    3 
    4 //线程B
    5 j = i;
    6 
    7 //线程C
    8 i = 2;

    如果只考虑A和B,并且保证A先行发生于B,那么B的值是多少?答案很显然是1。依据有两个:

    1. 根据先行发生的偏序关系,i的值的改变可以被j观察到
    2. 在线程C修改i值之前,线程A结束之后没有其他线程会修改i。

    但是如果考虑C线程,很悲桑,j的值会不确定。因为线程B和线程C没有先行发生定义的偏序,意思就是C可以发生在B前,B后的任意位置,如果C发生在A/B之间,那么显然j的值就是2了。所以线程B就不具备多线程安全性。为了解决这种问题,JMM定义了一些”天然的“先行发生关系来保证多线程的安全。假如所有的操作都像A/B定义好了偏序关系,那么并发就不会有任何难度了。但是为了更灵活的使用,Java只对一些场景定了先行发生原则,所以遇到这几个规则范围内的问题,我们就不需要考虑并发的各种问题,Java会自动帮我们解决。所以,以下操作无须任何同步手段就能保证并发的成功

    • 程序次序规则:一个线程内,代码的执行会按照程序书写的顺序
    • 管程锁定原则:对同一变量的unlock操作先行发生于后来的lock操作
    • volatile变量规则:对一个volatile的写操作先行发生于后来的读操作
    • 线程启动原则:Thread的start()先行发生于线程内的所有动作
    • 线程终止原则:线程内的所有动作都先行发生于线程的终止检测
    • 线程中断原则:对线程调用interrupt()先行发生于被中断的代码检测到是否有中断发生
    • 对象终结原则:一个对象的初始化操作先行发生于finalize()方法
    • 传递性:A先行发生于B,B先行发生于C,那么A先行发生于C

    二、先行发生原则的应用

    上面我们介绍了先行发生原则,下面我们就用实例来看看,它是如何工作的。考虑这样一段代码:

    1 private int value = 0;
    2 
    3 public int getValue() {
    4   return this.value;
    5 }
    6 
    7 public void setValue(int value) {
    8   this.value = value;
    9 }

    上面是一段再普通不过的getter/setter方法了,现在假设有A/B两个线程。线程A先(时间上的先后)调用了setValue(2),然后线程B调用了同一个对象的getValue(),那么线程B收到的返回值是多少呢?

    那么,我们就用前面介绍的先行发生原则来判断一下:

    • 因为A/B不是一个线程,所以无法使用程序次序原则
    • 因为没有synchronized,所以不存在lock/unlock操作,无法使用管程锁定原则
    • 没有volatile修饰,不能使用volatile变量原则
    • 因为是两个独立的线程,所以线程启动、终止、终端原则都不能使用
    • 因为不涉及对象的初始化和finalize(),所以无法使用对象终结原则
    • 因为根本就没有一个先行发生原则,所以也不能使用传递性

    综上所述,我们发生A/B之间不满足所有的先行发生原则。所以A/B线程的操作不是线程安全的。如果想要线程安全,必须通过程序员自己去实现。这里提供2个方法:

    1. 将getter/setter方法添加synchronized修饰,使之满足管程锁定原则
    2. 把value定义为volatile,因为setter中对value的修改不依赖value的原值,所以符合volatile的使用场景(一定要符合前提,如果这里方法是value++就肯定不行了),然后套用volatile变量原则就可以保证了

    通过上面的例子,我们可以得出一个结论:

    时间上先发生的操作是无法保证“先行发生”的。那如果一个操作满足”先行发生“的定义,是否就一定是时间上的先发生呢?很遗憾,这个结论也是不成立的。一个典型的例子就是提到过的指令重排序

    1 //以下操作在同一个线程内执行
    2 int i = 1;
    3 int j = 2;

    既然是同一个线程,那么肯定满足程序次序原则。所以int i = 1;先行发生于int j = 2;,但是int j = 2;完全可能被处理器先处理,这并不影响先行发生原则的正确性(我猜测是JVM在满足先行发生原则的基础上,会对某些无关语句进行指令重排序优化),从而我们无法在线程中感知。Java有句话是这样说的就是这个道理:

    线程内观察指令全部是串行的,而在其他线程观察那个线程,会发现内部程序的执行是杂乱无章的。但JVM会保证结果的正确性

    综合上面的解释我们就知道了:

    时间上的先后顺序与先行发生原则之间没有太大的关系,所以我们衡量并发安全问题的时候不能受到时间顺序的干扰,一切必须以先行发生原则为准

    展开全文
  • 这篇学习关于Thread类的两个方法,第一个是获取当前线程对象,返回的是一个Thread对象。第二个方法是我们自动化中经常使用的,线程休眠。 1.currentThread() 获取的是当前线程对象,是对象不是对象名称,如果要...

    这篇学习关于Thread类的两个方法,第一个是获取当前线程对象,返回的是一个Thread对象。第二个方法是我们自动化中经常使用的,线程休眠。

    1.currentThread()

    获取的是当前线程对象,是对象不是对象名称,如果要获取名称,需要对象.getName()实现。

    package thread;
    
    public class Demo5_Thread {
    
    	public static void main(String[] args) {
    		
    		new Thread() {
    			public void run() {
    				System.out.println(this.getName() +": aaaaa");
    			}
    		}.start();
    		
    		new Thread(new Runnable() {
    			
    			public void run() {
    				System.out.println(Thread.currentThread().getName()+": bbbb");
    			}
    		}).start();
    		
    		//main方法打印线程名称
    		System.out.println(Thread.currentThread().getName());
    	}
    
    }
    

    运行结果:

    Thread-0: aaaaa
    main
    Thread-1: bbbb
    

    这个打印结果,也说明了,多线程中,main方法本身就是一个单独线程执行,而且执行顺序并不会像代码写的从上往下的顺序。

    2.线程休眠

    休眠就是让线程停顿下来,支持不同时间单位的中断。这个方法是Thread.sleep(xxx毫秒)。我们写自动化脚本经常需要用到它。

    package thread;
    
    public class Demo5_Thread {
    
    	public static void main(String[] args) throws InterruptedException {
    		
    		new Thread() {
    			public void run() {
    				for(int i = 0; i< 10; i ++) {
    					try {
    						Thread.sleep(1000);
    					} catch (InterruptedException e) {
    						
    						e.printStackTrace();
    					}
    					System.out.println(this.getName() +": aaaaa");
    				}
    				
    			}
    		}.start();
    		
    		new Thread(new Runnable() {
    			
    			public void run() {
    				for(int i = 0; i< 10; i ++) {
    					try {
    						Thread.sleep(1000);
    					} catch (InterruptedException e) {
    						
    						e.printStackTrace();
    					}
    					System.out.println(Thread.currentThread().getName()+": bbbb");
    				}
    				
    			}
    		}).start();
    		
    		//main方法打印线程名称
    		System.out.println(Thread.currentThread().getName());
    	}
    
    }
    

    运行之后,可以看到间隔一秒输出一个。

    展开全文
  • 考虑一个场景,在运行时你必须找到一个Java线程是否对特定的对象加锁,例如,确认NewsReader线程是否持有NewsPaper对象的锁?如果这个问题出现在任何核心的Java面试中,那么我会自动假设可能有至少两个答案,一个是...

    本文为本博主翻译,未经允许,严禁转载

    简介

    考虑一个场景,在运行时你必须确认一个Java线程是否持有特定对象的锁,例如,确认NewsReader线程是否持有NewsPaper对象的锁?如果这个问题出现在任何核心的Java面试中,那么我会自动假设可能有至少两个答案,一个是难以获得的原始答案,程序员想根据基本原理找出答案,而另一个可能是一些很少使用的Java API调用,顺便说一下,这实际上是在接受我最大的全球投资银行之一面试时是被问到的问题。投资银行领域,特别是现金股票, 需要强大的核心Java和多线程技能来构建高性能,低延迟的Java应用程序,以处理每天数百万个订单。

    2种方法来查找线程是否持有Java对象的锁

    在这里,我正在给出我的答案以及我在面试后发现的东西。是的,非常不幸,面试官在电话面试中询问我时,我不知道答案。我设法提供了基于同步块和wait()和notify()方法的属性的逻辑,如第一个答案所示,但他当时并不满意。
    许多面试官期望得到他们认为最好的答案,他们会推动你继续寻找直到你放弃,或者你给他们他们想要的答案。这在面试中非常常见。
    1)我想过,当wait()和notify()方法从非同步上下文中调用时会抛出IllegalMonitorStateException,所以我说我会调用newspaper.wait(),如果这个调用抛出异常,这意味着Java中的线程并未持有锁,否则线程持有锁。


    2)后来我发现线程有一个名为holdsLock(Object obj)的静态方法,它根据线程是否对传递的对象持有锁来返回true或false。
    您还可以学习Cay S. Horstmann的Core Java Volume 1  -  Fundamentals或Java Threads 2n​​d Editon,以了解更多关于Java中的Thread类的内容。第一本书是以最容易的方式学习Java秘密的最佳书籍之一。
    这就是如何找到一个线程是否拥有Java中某个特定对象的锁。如果您需要在Java应用程序中知道这一点,则应该使用java.lang.Thread类的holdsLock()方法。

    意见,建议,创新更好的答案总是受欢迎的。

    原文链接

    How to check if a thread holds lock on a particular object in Java

    展开全文
  • Tread类中提供了两种方法来判断线程的状态是不是停止的。 this.interrupted():测试当前线程是否已经中断。this.isInterrupted():测试线程是否已经中断。 1)interrupted()方法:  interrupted()方法是静态的...
  • java判断线程是否是停止状态

    千次阅读 2017-11-18 13:30:02
    Thread.java类里提供了两种方法 (1)this.interrupted():测试当前线程是否已经中断。 (2)this.isInterrupted():测试线程是否已经中断。 interrupted()方法声明如下; public static boolean interrupted() ...
  • 万字图解Java线程

    万次阅读 多人点赞 2020-09-06 14:45:07
    java线程我个人觉得是javaSe中最难的一部分,我以前也是感觉学会了,但是真正有多线程的需求却不知道怎么下手,实际上还是对多线程这块知识了解不深刻,不知道多线程api的应用场景,不知道多线程的运行流程等等,...
  • 线程---java判断线程结束

    万次阅读 2016-10-25 16:00:36
    需求应用场景方法一isTerminatedshutdownvoid ...抛出:SecurityException - 如果安全管理器存在并且关闭,此 ExecutorService 可能操作某些不允许调用者修改的线程(因为它没有保持RuntimePermission("modifyThread
  • 这个没有什么需要描述的,就是创建(new )一个新的线程对象 就绪状态 线程对象创建后、调用对象的start()方法,该线程将会处于可运行线程池中,变为可运行后等待获取CPU的使用权 运行状态 就是这就绪状态下的线程...
  • java String 对象为空格时,长度不为0 通常判断null,字符串或者空格方式如下:  if (emailAddr == null || emailAddr.length()==0 || emailAddr.equals("") || emailAddr.trim().isEmpty()) {  addressName = ...
  • 判定规则: 无论何时,只要存在多于一个线程访问给定的状态变量,而其中某个线程会写入该变量...一般将涉及的变量修改的方法改synchronized修饰的方法public synchronized void change(){} ,将可变对象用synchroniz
  • Java线程学习(吐血超详细总结)

    万次阅读 多人点赞 2015-03-14 13:13:17
    本文主要讲了java中多线程的使用方法、线程同步、线程数据传递、线程状态及相应的一些线程函数用法、概述等。
  • Java线程

    万次阅读 多人点赞 2021-06-11 16:28:49
    Java线程Java线程线程的创建线程常见方法线程的状态线程的优先级守护线程线程Java线程池线程池的创建线程池的参数线程池的使用线程不安全问题Java中的锁synchronized同步方法synchronized同步语句块...
  • 本文将全面讲解判断Java对象存活的方式,希望你们会喜欢
  • 通过 Thread 类中的 start() 方法通知...在 Java 中可以使用 isAlive() 方法来测试线程是否已经启动 class MyThread implements Runnable{//实现 Runnable 接口 public void run(){//覆写 Thread 类中的 run() 方法...
  • Java线程状态

    千次阅读 2014-11-29 19:03:17
    线程跟人类一样拥有自己的生命周期,一条线程从创建到执行完毕的过程即是线程的生命周期,此过程可能在不同时刻处于不同的状态,线程状态正是这小节的主题,线程到底有多少种状态?不同状态之间是如何转化的? 对于...
  • 前几篇:Java线程编程-(1)-线程安全和锁Synchronized概念Java线程编程-(2)-可重入锁以及Synchronized的其他基本特性Java线程编程-(3)-线程本地ThreadLocal的介绍与使用Java线程编程-(4)-线程间通信...
  • Java线程(二)——Java对象的Monitor机制

    千次阅读 多人点赞 2018-08-03 16:54:17
    Java线程学习(二)——Java对象的Monitor机制与notify/wait方法 概述 Java虚拟机给每个对象和class字节码都设置了一个监听器Monitor,用于检测并发代码的重入,同时在Object类中还提供了notify和wait方法来对...
  • Java线程(九):Condition-线程通信更高效的方式

    万次阅读 多人点赞 2012-04-20 14:49:39
    接近一周没更新《Java线程》专栏了,主要是这周工作上比较忙,生活上也比较忙,呵呵,进入正题,上一篇讲述了并发包下的Lock,Lock可以更好的解决线程同步问题,使之更面向对象,并且ReadWriteLock在处理同步时更...
  • Java的内存区域中,有哪些区域是垃圾收集器所关注的?怎么判断一个对象是不是需要回收?对象起死回生又是怎么回事?
  • Java线程超详解

    万次阅读 多人点赞 2019-06-11 01:00:30
    随着计算机的配置越来越高,我们需要将进程进一步优化,细分为线程,充分提高图形化界面的多线程的开发。这就要求对线程的掌握很彻底。 那么话不多说,今天本帅将记录自己线程的学习。 线程的相关API //获取当前...
  • 本文就将讲解JVM在回收对象之前,如何判断一个对象是否应该被回收。 在此之前,我们先来复习一个和Java对象回收有关的知识,那便是finalize方法,这是一个在Object类中定义的方法,如果我们重写了finalize方法,...
  • 同一个线程对象能否多次调用start方法,搞清楚这个问题,首先需要了解线程的生命周期 一、线程生命周期 更多线程状态细节描述可查看Thread内部枚举类:State 从上图线程状态转换图可以看出: 新建(NEW)状态是...
  • JAVA线程知识点

    千次阅读 2018-09-12 18:30:12
    java线程知识点大全 java线程知识点大全 1、 什么是线程? 1、 什么是线程? 线程是操作系统能够进行运算的最小单位,他包含在实际的运作单位里面,是进程中的实际运作单位。 程序员可以通过它进行...
  • Java线程片——线程的关闭

    千次阅读 2018-10-24 11:38:46
    在我们寻求Java线程的关闭关闭方式的时候,我们也许会按住Ctrl键进入到Thread类中阅读源码,很快的我们就能找到一个stop()方法。似乎stop()方法就是结束线程的方法,但是事实恰恰与我们的猜想相反。stop()方法太过于...
  • Java线程:概念与原理

    千次阅读 2017-03-29 21:10:42
    Java线程创建与启动 Java线程线程栈模型与线程的变量 Java线程线程状态的转换 Java线程线程的同步与锁 Java线程线程的交互 Java线程线程的调度-休眠 Java线程线程的调度-优先级 Java线程线程的调度-让步 Java线程...
  • java线程join方法

    千次阅读 2020-04-16 23:04:39
    java线程join方法 1.join方法 ​ join方法的作用是进行线程插队,也就是说调用了join方法的线程相对于调用它的上级线程拥有跟高的执行权。调用join方法的线程的上级线程必须等待调用join方法的线程执行完成才能继续...
  • Java线程Dump分析

    千次阅读 2019-10-29 08:48:43
    每一个Java虚拟机都有及时生成所有线程在某一点状态的thread-dump的能力,虽然各个 Java虚拟机打印的thread dump略有不同,但是 大多都提供了当前活动线程的快照,及JVM中所有Java线程的堆栈跟踪信息,堆栈信息一般...
  • Java线程探究-Lock对象锁条件变量

    千次阅读 2017-04-12 18:08:50
    Lock锁的条件变量 设想这样的一种情况,现在有一个盘子,一个线程负责往盘子里放一个苹果,一个线程从盘子取一个苹果,如何保证线程A放一个苹果,线程B就把这个苹果取...应该是加条件判断线程A每次放的时候,判断
  • 理解了线程同步和线程通信之后,再来看本文的知识点就会简单的多了,本文是做传统线程知识点的一个补充。有人会问:JDK5之后有了更完善的处理多线程问题的类(并发包),我们还需要去了解传统线程吗?答:需要。

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 324,512
精华内容 129,804
关键字:

判断java线程对象是否为空

java 订阅