就是一个正在执行中的程序
每一个进程的执行都有一个执行顺序,该顺序是一个执行路径,或者叫一个控制单元
2线程
就是进程中的一个独立的控制单元,线程在控制着进程的执行
一个进程至少有一个线程
3多线程的意义:
提高效率
多条线程一块运行
4地址
多线程的API位置lang-thread
5继承方式步骤
1.定义类继承Thread
2.复写run()方法
3.调用线程的start()方法:该方法有两个作用启动线程和调用run方法
实现方式步骤1
1.定义接口runable
2.定义线程Thread
把runable对象传给Thread
Thread对象atart();
两种方式的不同:
继承Thread:线程代码存放Thread子类Run方法中
实现Runnable线程代码存在接口的子类的run方法
例:
》1:
class Dome extends Thread{
publicvoid run(){
for(int x=0; x<30;x++){
System.out.println(Thread.currentThread().getName()+”:"+x);
}
}
}
调用:
Dome dome=new Dome();
dome.start();
》2:
class Ticket implements Runnable {
privatestaticinttick =50;
publicvoid run(){
while(true){
if(tick>0){
System.out.println(Thread.currentThread().getName()+"...sale:"+tick--);
}
}
}
}
调用:
Ticket t=new Ticket();
Thread t1=new Thread(t);
t1.start();
6多线程的状态
7同步代码
同步快:
Synchronized(对象){//他的锁是对象,对象可以是任何类型的
需要同步的数据
}
函数同步快:
修饰符 synchronized 返回值 方法名称(){//他的锁是this
}
静态函数同步快
修饰符 static synchronized 返回值 方法名称(){//静态的同步方法的锁是该类的字节码文件-类名.class
}
例:
publicsynchronizedvoid add(int n){
synchronized(obj){//同步代码
sum=sum+n;
try{Thread.sleep(10);}catch(Exception e){}//线程睡眠
System.out.println("sum"+sum);
}
}
7.1同步的前提:
>必须要有两个或者两个以上的线程
>必须是朵儿线程使用同一个锁
>必须保证同步中只能有一个线程在运行
好处:解决了多线程的安全问题
弊端:多个线程需要判断锁,较为消耗资源
8
等待唤醒机制:
对象.Wait();//等待
对象.Notify();//唤醒
对象.NotifyAll();//唤醒所有
例:input output线程
class Res {
String name;
String sex;
booleanflag=true;
}
class Input implements Runnable {
private Res r;
Input(Res r) {
this.r = r;
}
publicvoid run() {
int x = 0;
while (true) {
synchronized (r) {
if(r.flag==false){
try {
r.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}else{
if (x == 0) {
r.name = "Mike";
r.sex = "Man";
} else {
r.name = "丽丽";
r.sex = "女";
}
x = (x + 1) % 2;
r.flag=false;
}
r.notify();
}
}
}
}
class Output implements Runnable {
private Res r;
Output(Res r) {
this.r = r;
}
publicvoid run() {
while (true) {
synchronized (r) {
if(r.flag==true)
{
try {
r.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}else{
System.out.println(r.name + "....." + r.sex);
r.flag=true;
}
r.notify();
}
}
}
}
publicclass 线程间通信 {
publicstaticvoid main(String[] args) {
Res r = new Res();
Output ou = new Output(r);
Input in = new Input(r);
Thread t1 = new Thread(in);
Thread t2 = new Thread(ou);
t1.start();
t2.start();
}
9.线程新特性
Lock接口:Lock 实现提供了比使用 synchronized 方法和语句可获得的更广泛的锁定操作
方法:
Void lock();获取锁
Void unlock();释放锁
Condition接口:
Condition 将 Object 监视器方法(wait、notify 和 notifyAll)分解成截然不同的对象,以便通过将这些对象与任意 Lock 实现组合使用,为每个对象提供多个等待 set(wait-set)。
方法:
Void await():等待
Void signal();唤醒一个等待线程
Void signalAll();唤醒所有等待线程
注意5.0后:Lock 替代了 synchronized 方法和语句的使用,Condition 替代了 Object 监视器方法的使用
例:
class Producer implements Runnable {
private ProduceCusumer res;
Producer(ProduceCusumer res) {
this.res = res;
}
@Override
public void run() {
while (true) {
try {
res.set("商品");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
class Consumer implements Runnable {
private ProduceCusumer res;
Consumer(ProduceCusumer res) {
this.res = res;
}
@Override
public void run() {
while (true) {
try {
res.out();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
class ProduceCusumer {
private String name;
private int count = 1;
private boolean flag = false;
// 创建一个锁
final Lock lock = new ReentrantLock();
// 创建一个Condition对象
final Condition condition = lock.newCondition();
final Condition notEmpty = lock.newCondition();
public void set(String name) throws InterruptedException {
lock.lock();
try {
while (flag == true) {
condition.await();//等待
}
this.name = name + ".." + count++;
System.out.println(Thread.currentThread().getName() + "生产者:"
+ this.name);
flag = true;
condition.signalAll();//唤醒
} finally {
lock.unlock();//释放锁
}
}
public void out() throws InterruptedException {
lock.lock();
try {
while (flag == false) {
condition.await();
}
System.out.println(Thread.currentThread().getName() + "消费者:............."
+ this.name);
flag=false;
condition.signalAll();
} finally {
lock.unlock();
}
}
}
public class ProduceCusumerDemo {
public static void main(String[] args) {
ProduceCusumer r=new ProduceCusumer();
Producer dc=new Producer(r);
Consumer cm=new Consumer(r);
Thread th1=new Thread(dc);
Thread th2=new Thread(cm);
Thread th3=new Thread(dc);
Thread th4=new Thread(cm);
th1.start();
th2.start();
th3.start();
th4.start();
}
10.停止线程
如何停止线程?
只有一种方法,run方法结束。
开启线程运行运行代码通常是循环结构。
只要控制循环,就可以让run方法结束,也就是线程结束。
注意:特殊情况:
当线程处于冻结状态,就不会读取标记。
可以用Thread.interrupt();强制线程恢复运行状态
例:
class StopThread implements Runnable {
booleanflag=true;
publicvoid flagchanger(){
flag=false;
}
publicsynchronizedvoid run() {
while (flag) {
try {
wait();
} catch (InterruptedException e) {
System.out.println("中断状态被清除");
flag=false;
}
System.out.println(Thread.currentThread().getName() + "...run");
}
}
}
publicclass 停止线程 {
publicstaticvoid main(String[] args) {
StopThread tt = new StopThread();
Thread t1 = new Thread(tt);
Thread t2 = new Thread(tt);
t1.start();
t2.start();
int num=0;
while(true){
if(num++==60){
tt.flagchanger();//改变标记
t1.interrupt();//强制线程恢复运行状态
t2.interrupt();
break;
}
System.out.println(Thread.currentThread()+"..."+num);
}
System.out.println("程序结束");
}
11.线程的其他方法:
守护线程就是后台线程:特点就是依靠前台线程,如果前台线程都结束了,后台线程自动结束。
线程组:谁开启的线程谁就是组,可以用Threadgroup创建线程组
Thread.Setdaemon();标记为守护线程
Thread.join();抢夺cup执行权,结束后,其他线程恢复运行状态
Thread.toString();打印详细信息
Thread.setPrority();设置优先级.
MAX_Prority:线程可以具有的最高优先级
MIN_Prority:线程可以具有的最低优先级。
NORM_Prority:分配给线程的默认优先级。
Thread.Yield():暂停一下线程
12.开发中如何写线程:
publicstaticvoid main(String[] args) {
new Thread(){
publicvoid run(){
for(int x=0;x<100;x++){
System.out.println(Thread.currentThread().getName()+":"+x);
}
}
}.start();
Runnable r=new Runnable() {
@Override
publicvoid run() {
for(int x=0;x<100;x++){
System.out.println(Thread.currentThread().getName()+":"+x);
}
}
};
new Thread(r).start();
for(int x=0;x<100;x++){
System.out.println(Thread.currentThread().getName()+":"+x);
}
}
转载于:https://blog.51cto.com/yzbxcf/1202689