java程序设计第九章课后习题

1.线程和进程的联系和区别是什么?
联系:一个进程中可以同时运行多个不同的线程。
区别:线程是程序执行中的单个程序流程,进程是操作系统对其资源进行分配的基本单位。同类的多个线程共享一块内存空间和一组系统资源,而线程本身的数据通常指有微处理器的寄存器数据,以及一个供程序执行时使用的堆栈,所以系统在产生一个线程,或者在各个线程之间切换时,负担要比进程小得多。
2.什么是前台线程,什么是后台线程?
main()函数即主函数,是一个前台线程,前台进程是程序中必须执行完成的,而后台线程则是java中所有前台结束后结束,不管有没有完成,后台线程主要用与内存分配等方面。
前台线程和后台线程的区别和联系:
(1)后台线程不会阻止进程的终止。属于某个进程的所有前台线程都终止后,该进程就会被终止。所有剩余的后台线程都会停止且不会完成。
(2)可以在任何时候将前台线程修改为后台线程,方式是设置Thread.IsBackground 属性。
(3)不管是前台线程还是后台线程,如果线程内出现了异常,都会导致进程的终止。
(4)托管线程池中的线程都是后台线程,使用new Thread方式创建的线程默认都是前台线程。
3.创建线程有几种方法?它们之间的区别是什么?
创建线程有三种方法:
(1)通过继承Thread类创建线程。
(2)利用Runnable接口产生线程。
(3)通过线程池Threadpool Execntor创建线程。
区别:(1)直接继承线程Thread类:该方法编写简单,可以直接操作线程,但是不能再继承其他类了。
(2)实现Runnable接口:当一个类已经继承了另一个类时,就只能用实现Runnable接口的方式来创建线程。另外,使用此方法的更多原因是多个线程可共享实现类对象的资源。
(3)线程池主要用来解决线程生命周期开销问题和资源不足问题。通过对多个任务重用线程,线程创建的开销就被分摊到了多个任务上了,而且由于在请求到达时线程已经存在,所以消除了线程创建所带来的延迟。这样,就可以立即为请求服务,使应用程序响应更快。另外,通过适当地调整线程池中的线程数目可以防止出现资源不足的情况。
4,线程的生命周期有哪些状态?哪些方法可以改变这些状态?
线程的生命周期:创建,可运行(就绪),运行中,阻塞,死亡

  • 一个正在运行的线程如果执行了join、sleep、wait方法,将让出cpu并暂时中止自己的执行,进入阻塞状态。
  • 线程到达其run()方法的末尾,将结束线程,进入死亡状态。
  • notify(),notifyAll()等方法会唤醒等待的线程。
    5.什么是线程安全?为什么会产生线程安全问题?如何解决线程安全问题?
    线程安全:多线程访问时,采用了加锁机制,当一个线程访问该类的某个数据时,进行保护,其他线程不能进行访问直到该线程读取完,其他线程才可使用。不会出现数据不一致或者数据污染。 线程不安全就是不提供数据访问保护,有可能出现多个线程先后更改数据造成所得到的数据是脏数据。
    原因:由于不同线程获取到资源时进行运算,但未来得及写入时,线程改变,则另外线程读入的资源就是错误,导致所有线程写入读入不同步。
    解决办法:使用监视器,使用关键字synchronized监视同步代码块,当一个线程获得监视权限时,别的线程就无法获得,保证每时每刻只有一个线程调用某一方法
    6.什么是线程的同步通信?同步通信又是如何实现的?
    线程同步通信是希望实现两个或多个线程之间的某种制约关系。
    实现:首先是用监视器synchronized来保证每次只有一个线程调用方法,其次引入一个boolean型标志来判断该线程是否执行或wait,两个线程时使用notify(),多个线程时用notifyAll()来让出监视器并唤醒其他线程。
    7.什么是死锁?
    如果多个线程都处于等待状态,彼此需要对方所占用的监听器所有权,就构成死锁。
    8.如何让某个对象的A方法内的一个代码块和另一个方法B实现同步?
class Account{
    volatile private int value;
    volatile private boolean isMoney=false;
    synchronized void put(int i){
        if(isMoney){
            try{wait();}
            catch(Exception e){}
        }
        value=value+i;
        System.out.println("存入"+i+"账上金额为:"+value);
        isMoney=true;
        notify();
        }
        synchronized int get(int i){
            if(!isMoney){
                try{wait();}
                catch(Exception e){}
            }
            if(value>i)
                value=value-i;
            else{
                i=value;
                value=0;
            }
            System.out.println("取走"+i+"账上金额为:"+value);
            isMoney=false;
            notify();
            return i;
        }
    }
   

9.设计一个程序产生两个线程A与B,B线程执行10秒钟后,被A线程中止。

class Account                              
{
 int b=0;
 void change(int _a) {b=_a;}
 int getb() {return b;}
    volatile private int value;
    synchronized void put(int i)                       
 {
  value = value + i; 
  System.out.println("存入"+i+", 账上金额为:"+value);
 }
}
class  Save implements Runnable            
{
 //int a=2000;
    private Account a1;     
    public Save(Account a1)
    {
        this.a1 = a1;
    }
    public void run()
    {
     while(a1.getb()==0) {
         try {
    Thread.sleep(900);
   } catch (InterruptedException e) {
    // TODO Auto-generated catch block
    e.printStackTrace();
   }
   a1.put(1);   
     }
     System.out.println("10秒已到,停止存钱。stop!");
    }
}
class Fetch implements Runnable            
{
 //int a=20;
    private Account a1;
    public Fetch(Account a1)
    {this.a1 = a1 ;}
    public void run()
    {    
     if(a1.getb()==0) {
     try {
  Thread.sleep(9000);
     } catch (InterruptedException e) {}
     }
     a1.change(1); 
    }
}
public class Test{
 public static void main(String[] args){
       Account a1 = new Account();
       new Thread(new Save(a1)).start(); 
       new Thread(new Fetch(a1)).start();
 }
}

你可能感兴趣的:(java程序设计第九章课后习题)