Java内部类处理事件.docx

上传人:b****4 文档编号:3773275 上传时间:2022-11-25 格式:DOCX 页数:13 大小:119.84KB
下载 相关 举报
Java内部类处理事件.docx_第1页
第1页 / 共13页
Java内部类处理事件.docx_第2页
第2页 / 共13页
Java内部类处理事件.docx_第3页
第3页 / 共13页
Java内部类处理事件.docx_第4页
第4页 / 共13页
Java内部类处理事件.docx_第5页
第5页 / 共13页
点击查看更多>>
下载资源
资源描述

Java内部类处理事件.docx

《Java内部类处理事件.docx》由会员分享,可在线阅读,更多相关《Java内部类处理事件.docx(13页珍藏版)》请在冰豆网上搜索。

Java内部类处理事件.docx

Java内部类处理事件

1内部类

内部类是Java独有的一种语法结构,即在一个类的内部定义另一个类,如:

publicclassExteriorClass{

privateclassInteriorClass{

}

}

此时,内部类InteriorClass就成为外部类ExteriorClass中的成员,访问权限遵循类成员的访问权限机制,可以是public、protected、缺省和private;

内部类可以很方便地访问外部类中的其它成员;

内部类主要为了解决类成员间相互访问的问题

内部类处理事件监听

importjava.awt.*;

importjava.awt.event.*;

importjavax.swing.*;

publicclassEventDemoextendsJFrame{

privateJLabellblMsg;

privateJButtonbtnClick;

publicEventDemo(){

lblMsg=newJLabel("请点击下面的按钮...");

btnClick=newJButton("请点击我");

ContainercpMe=getContentPane();

cpMe.setLayout(newBorderLayout());

cpMe.add(lblMsg,BorderLayout.CENTER);

cpMe.add(btnClick,BorderLayout.SOUTH);

setTitle("ActionListenerDemo");

setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

setSize(300,200);

setResizable(false);//设置不允许用户自行调整窗口大小

setVisible(true);

}

publicstaticvoidmain(String[]args){

newEventDemo();

}

}

内部类处理事件监听

由于我们想要处理按钮的点击事件,因此,按钮便是事件源;

监听器类型是ActionListener。

件处理步骤2:

实现监听器接口(代码)

importjava.awt.*;

importjava.awt.event.*;//要进行事件处理,必须导入此包

importjavax.swing.*;

publicclassEventDemoextendsJFrame{

privateJLabellblMsg;

privateJButtonbtnClick;

publicEventDemo(){//构造方法,代码略

……

……

}

/*采用内部类的方式实现监听器接口*/

privateclassMyListenerimplementsActionListener{

/*实现接口中的抽象方法,事件发生时,将自动调用此方法*/

publicvoidactionPerformed(ActionEventae){

lblMsg.setText("我被点击了!

");//设置标签中的文本

}

}

publicstaticvoidmain(String[]args){

newEventDemo();

}

}

内部类处理事件监听

importjava.awt.*;

importjava.awt.event.*;

importjavax.swing.*;

publicclassEventDemoextendsJFrame{

privateJLabellblMsg;

privateJButtonbtnClick;

publicEventDemo(){//构造方法,代码略

……

btnClick.addActionListener(newMyListener());//将事件源注册到监听器

……

}

/*内部类实现监听器接口*/

privateclassMyListenerimplementsActionListener{

publicvoidactionPerformed(ActionEventae){//实现事件处理函数

lblMsg.setText("我被点击了!

");

}

}

publicstaticvoidmain(String[]args){

newEventDemo();

}

}

用一个监听器监听三个事件源

publicclassGuessFrameextendsJFrame{

……

privateclassSouthPanelextendsJPanelimplementsActionListener{

publicSouthPanel(){

……

//分别为三个按钮注册到同一个监听器

btnGuess.addActionListener(this);

btnAnew.addActionListener(this);

btnExit.addActionListener(this);

……

}

//事件处理方法,无论哪个按钮被点击,都会执行此方法

publicvoidactionPerformed(ActionEventae){

JButtonbtnTemp=(JButton)(ae.getSource());//获得真正的事件源

if(btnTemp==btnGuess){

……//【猜】按钮被点击时应执行的动作

}elseif(btnTemp==btnAnew){

……//【重新开始】按钮被点击时应执行的动作

}elseif(btnTemp==btnExit){

……//【退出游戏】按钮被点击时应执行的动作

}

}

}

}

匿名类其实就是一种比较特殊的内部类,只是这个类没有名字而已;

匿名类与内部类相似,能够访问到外部类中的所有成员;

很多情况下(特别是在事件处理中),匿名类一般被定义在外部类的某个方法中,所以也被称为局部内部类,对于局部内部类,它还可以访问到这个方法的参数;

在适当的情况下,使用匿名类来实现事件处理,会使代码更简洁,更灵活。

只能使用一次。

匿名类的方式进行事件处理

publicclassMouseMotionDemoextendsJFrame{

……//声明窗体中的组件,代码略

publicMouseMotionDemo(){//构造方法,代码略

……

/*将事件源注册到监听器,监听器用匿名类实现*/

this.addMouseMotionListener(newMouseMotionListener(){

//实现MouseMotionListener接口中的鼠标移动方法,代码略

publicvoidmouseMoved(MouseEventme){

……

}

//实现MouseMotionListener接口中的鼠标拖动方法,代码略

publicvoidmouseDragged(MouseEventme){

……

}

});

……

}

publicstaticvoidmain(String[]args){……}

}

GUI中的并发任务

在GUI中,常常可能需要处理并发任务,例如,聊天室应该可以支持传递文件的功能,而传递文件的同时可以继续聊天

修改清空聊天记录事件处理,使其死循环,模拟需要很长时间,可见清理过程中,不能做其他操作

使用多线程编程,将解决该问题

3进程

进程就是正在执行的程序,一个进程通常就是一个正在执行的应用程序。

从Windows角度讲,进程是含有内存和资源并安置线程的地方。

=准确的讲,进程就是一个可执行的程序一次运行的过程,它是系统进行资源分配和调度的一个独立单位。

线程是程序中的一个执行流,每个线程都有自己的专有寄存器(栈指针、程序计数器等),但代码区是共享的,即不同的线程可以执行同样的函数。

一个线程只能属于一个进程,而一个进程可以有多个线程,但至少有一个主线程。

系统资源分配给进程,同一进程的所有线程共享该进程的所有资源。

线程是指进程内的一个执行单元,也是进程内的可调度实体。

多线程是指程序中包含多个执行流,即在一个程序中可以同时运行多个不同的线程来执行不同的任务,也就是说允许单个程序创建多个并行执行的线程来完成各自的任务。

多线程的好处

Java支持编写多线程的程序;

多线程最大好处在于可以同时并发执行多个任务;

多线程可以最大限度地减低CPU的闲置时间,从而提高CPU的利用率。

多线程的不利方面

线程也是程序,所以线程需要占用内存,线程越多占用内存也越多;

多线程需要协调和管理,所以需要CPU时间跟踪线程;

线程之间对共享资源的访问会相互影响,必须解决竞用共享资源的问题;

线程太多会导致控制太复杂,最终可能造成很多Bug。

 

任何一个Java程序启动时,一个线程立刻运行,它执行main方法,这个线程称为程序的主线程;

也就是说,任何Java程序都至少有一个线程,即主线程;

主线程的特殊之处在于:

它是产生其它线程子线程的线程;

通常它必须最后结束,因为它要执行其它子线程的关闭工作。

4匿名内部类的相关概念

内部类是指在一个外部类的内部再定义一个类。

匿名内部类也就是没有名字的内部类。

正因为没有名字,所以匿名内部类只能使用一次,它通常用来简化代码编写。

使用匿名内部类的前提条件是必须继承一个父类或实现一个接口。

继承抽象类的匿名内部类

abstract class Person{

    public abstract void eat();

}

 

public class Demo{

    public static void main(String[]args){

        Personp= new Person(){

            public void eat(){

                System.out.println("eatsomething");

            }

        };

        p.eat();

    }

}

实现接口的匿名内部类

interface Person{

    public void eat();

}

 

public class Demo{

    public static void main(String[]args){

        Personp= new Person(){

            public void eat(){

                System.out.println("eatsomething");

            }

        };

        p.eat();

    }

}

使用匿名内部类的注意点

匿名内部类不能有构造方法;

匿名内部类不能定义任何静态成员、方法和类;

匿名内部类不能是public、protected、private、static;

只能创建匿名内部类的一个实例;

一个匿名内部类一定是在new的后面,用其隐含实现一个接口或实现一个类;

因匿名内部类为局部内部类,所以局部内部类的所有限制都对其生效;

在匿名类中用this时,这个this指的是匿名类本身。

如果我们要使用外部类的方法和变量的话,应该加上外部类的类名。

匿名内部类常用在多线程的实现上,因为要实现多线程必须继承Thread类或是实现Runnable接口。

Thread类的匿名内部类实现

publicclassThreadDemo{

publicstaticvoidmain(String[]args){

Threadthread=newThread(){

publicvoidrun(){

for(inti=1;i<=5;i++){

System.out.print(i+"");

}

}

};

thread.start();

}

等价的非匿名内部类实现

classMyThreadextendsThread{

publicvoidrun(){

for(inti=1;i<=5;i++){

System.out.print(i+"");

}

}

}

publicclassThreadDemo{

publicstaticvoidmain(String[]args){

MyThreadthread=newMyThread();

thread.start();

}

}

publicclassRunnableDemo{

publicstaticvoidmain(String[]args){

Runnabler=newRunnable(){

publicvoidrun(){

for(inti=1;i<=5;i++){

System.out.print(i+"");

}

}

};

Threadthread=newThread(r);

thread.start();

}

}

classMyThreadimplementsRunnable{

publicvoidrun(){

for(inti=1;i<=5;i++){

System.out.print(i+"");

}

}

}

publicclassRunnableDemo{

publicstaticvoidmain(String[]args){

MyThreadr=newMyThread();

Threadthread=newThread(r);

thread.start();

}

}

5Thread类的构造方法

Thread类共提供8种构造方法重载,以下是常用的几种

java.lang.Thread类用于创建和操作线程,其中包括几个很重要的静态方法,用于控制当前线程:

线程优先级

事实上,计算机只有一个CPU,各个线程轮流获得CPU的使用权,才能执行任务;

优先级较高的线程有更多获得CPU的机会,反之亦然;

优先级用整数表示,取值范围是1~10,一般情况下,线程的默认优先级都是5,但是也可以通过setPriority和getPriority方法来设置或返回优先级;

Thread类有如下3个静态常量来表示优先级

MAX_PRIORITY:

取值为10,表示最高优先级。

MIN_PRIORITY:

取值为1,表示最底优先级。

NORM_PRIORITY:

取值为5,表示默认的优先级。

sleep用法

Thread.sleep(longmillis)和Thread.sleep(longmillis,intnanos)静态方法强制当前正在执行的线程休眠(暂停执行),以“减慢线程”。

当线程睡眠时,它入睡在某个地方,在苏醒之前不会返回到可运行状态。

当睡眠时间到期,则返回到可运行状态。

线程睡眠的原因:

线程执行太快,或者需要强制进入下一轮

睡眠的实现:

调用静态方法。

try{

Thread.sleep(1000);

}catch(InterruptedExceptione){

e.printStackTrace();  

}

睡眠的位置:

为了让其他线程有机会执行,可以将Thread.sleep()的调用放线程run()之内。

这样才能保证该线程执行过程中会睡眠。

线程睡眠是帮助所有线程获得运行机会的最好方法。

线程睡眠到期自动苏醒,并返回到可运行状态,不是运行状态。

sleep()中指定的时间是线程不会运行的最短时间。

因此,sleep()方法不能保证该线程睡眠到期后就开始执行。

sleep()是静态方法,只能控制当前正在运行的线程。

yield的用法

Thread.yield()方法作用是:

暂停当前正在执行的线程对象,并执行其他线程,让相同优先级的线程之间能适当的轮转执行。

yield()做的是让当前运行线程回到可运行状态,以允许具有相同优先级的其他线程获得运行机会。

但是,实际中无法保证yield()达到让步目的,因为让步的线程还有可能被线程调度程序再次选中。

结论:

yield()从未导致线程转到等待/睡眠/阻塞状态。

在大多数情况下,yield()将导致线程从运行状态转到可运行状态,但有可能没有效果。

常用于主线程需要用到子线程执行完后的结果,即主线程需要等待子线程执行完成后再结束。

例:

创建并启动线程t,加入到当前运行的线程中

MyThreadt=newMyThread();

t.start();

t.join();

与后台线程相关的方法

要将某个线程设置为后台线程的话,必须在它启动之前调用setDeamon方法;

默认情况下,由前台线程创建的线程仍是前台线程,由后台线程创建的线程仍是后台线程。

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 考试认证 > 司法考试

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1