多线程---线程简介。

Windows操作系统是多任务操作系统,它以进程为单位。一个进程是一个包含有自身地址的程序,每个独立执行的程序都称为进程,也就是正在执行的程序。系统可以分配给每个进程一段有限的使用CPU的时间,CPU在这段时间中执行某个进程,然后下一个时间片又跳至另一个进程中去执行,由于CPU转换较快,所以使得每个进程好像是同时执行一样。

一个线程则是进程中的执行流程,一个进程中可以同时包括多个线程,每个线程也可以得到一小段程序的执行时间,这样一个进程就可以具有多个并发执行的线程,在单线程中程序代码按调用顺序依次往下执行,如果需要一个进程同时完成多段代码的操作,就需要产生多线程。

在Java中主要提供两种方式实现线程,分别为继承java.lang.Thread类与实现java.lang.Runnable接口。

1 . 继承Thread类。

Thread类是java.lang包中的一个类,从这个类中实例化的对象代表线程,程序员启动一个新线程城需要建立Thread实例。Thread类中常用的两个构造方法如下:

public Thread():创建一个新的线程对象。

public Thread(String threadName):创建一个名称为threadName的线程对象。

继承Thread类创建一个新的线程的语法如下:

public class ThreadTest extends Thread{

}

完成线程真正功能的代码放在类的run()方法中,当一个类继承Thread类后,就可以在该类中覆盖run()方法,将实现该线程功能的代码写入run()方法中,然后同时调用Thread类中的start()方法执行线程,也就是调用run()方法。

Thread对象需要一个任务来执行,任务是指线程在启东市执行的工作,该工作的功能代码被写在run()方法中,run()方法必须使用以下语法格式:

public void run(){

}

PS:如果start()方法调用一个已经启动的线程,系统将抛出IllegalThreadStateException异常。

当执行一个线程程序时就自动产生一个线程,主方法正是在这个线程上运行的,当不再启动其他线程时,该程序就为单线程程序。主方法线程启动由JAVA虚拟机负责,程序员负责启动自己的线程。

public static void (String[] args){
    new ThreadTest().start();
}

下面看一个继承Thread类的实例。

    /*
    指定类继承Thread类。
     */
public class ThreadTest extends Thread{
    private int count = 10;
    // 1 . 重写run()方法。
        public void run(){
            while (true){
                // 2 . 打印count变量。
                System.out.print(count + "");
                // 3 . 使count变量自减,当自减为0时,退出循环。
                if(--count == 0){
                    return;
                }
            }
        }

        public static void main(String[] args) {
            new ThreadTest().start();
        }
}

在上述实例中继承了Thread类,然后在类中覆盖了run()方法,通常在run()方法中使用无限循环的形式,使得线程一直运行下去,所以要指定一个跳出循环的条件。如本实例中使用变量count递减为0作为跳出循环的条件,在main()方法中实现成执行需要调用Thread类中的start()方法,start()方法调用被覆盖的run()方法,如果不调用start()方法,线程永远都不会启动,在主方法没有调用start()方法之前。Thread对象只是一个实例,而不是一个真正的线程。

2 . 实现Runnable接口。

到目前为止,线程都是通过扩展Thread类来创建的,如果程序员需要继承其他类非Thread类,而且还要使当前类实现多线程,那么可以通过接口来实现,例如一个扩展JFrame类的GUI程序不可能再继承Thread类,因为JAVA语言中不支持多继承,这时该类就需要实现Runnable接口使其具有使用线程的功能。

实现Runnable接口的语法如下:

public class Thread extends Object implement Runnable

PS:实质上,Thread类实现了Runnable接口,其中的run()方法正式对Runnable接口中的run()方法的具体实现。

实现Runnable接口的程序会创建一个Thread对象,并将Runnable对象与Thread对象相关联。Thread类中有一下两个构造方法:

public Thread(Runnable target)

public Thread(Runnable target,String name).

这两个构造方法的参数中都存在Runnable实例,使用以上构造方法就可以将Runnable实例与Thread实例相关联。

使用Runnable接口启动新的线程的步骤如下:

1 .  建立Runnable对象。

2 . 使用参数为Runnable对象的构造方法创建Thread实例。

3 . 调用start()方法启动线程。

线程最引人注目的部分应该是与Swing相结合创建GUI程序,下面演示一个GUI程序,该程序结合了图标滚动的功能。

import javax.swing.*;
import java.awt.*;
import java.net.URL;

public class SwingAndThread extends JFrame {
    /*
    在项目中创建SwingAndThread类,该类继承了JFrame类,实现图标移动的功能,其中使用了Swing与线程相结合的技术。
     */

    // 1 . 声明JLabel对象。
    private JLabel jl = new JLabel();
    // 2 . 声明线程对象。
    private static Thread t;
    // 3 . 声明计数变量。
    private int count = 0;
    // 4 . 声明容器。
    private Container container = getContentPane();

    public SwingAndThread(){
        // 5 . 绝对定位窗体大小与位置。
        setBounds(300,200,250,100);
        // 6 . 使窗体不使用任何布局管理器。
        container.setLayout(null);
        // 7 . 获取图片的URL。
        URL url = SwingAndThread.class.getResource("/1.gif");
        // 8 . 实例化一个Icon。
        Icon icon = new ImageIcon(url);
        // 9 . 将图标放置在标签中。
        jl.setIcon(icon);
        // 10 . 设置图片在标签的最左上方。
        jl.setHorizontalAlignment(SwingConstants.LEFT);
        // 11 . 设置标签的位置与大小。
        jl.setBounds(10,10,200,50);
        jl.setOpaque(true);
        // 12 . 定义匿名内部类,该类实现Runnable接口。
        t = new Thread(new Runnable() {
            // 13 . 重写run()方法。
            @Override
            public void run() {
                // 14 . 设置循环条件.
                while(count <= 200){
                    // 15 . 将标签的横坐标用变量表示。
                    jl.setBounds(count,10,200,50);
                    try{
                        // 16 . 使线程休眠1000ms。
                        Thread.sleep(1000);
                    }catch (Exception e){
                        e.printStackTrace();
                    }
                    // 17 . 使横坐标每次增加4.
                    count += 4;
                    // 18 . 当图标到达标签的最右边时,使其回到标签最左边。
                    if(count == 200){
                        count = 10;
                    }
                }
            }
        });
        // 19 . 启动线程。
        t.start();
        // 20 . 将标签添加到容器中。
        container.add(jl);
        // 21 . 使窗体可见。
        setVisible(true);
        // 22 . 设置窗体的关闭方式。
        setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE);
    }

    public static void main(String[] args) {
        // 23 . 实例化一个SwingAndThread对象。
        new SwingAndThread();
    }
}

关于图片的URL问题,在文件夹里找生成的.class文件,找到之后将图片与.class文件放在一个文件夹里即可。

在本实例中,为了使图标具有滚动功能,需要在类的构造方法中创造Thread的实例,在创建该实例的同时,需要Runnable对象作为Thread类构造方法的参数,然后使用内部类形式实现run()方法,然后在run()方法中主要循环图标的横坐标位置,当图标横坐标到达标签最右方时,再次将图标的横坐标至于图标滚动的初始位置。

PS:启动一个新的线程不是直接调用Thread子类对象的run()方法,而是调用Thread子类的start()方法,Thread类的start()方法产生一个新的线程,该线程运行子类的run()方法。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值