什么是线程
要了解线程,要先了解进程
-进程
进程是指可执行程序并存放在计算机存储器的一个指令序列,它是一个动态执行的过程。(平时:)
-线程
线程是比进程还要小的运行单位,一个进程包含多个线程。(线程可以看成是一个子程序)
线程的创建
-法一:创建一个Thread类(位于java.lang包下),或者一个Thread子类(自定义线程类可直接继承Thread)的对象。
-法二:创建一个实现Runnable接口的类的对象。
Thread类的常用方法
方法
|
说明 |
public void run() |
线程相关的代码写在该方法中,一般需要重写 |
public void start() |
启动线程的方法 |
public static void sleep(long m) |
线程休眠m毫秒的方法 |
public void join() |
优先执行调用join()方法的线程 |
Runnable接口
-只有一个方法run();
-Runnable是Java中用以实现线程的接口
-任何 实现线程功能的类都必须实现该接口
通过Thread类创建线程
简单介绍线程
package Thread;
class MyThread extends Thread{
public void run(){
System.out.println(getName()+"该线程正在执行");
}
}
public class ThreadTest {
/**
* @param args
*/
public static void main(String[] args) {
// System.out.println("主线程1");
MyThread mt=new MyThread();
mt.start();//启动线程,每个线程只能启动一次
// mt.start();//without compile error.But run error
// System.out.println("主线程2");
}
}
复杂线程
package Thread;
class MyThread2 extends Thread{
public MyThread2(String name){
super(name);
}
public void run(){
for(int i=1;i<=10;i++)
System.out.println(getName()+"正在执行第"+i+"次");
}
}
public class ThreadTest2 {
public static void main(String[] args){
MyThread2 one=new MyThread2("线程1");
MyThread2 two=new MyThread2("线程2");
one.start();
two.start();
}
}
线程的运行时随机的,因为我们不知道它什么时候获得CPU的使用权限,因此线程运行的结果也是随机的。
通过实现Runnable接口的方式创建
为什么要实现Runnable接口?
-Java不支持多继承,如果类已继承一个类就不能再继承Thread
-不打算重写Thread类的其他方法
例子一:
package Runnable;
class PrintRunnable implements Runnable{
public void run() {
int i=1;
while(i<=10)
System.out.println(Thread.currentThread().getName()+"正在运行"+(i++)+"次");
}
}
public class Test {
/** * @param args */
public static void main(String[] args
) { // TODO Auto-generated method stub PrintRunnable test=new PrintRunnable(); Thread t1=new Thread(test); t1.start(); PrintRunnable test2=new PrintRunnable(); Thread t2=new Thread(test2); t2.start(); } }
例一运行结果:
Thread-0正在运行1次 Thread-0正在运行2次 Thread-0正在运行3次 Thread-0正在运行4次 Thread-0正在运行5次 Thread-0正在运行6次 Thread-0正在运行7次 Thread-0正在运行8次 Thread-0正在运行9次 Thread-0正在运行10次 Thread-1正在运行1次 Thread-1正在运行2次 Thread-1正在运行3次 Thread-1正在运行4次 Thread-1正在运行5次 Thread-1正在运行6次 Thread-1正在运行7次 Thread-1正在运行8次 Thread-1正在运行9次 Thread-1正在运行10次
|
例2
package Runnable;
class PrintRunnable implements Runnable{
int i=1;
public void run() {
while(i<=10)
System.out.println(Thread.currentThread().getName()+"正在运行"+(i++)+"次");
}
}
public class Test {
/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
PrintRunnable test=new PrintRunnable();
Thread t1=new Thread(test);
t1.start();
// PrintRunnable test2=new PrintRunnable();
Thread t2=new Thread(test);
//这里将Thread的test2转换成test,也是可以的
//Thread t2=new Thread(test);
t2.start();
}
}
例二运行结果
Thread-0正在运行1次 Thread-1正在运行2次 Thread-0正在运行3次 Thread-1正在运行4次 Thread-0正在运行5次 Thread-1正在运行6次 Thread-0正在运行7次 Thread-1正在运行8次 Thread-0正在运行9次 Thread-1正在运行10次
|
从运行结果可以看到,在这里线程1和线程2公用了同一个代码i。适合于多个线程处理同一个资源。
线程的状态
-新建(New):创建Thread或者Thread的子类时,线程处于新建状态。
-可运行(Runnable):当调用star()方法时,线程获取CPU使用权前的状态。
-正在进行(Running):获取CPU使用权后的状态,调用yield()方法,可以从正在运行状态进入到可运行状态或者当时间片用完时,也会重新进入可运行状态等待获取CPU使用权限。
-阻塞(Blocked):线程遇到干扰后(正在运行状态时可调用Thread类当中的方法,如join()、wait()、sleep()、I/O请求,进入阻塞状态。相反阻塞状态无法直接进入正在运行状态,但是当(1)等待调用join()的线程执行完毕或者(2)调用notify()或notifyAll()或(3)sleep超时或(4)I/O请求完成后,可以进入可运行状态),无法执行的状态。
-终止(Dead):终止。
线程的生命周期
![123]()
![]()
-sleep方法应用
Thread类的方法:public static void sleep(long millis),millis表示毫秒
作用:在指定的毫秒数内让正在执行的线程休眠(暂停执行)
参数为休眠的时间,单位是毫秒
例子:
package Thread;
class MyThread3 implements Runnable{
public void run() {
for(int i=1;i<=15;i++){
System.out.println(Thread.currentThread().getName()+"正在运行第"+i+"次");
//当我们想一秒钟实现一次输出可以调用Thread类中的sleep
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
//当我们运行该代码块时,被打断将出现异常
e.printStackTrace();
}
}
}
}
public class SleepDemo {
/**
* @param args
*/
public static void main(String[] args) {
MyThread3 mt=new MyThread3();
Thread t=new Thread(mt);
t.start();
}
}
作用:当我们想实现计时功能或定期刷新某数据时,可以调用sleep方法。但是有一点需要注意,当我们调用完sleep方法后,系统是不会进入正在运行状态,而是进入可运行状态等待获取CPU权限,因此,当我们用该方法写时钟时,是有一定的误差,会发现时间越走越慢。sleep方法适用于时间要求不太精确的状况。
例二:
package Thread;
class MyThread3 implements Runnable{
public void run() {
for(int i=1;i<=15;i++){
System.out.println(Thread.currentThread().getName()+"正在运行第"+i+"次");
//当我们想一秒钟实现一次输出可以调用Thread类中的sleep
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
//当我们运行该代码块时,被打断将出现异常
e.printStackTrace();
}
}
}
}
public class SleepDemo {
/**
* @param args
*/
public static void main(String[] args) {
MyThread3 mt=new MyThread3();
Thread t=new Thread(mt);
t.start();
Thread t1=new Thread(mt);
t1.start();
}
}
运行结果:
Thread-0正在运行第1次 Thread-1正在运行第1次 Thread-1正在运行第2次 Thread-0正在运行第2次 Thread-0正在运行第3次 Thread-1正在运行第3次 Thread-0正在运行第4次 Thread-1正在运行第4次 Thread-0正在运行第5次 Thread-1正在运行第5次 Thread-0正在运行第6次 Thread-1正在运行第6次 Thread-0正在运行第7次 Thread-1正在运行第7次 Thread-0正在运行第8次 Thread-1正在运行第8次 Thread-0正在运行第9次 Thread-1正在运行第9次 Thread-0正在运行第10次 Thread-1正在运行第10次 Thread-0正在运行第11次 Thread-1正在运行第11次 Thread-0正在运行第12次 Thread-1正在运行第12次 Thread-0正在运行第13次 Thread-1正在运行第13次 Thread-0正在运行第14次 Thread-1正在运行第14次 Thread-0正在运行第15次 Thread-1正在运行第15次
|
当有多个线程同时执行时,我们可以发现它是两个线程交替工作的,同时谁先执行也仍具有随机性。当线程1执行完之后,将进入休眠期,此期间,线程2有更大的机会去获取CPU的使用权限,那如果当线程2未获取使用权限而线程1“苏醒后”又要获取CPU权限,这时候怎么办?
-join方法应用
Thread类的方法:public final void join()
作用:等待调用该方法的线程结束后才能执行。当一个线程调用join()方法后,它会优先执行,只有先执行完它之后才会执行别的线程。因此他是一种抢占资源的方法。
package Thread;
class MyThread4 extends Thread{
public void run(){
for(int i=1;i<=15;i++)
System.out.println(getName()+"正在执行"+i);
}
}
public class JoinDemo {
public static void main(String[] args){
MyThread4 mt=new MyThread4();
mt.start();
try {
mt.join();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
for(int i=1;i<=18;i++)
System.out.println("主线程执行完毕"+i);
}
}
运行结果:
Thread-0正在执行1 Thread-0正在执行2 Thread-0正在执行3 Thread-0正在执行4 Thread-0正在执行5 Thread-0正在执行6 Thread-0正在执行7 Thread-0正在执行8 Thread-0正在执行9 Thread-0正在执行10 Thread-0正在执行11 Thread-0正在执行12 Thread-0正在执行13 Thread-0正在执行14 Thread-0正在执行15 主线程执行完毕1 主线程执行完毕2 主线程执行完毕3 主线程执行完毕4 主线程执行完毕5 主线程执行完毕6 主线程执行完毕7 主线程执行完毕8 主线程执行完毕9 主线程执行完毕10 主线程执行完毕11 主线程执行完毕12 主线程执行完毕13 主线程执行完毕14 主线程执行完毕15 主线程执行完毕16 主线程执行完毕17 主线程执行完毕18
|
通过运行结果我们可以发现,mt线程调用了join()方法之后,不管运行多少次他都是优先执行的。
Thread类的方法:public final void join(long millis)
作用:等待该线程终止的最长时间为millis毫秒。当millis=1000,当调用join()方法后,mt执行了1000毫秒,不管mt方法是否执行完毕,系统都会执行下一个线程。
例子:
package Thread;
class MyThread4 extends Thread{
public void run(){
for(int i=1;i<=300;i++)
System.out.println(getName()+"正在执行"+i);
}
}
public class JoinDemo {
public static void main(String[] args){
MyThread4 mt=new MyThread4();
mt.start();
try {
mt.join(1);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
for(int i=1;i<=18;i++)
System.out.println("主线程执行完毕"+i);
}
}
运行结果:
Thread-0正在执行1 Thread-0正在执行2 Thread-0正在执行3 Thread-0正在执行4 Thread-0正在执行5 Thread-0正在执行6 Thread-0正在执行7 Thread-0正在执行8 Thread-0正在执行9 Thread-0正在执行10 Thread-0正在执行11 Thread-0正在执行12 Thread-0正在执行13 Thread-0正在执行14 Thread-0正在执行15 Thread-0正在执行16 Thread-0正在执行17 Thread-0正在执行18 Thread-0正在执行19 Thread-0正在执行20 Thread-0正在执行21 Thread-0正在执行22 Thread-0正在执行23 Thread-0正在执行24 Thread-0正在执行25 Thread-0正在执行26 Thread-0正在执行27 Thread-0正在执行28 Thread-0正在执行29 Thread-0正在执行30 Thread-0正在执行31 主线程执行完毕1 主线程执行完毕2 主线程执行完毕3 主线程执行完毕4 主线程执行完毕5 主线程执行完毕6 主线程执行完毕7 主线程执行完毕8 主线程执行完毕9 Thread-0正在执行32 主线程执行完毕10 Thread-0正在执行33 主线程执行完毕11 主线程执行完毕12 Thread-0正在执行34 主线程执行完毕13 Thread-0正在执行35 主线程执行完毕14 主线程执行完毕15 主线程执行完毕16 Thread-0正在执行36 主线程执行完毕17 Thread-0正在执行37 主线程执行完毕18 Thread-0正在执行38 主线程执行完毕19 Thread-0正在执行39 主线程执行完毕20 Thread-0正在执行40 主线程执行完毕21 Thread-0正在执行41 主线程执行完毕22 Thread-0正在执行42 主线程执行完毕23 Thread-0正在执行43 主线程执行完毕24 Thread-0正在执行44 主线程执行完毕25 Thread-0正在执行45 主线程执行完毕26 Thread-0正在执行46 主线程执行完毕27 Thread-0正在执行47 主线程执行完毕28 Thread-0正在执行48 主线程执行完毕29 Thread-0正在执行49 主线程执行完毕30 Thread-0正在执行50 主线程执行完毕31 Thread-0正在执行51 主线程执行完毕32 Thread-0正在执行52 主线程执行完毕33 Thread-0正在执行53 主线程执行完毕34 Thread-0正在执行54 主线程执行完毕35 Thread-0正在执行55 主线程执行完毕36 Thread-0正在执行56 主线程执行完毕37 Thread-0正在执行57 主线程执行完毕38 Thread-0正在执行58 主线程执行完毕39 Thread-0正在执行59 主线程执行完毕40 Thread-0正在执行60 主线程执行完毕41 Thread-0正在执行61 主线程执行完毕42 Thread-0正在执行62 主线程执行完毕43 主线程执行完毕44 Thread-0正在执行63 主线程执行完毕45 Thread-0正在执行64 主线程执行完毕46 Thread-0正在执行65 主线程执行完毕47 Thread-0正在执行66 主线程执行完毕48 Thread-0正在执行67 主线程执行完毕49 Thread-0正在执行68 Thread-0正在执行69 Thread-0正在执行70 Thread-0正在执行71 Thread-0正在执行72 Thread-0正在执行73 Thread-0正在执行74 主线程执行完毕50 Thread-0正在执行75 主线程执行完毕51 Thread-0正在执行76 主线程执行完毕52 Thread-0正在执行77 主线程执行完毕53 Thread-0正在执行78 主线程执行完毕54 主线程执行完毕55 主线程执行完毕56 主线程执行完毕57 Thread-0正在执行79 Thread-0正在执行80 Thread-0正在执行81 主线程执行完毕58 Thread-0正在执行82 主线程执行完毕59 Thread-0正在执行83 主线程执行完毕60 Thread-0正在执行84 主线程执行完毕61 Thread-0正在执行85 主线程执行完毕62 Thread-0正在执行86 主线程执行完毕63 Thread-0正在执行87 主线程执行完毕64 Thread-0正在执行88 主线程执行完毕65 Thread-0正在执行89 主线程执行完毕66 Thread-0正在执行90 主线程执行完毕67 Thread-0正在执行91 主线程执行完毕68 Thread-0正在执行92 主线程执行完毕69 Thread-0正在执行93 主线程执行完毕70 Thread-0正在执行94 主线程执行完毕71 Thread-0正在执行95 主线程执行完毕72 Thread-0正在执行96 主线程执行完毕73 Thread-0正在执行97 主线程执行完毕74 Thread-0正在执行98 主线程执行完毕75 Thread-0正在执行99 主线程执行完毕76 Thread-0正在执行100 主线程执行完毕77 Thread-0正在执行101 主线程执行完毕78 Thread-0正在执行102 主线程执行完毕79 Thread-0正在执行103 主线程执行完毕80 Thread-0正在执行104 主线程执行完毕81 Thread-0正在执行105 主线程执行完毕82 Thread-0正在执行106 主线程执行完毕83 Thread-0正在执行107 主线程执行完毕84 Thread-0正在执行108 主线程执行完毕85 Thread-0正在执行109 主线程执行完毕86 Thread-0正在执行110 主线程执行完毕87 Thread-0正在执行111 主线程执行完毕88 主线程执行完毕89 主线程执行完毕90 主线程执行完毕91 主线程执行完毕92 主线程执行完毕93 主线程执行完毕94 Thread-0正在执行112 主线程执行完毕95 Thread-0正在执行113 主线程执行完毕96 Thread-0正在执行114 主线程执行完毕97 Thread-0正在执行115 主线程执行完毕98 Thread-0正在执行116 主线程执行完毕99 Thread-0正在执行117 主线程执行完毕100 Thread-0正在执行118 主线程执行完毕101 Thread-0正在执行119 主线程执行完毕102 Thread-0正在执行120 主线程执行完毕103 Thread-0正在执行121 主线程执行完毕104 Thread-0正在执行122 主线程执行完毕105 Thread-0正在执行123 主线程执行完毕106 Thread-0正在执行124 主线程执行完毕107 Thread-0正在执行125 主线程执行完毕108 Thread-0正在执行126 主线程执行完毕109 Thread-0正在执行127 主线程执行完毕110 Thread-0正在执行128 主线程执行完毕111 Thread-0正在执行129 主线程执行完毕112 Thread-0正在执行130 主线程执行完毕113 Thread-0正在执行131 主线程执行完毕114 Thread-0正在执行132 主线程执行完毕115 Thread-0正在执行133 主线程执行完毕116 Thread-0正在执行134 主线程执行完毕117 Thread-0正在执行135 主线程执行完毕118 Thread-0正在执行136 主线程执行完毕119 Thread-0正在执行137 主线程执行完毕120 Thread-0正在执行138 Thread-0正在执行139 Thread-0正在执行140 Thread-0正在执行141 主线程执行完毕121 主线程执行完毕122 Thread-0正在执行142 主线程执行完毕123 Thread-0正在执行143 主线程执行完毕124 Thread-0正在执行144 主线程执行完毕125 Thread-0正在执行145 主线程执行完毕126 Thread-0正在执行146 主线程执行完毕127 Thread-0正在执行147 主线程执行完毕128 Thread-0正在执行148 主线程执行完毕129 Thread-0正在执行149 主线程执行完毕130 Thread-0正在执行150 主线程执行完毕131 Thread-0正在执行151 主线程执行完毕132 Thread-0正在执行152 主线程执行完毕133 Thread-0正在执行153 主线程执行完毕134 Thread-0正在执行154 主线程执行完毕135 Thread-0正在执行155 主线程执行完毕136 Thread-0正在执行156 主线程执行完毕137 Thread-0正在执行157 主线程执行完毕138 Thread-0正在执行158 主线程执行完毕139 Thread-0正在执行159 主线程执行完毕140 Thread-0正在执行160 主线程执行完毕141 Thread-0正在执行161 Thread-0正在执行162 Thread-0正在执行163 Thread-0正在执行164 Thread-0正在执行165 Thread-0正在执行166 Thread-0正在执行167 Thread-0正在执行168 Thread-0正在执行169 Thread-0正在执行170 Thread-0正在执行171 Thread-0正在执行172 Thread-0正在执行173 主线程执行完毕142 主线程执行完毕143 主线程执行完毕144 主线程执行完毕145 Thread-0正在执行174 Thread-0正在执行175 Thread-0正在执行176 Thread-0正在执行177 Thread-0正在执行178 主线程执行完毕146 Thread-0正在执行179 主线程执行完毕147 Thread-0正在执行180 主线程执行完毕148 Thread-0正在执行181 主线程执行完毕149 Thread-0正在执行182 主线程执行完毕150 Thread-0正在执行183 主线程执行完毕151 Thread-0正在执行184 主线程执行完毕152 Thread-0正在执行185 主线程执行完毕153 Thread-0正在执行186 主线程执行完毕154 Thread-0正在执行187 主线程执行完毕155 Thread-0正在执行188 主线程执行完毕156 Thread-0正在执行189 主线程执行完毕157 Thread-0正在执行190 主线程执行完毕158 Thread-0正在执行191 主线程执行完毕159 Thread-0正在执行192 主线程执行完毕160 Thread-0正在执行193 主线程执行完毕161 Thread-0正在执行194 主线程执行完毕162 Thread-0正在执行195 主线程执行完毕163 Thread-0正在执行196 主线程执行完毕164 Thread-0正在执行197 主线程执行完毕165 Thread-0正在执行198 主线程执行完毕166 Thread-0正在执行199 主线程执行完毕167 Thread-0正在执行200 主线程执行完毕168 Thread-0正在执行201 主线程执行完毕169 Thread-0正在执行202 主线程执行完毕170 Thread-0正在执行203 主线程执行完毕171 Thread-0正在执行204 主线程执行完毕172 Thread-0正在执行205 主线程执行完毕173 Thread-0正在执行206 主线程执行完毕174 Thread-0正在执行207 主线程执行完毕175 Thread-0正在执行208 主线程执行完毕176 Thread-0正在执行209 主线程执行完毕177 Thread-0正在执行210 主线程执行完毕178 Thread-0正在执行211 主线程执行完毕179 Thread-0正在执行212 主线程执行完毕180 Thread-0正在执行213 主线程执行完毕181 Thread-0正在执行214 主线程执行完毕182 Thread-0正在执行215 主线程执行完毕183 Thread-0正在执行216 主线程执行完毕184 Thread-0正在执行217 主线程执行完毕185 Thread-0正在执行218 主线程执行完毕186 Thread-0正在执行219 主线程执行完毕187 Thread-0正在执行220 主线程执行完毕188 Thread-0正在执行221 主线程执行完毕189 Thread-0正在执行222 主线程执行完毕190 Thread-0正在执行223 主线程执行完毕191 Thread-0正在执行224 主线程执行完毕192 Thread-0正在执行225 主线程执行完毕193 主线程执行完毕194 主线程执行完毕195 主线程执行完毕196 主线程执行完毕197 主线程执行完毕198 主线程执行完毕199 主线程执行完毕200 主线程执行完毕201 主线程执行完毕202 主线程执行完毕203 主线程执行完毕204 主线程执行完毕205 主线程执行完毕206 主线程执行完毕207 主线程执行完毕208 主线程执行完毕209 主线程执行完毕210 主线程执行完毕211 主线程执行完毕212 Thread-0正在执行226 主线程执行完毕213 Thread-0正在执行227 主线程执行完毕214 Thread-0正在执行228 主线程执行完毕215 Thread-0正在执行229 主线程执行完毕216 Thread-0正在执行230 主线程执行完毕217 Thread-0正在执行231 主线程执行完毕218 Thread-0正在执行232 主线程执行完毕219 Thread-0正在执行233 主线程执行完毕220 Thread-0正在执行234 主线程执行完毕221 Thread-0正在执行235 主线程执行完毕222 Thread-0正在执行236 主线程执行完毕223 Thread-0正在执行237 主线程执行完毕224 Thread-0正在执行238 主线程执行完毕225 主线程执行完毕226 主线程执行完毕227 主线程执行完毕228 主线程执行完毕229 Thread-0正在执行239 主线程执行完毕230 Thread-0正在执行240 主线程执行完毕231 Thread-0正在执行241 主线程执行完毕232 Thread-0正在执行242 主线程执行完毕233 Thread-0正在执行243 主线程执行完毕234 Thread-0正在执行244 主线程执行完毕235 Thread-0正在执行245 主线程执行完毕236 Thread-0正在执行246 主线程执行完毕237 Thread-0正在执行247 主线程执行完毕238 Thread-0正在执行248 主线程执行完毕239 Thread-0正在执行249 主线程执行完毕240 Thread-0正在执行250 主线程执行完毕241 Thread-0正在执行251 主线程执行完毕242 Thread-0正在执行252 主线程执行完毕243 Thread-0正在执行253 主线程执行完毕244 Thread-0正在执行254 主线程执行完毕245 Thread-0正在执行255 主线程执行完毕246 Thread-0正在执行256 Thread-0正在执行257 Thread-0正在执行258 Thread-0正在执行259 主线程执行完毕247 Thread-0正在执行260 主线程执行完毕248 主线程执行完毕249 主线程执行完毕250 主线程执行完毕251 主线程执行完毕252 主线程执行完毕253 主线程执行完毕254 主线程执行完毕255 主线程执行完毕256 主线程执行完毕257 主线程执行完毕258 主线程执行完毕259 Thread-0正在执行261 主线程执行完毕260 Thread-0正在执行262 主线程执行完毕261 Thread-0正在执行263 主线程执行完毕262 Thread-0正在执行264 主线程执行完毕263 Thread-0正在执行265 主线程执行完毕264 Thread-0正在执行266 主线程执行完毕265 Thread-0正在执行267 主线程执行完毕266 Thread-0正在执行268 主线程执行完毕267 Thread-0正在执行269 主线程执行完毕268 Thread-0正在执行270 主线程执行完毕269 Thread-0正在执行271 主线程执行完毕270 Thread-0正在执行272 主线程执行完毕271 Thread-0正在执行273 主线程执行完毕272 主线程执行完毕273 Thread-0正在执行274 Thread-0正在执行275 Thread-0正在执行276 Thread-0正在执行277 主线程执行完毕274 Thread-0正在执行278 主线程执行完毕275 Thread-0正在执行279 主线程执行完毕276 Thread-0正在执行280 主线程执行完毕277 Thread-0正在执行281 主线程执行完毕278 Thread-0正在执行282 主线程执行完毕279 Thread-0正在执行283 主线程执行完毕280 Thread-0正在执行284 主线程执行完毕281 Thread-0正在执行285 主线程执行完毕282 Thread-0正在执行286 主线程执行完毕283 Thread-0正在执行287 主线程执行完毕284 Thread-0正在执行288 主线程执行完毕285 Thread-0正在执行289 主线程执行完毕286 Thread-0正在执行290 主线程执行完毕287 Thread-0正在执行291 主线程执行完毕288 Thread-0正在执行292 主线程执行完毕289 Thread-0正在执行293 主线程执行完毕290 Thread-0正在执行294 主线程执行完毕291 Thread-0正在执行295 主线程执行完毕292 Thread-0正在执行296 主线程执行完毕293 Thread-0正在执行297 主线程执行完毕294 Thread-0正在执行298 主线程执行完毕295 Thread-0正在执行299 主线程执行完毕296 Thread-0正在执行300 主线程执行完毕297 主线程执行完毕298 主线程执行完毕299 主线程执行完毕300
|
从运行结果我们可以发现,我们设置millis=1,当mt线程执行到第31次后,线程进入休眠状态但仍未结束,然后执行主线程,此后mt线程和主线程将随机获取CPU的使用权限,继续执行直至线程结束。
线程优先级
-Java为线程类提供了10个优先级
-优先级可以同整数1-10表示,超过范围会抛出异常
-主线程默认优先级为5
-数字越大,优先级别越高
-可以使用优先级常量表示优先级
(1)MAX_PRIORITY:线程的最高优先级10
(2)MIN_PRIORITY:线程的最低优先级1
(3)NORM_PRIORITY:线程的默认优先级5
-优先级相关的方法:
方法 |
说明 |
public void getPriority() |
获取线程优先级的方法 |
public void setPriority(int newPriority) |
设置线程优先级的方法 |
例子:
package Thread;
class MyThread5 extends Thread{
private String name;
public MyThread5(String name){
this.name=name;
}
public void run(){
for(int i=1;i<=10;i++){
System.out.println("线程"+name+"正在执行"+i);
}
}
}
public class Priority {
public static void main(String [] args){
//获取主线程的优先级
int mainPriority=Thread.currentThread().getPriority();
System.out.println("主线程的优先级"+mainPriority);
MyThread5 mt1=new MyThread5("线程1");
mt1.setPriority(Thread.MAX_PRIORITY);
mt1.start();
System.out.println("线程1的优先级"+mt1.getPriority());
MyThread5 mt2=new MyThread5("线程2");
mt2.setPriority(1);
mt2.start();
}
}
运行结果:
主线程的优先级5 线程1的优先级10 线程线程1正在执行1 线程线程1正在执行2 线程线程1正在执行3 线程线程1正在执行4 线程线程1正在执行5 线程线程2正在执行1 线程线程1正在执行6 线程线程2正在执行2 线程线程1正在执行7 线程线程2正在执行3 线程线程1正在执行8 线程线程2正在执行4 线程线程1正在执行9 线程线程2正在执行5 线程线程1正在执行10 线程线程2正在执行6 线程线程2正在执行7 线程线程2正在执行8 线程线程2正在执行9 线程线程2正在执行10
|
从运行结果我们会发现即使线程1的优先级比主程序优先级高,系统仍会先输出“线程1的优先级为10”,然后再执行线程2,而且,即使线程1比线程2的优先级高,仍有可能在线程1执行的过程中执行线程2。这与系统环境有关!
多线程运行问题
-各个线程是通过竞争CPU时间而获得运行机会的
-各线程什么时候得到CPU时间,占用多久,是不可预测的
-一个正在运行着的线程在什么地方被暂停是不确定的
线程同步
-