线程小球

首先,什么是线程?线程是程序中一个单一的顺序控制流程。进程内一个相对独立的、可调度的执行单元,是系统独立调度和分派CPU的基本单位指运行中的程序的调度单位。在单个程序中同时运行多个线程完成不同的工作,称为多线程。线程,有时被称为轻量级进程(Lightweight Process,LWP),是程序执行流的最小单元。一个标准的线程由线程ID,当前指令指针(PC),寄存器集合和堆栈组成。另外,线程是进程中的一个实体,是被系统独立调度和分派的基本单位,线程自己不拥有系统资源,只拥有一点儿在运行中必不可少的资源,但它可与同属一个进程的其它线程共享进程所拥有的全部资源。一个线程可以创建和撤消另一个线程,同一进程中的多个线程之间可以并发执行。由于线程之间的相互制约,致使线程在运行中呈现出间断性。线程也有就绪阻塞和运行三种基本状态。就绪状态是指线程具备运行的所有条件,逻辑上可以运行,在等待处理机;运行状态是指线程占有处理机正在运行;阻塞状态是指线程在等待一个事件(如某个信号量),逻辑上不可执行。每一个程序都至少有一个线程,若程序只有一个线程,那就是程序本身。

   每一个java程序都至少有一个线程,这个线程称为主线程。当一个java程序启动时,JVM会创建主线程,并在该线程中调用main()方法。也就是我们通常说的主函数是程序的入口。线程可以理解为“程序内部的一个独立的运行单位”。我们通常写的java程序大多数

是单线程程序,也称为顺序编程。程序通过主线程入口进入之后然后按顺序执行下去,然后结束程序。

   这里所说的线程小球,不是通常的单线程程序,而是多线程程序。那什么又是多线程程序呢?多个进程的内部是完全独立的,而多线程是共享一块内存空间和一组系统资源(在同一进程内),在程序内部可以互相调用。

   废话不多先说,看看怎么来实现线程小球,让多个小球在我们的窗体上动起来吧。Java中多线程的实现,有两种方法,第一可以继承Thread类实现,第二可以实现Runnable接口创建线程。这两种方法都要重写它的run()方法。

   下面我以第一种方法为例说明:

首先新建一个窗体类BallFrame:

   public class BallFrame extends JFrame{

private static final long serialVersionUID = -1450872967753766027L;

public static void main(String[] args){

BallFrame bf=new BallFrame();

bf.initUI();

}

public void initUI(){

this.setTitle("线程小球");

this.setSize(400, 500);

this.setDefaultCloseOperation(3);

this.setLocationRelativeTo(null);

this.setVisible(true);

BallListener bl=new BallListener(this);//建立小球监听

this.addMouseListener(bl);//给窗体添加监听

}

 

}

然后建立监听类:BallListener:

public class BallListener extends MouseAdapter{

  private Graphics2D g;

  private BallFrame bf;

  public BallListener(BallFrame bf){

  this.bf=bf;

  g=(Graphics2D)bf.getGraphics();//获取画笔

  }

public void mousePressed(MouseEvent e) {

int x=e.getX();

int y=e.getY();

 

Ball ball=new Ball(x,y,g,bf);//建立小球对象,画小球

ball.start();//启动小球线程

}

}

最后需要建立一个小球类,主要思路就是通过鼠标监听每点击一次建立一个小球对象,然后每一个小球对象是一个子线程,所以当主线程结束之后,每一个小球作为一个独立的运行单元,可以不受主线程的影响,在窗体中独立的运行:

public class Ball extends Thread{

   private Graphics2D g;

   private int x,y;

   private BallFrame bf;

   public Ball(int x,int y,Graphics2D g,BallFrame bf){//通过构造函数将画笔、窗体                和坐标传过来

   this.x=x;

   this.y=y;

   this.bf=bf;

   this.g=g;

   }

   @SuppressWarnings("static-access")

public void run(){//重写Thread的run()方法

   while(y<bf.getHeight()+25){

 

      g.setColor(bf.getBackground());

      g.fillOval(x-26, y-26, 52, 52);

      y++;//将纵坐标递加,使小向下落,当然也可以通过将x、y坐标不同的处理使小球往不同方向移动

      g.setColor(Color.black);

   g.fillOval(x-25, y-25, 50, 50);

   try {

   this.sleep(42);//线程执行得太快,需要使线程休眠一下,42毫秒

} catch (InterruptedException e) {

e.printStackTrace();

}

   

   }

   }

   

}

(通过这种方法画出的小球会出现一闪一闪的情况,笔者这个需要慢慢改进。。。)

posted @ 2016-04-29 17:10  赵老  阅读(228)  评论(0编辑  收藏  举报