1、进程和线程的概念于区别
进程:是程序执行的一次过程,本质上是程序的执行,一个进程可以包含多个线程,拥有独立的地址空间,执行重量级任务。
线程:是程序执行的最小单位,多个线程可以访问一个地址空间,执行轻量级任务。
2、创建多线程方式有两种:
1、实现runnable 接口:
class Test implements runnable{
public void run(){
//需要执行的内容
}
}
2、继承 Thread类
class Test exdents Thread(){
public void run(){
//
}
}
在调用线程处开启:
注意:开启线程用start()方法开启线程,而不是调用run()方法。
3、线程同步:当多个线程需要调用同一个资源时,就需要用到线程同步。当一个线程B调用资源A时,线程C便要等待线程B退出管程后,C才可以使用资源A。
1、方法同步:在方法的头部void之前加关键字:synchronized关键字
class Test implements runnable{
public synchonized void run(){
//需要执行的内容
}
}
2、块同步:将需要同步的资源封装到调用线程处
4、线程通讯:
生产者与消费者案例:
public class Consumer implements Runnable { //消费者类
Q q;
public Consumer(Q q){ //开启线程
this.q = q;
new Thread(this).start();
}
@Override
public void run() {
while(true){
q.get();
}
}
}
public class Producer implements Runnable { //消费者
Q q;
public Producer(Q q){
this.q = q;
new Thread(this).start();
}
@Override
public void run() {
int i =1;
while(true){
Product p = new Product("面包", i++);
q.put(p);
}
}
}
public class Product { //面包类
String name;
int number;
public Product(String name,int number){
this.name = name;
this.number = number;
}
@Override
public String toString() {
return "产品 [名称=" + name + ", 编号=" + number + "]";
}
}
public class Q { //
Product[] boxs = new Product[5];
int index = 0;
public synchronized void put(Product p){ //生产面包
if(index == boxs.length){
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
boxs[index++] = p;
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("生产者"+p);
notify();
}
public synchronized Product get(){ //消费面包
if(index <= 0){
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("消费者"+boxs[--index]);
notify();
return boxs[index];
}
}
public class TestThread { // 测试类
public static void main(String[] args) {
Q q = new Q();
new Producer(q);
new Consumer(q);
}
}
线程的死锁:当多个线程相互调用时出现死锁问题。