最近回顾了下内部类的用法,有两个问题备忘下。
1 内部类标准用法
java中内部类用处很广,但是感觉标准用法如下:
内部类child使用private修饰符,实现一个公开的接口interface,然后通过父类parent的public方法初始化newInstance,在外部通过接口interface访问,而内部类child又可以访问父类parent的内部资源
其中最经典的例子当属于util中的Iterator方式了。父类AbstractList中有private内部类Itr,实现了java.util.Iterator接口,然后内部类中可以访问AbstractList的各种变量和方法
private class Itr implements Iterator<E>{
public E next() {
checkForComodification();
try {
E next = get(cursor);
lastRet = cursor++;
return next;
} catch (IndexOutOfBoundsException e) {
checkForComodification();
throw new NoSuchElementException();
}
}
final void checkForComodification() {
if (modCount != expectedModCount)
throw new ConcurrentModificationException();
}
}
在外部通过接口访问
List list=new ArrayList();
Iterator it=list.iterator();//通过接口访问
it.next();
这样做能够实现外部接口,访问内部变量,且不暴露访问细节
因为内部类是private的,只能在父类内部访问,在外部不能访问,因此就和根本不存在一样
List list=new ArrayList();
List.Itr it=list.new Itr();//不能通过这种标准方式访问
2 匿名内部类和final
另外关于匿名内部类只能访问final类型的局部变量的原因,确定的是匿名内部类一般可能是线程之类的,生命周期远比一般的方法调用要长。
有一种说法是内部类里面将该变量copy一份,如果该变量还可以随意赋值的话,可能导致内部类中的那份copy和外部的相比不一样了,因此需要final修饰符,但是感觉这样不对,写了个例子测试了下,如下:
private static void test() throws Exception{
final List<String> list = new ArrayList<String>();
list.add("aa");
list.add("bb");
new Thread() {
public void run() {
int i = 0;
while (true) {
i++;
if (i == 10)
break;
System.out.println(list);
try { Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}.start();
list.add("cc");
Thread.sleep(2000);
list.add("dd");
}
代码的目的是匿名类里面不停访问list,匿名类外部修改list,结果如下:
[aa, bb, cc]
[aa, bb, cc]
[aa, bb, cc, dd]
[aa, bb, cc, dd]
[aa, bb, cc, dd]
[aa, bb, cc, dd]
[aa, bb, cc, dd]
[aa, bb, cc, dd]
[aa, bb, cc, dd]
从结果可以看到匿名类内部和外部访问的是同一个对象,而不是通过copy的方式。
因此怀疑final类型的局部变量的生命周期比一般的局部变量周期要长,在方法调用完毕之后还存在。
分享到:
相关推荐
Java 内部类是指在一个外部类的内部再定义一个类。内部类作为外部类的一个成员,并且依附于外部类而存在的。内部类可为静态,可用 protected 和 private 修饰(而外部类只能使用 public 和缺省的包访问权限)。 ...
Java 中的嵌套类和内部类是指在一个类的内部定义另一个类,这种类称为嵌套类(nested classes)。嵌套类有两种类型:静态嵌套类和非静态嵌套类。静态嵌套类使用很少,非静态嵌套类也即被称作为内部类(inner)。嵌套...
Java内部类是Java语言中一个独特且强大的特性,它允许在一个类的定义内部定义另一个类。内部类可以访问外部类的所有成员,包括私有成员,这使得内部类在实现某些特定设计模式时非常有用。本篇文章将深入探讨Java内部...
Java接口和内部类是Java语言中两种重要的抽象机制,它们在软件设计中起着关键作用。接口主要用于定义对象之间的交互规范,而内部类则提供了一种封装和隐藏类的机制,使得类的设计更加灵活。 首先,接口是一个合约,...
如果我们需要在同一个类中实现两种不同的`calculate`方法,可以通过创建两个内部类来实现这一目标,每个内部类实现`Calculator`接口并提供不同的实现方式。 ```java public interface Calculator { double ...
此外,文章引用了其他研究者的继承准则,如Clidamber和Kemerer的两个准则,以及Brito和Carapuca的三个类继承指标,这些准则和指标虽然主要关注普通类的继承体系,但也可以为内部类的继承问题提供一定的参考。...
Java内部类是Java语言中一个独特且强大的特性,它允许我们在一个类的内部定义另一个类。内部类可以分为四种类型:静态内部类、成员内部类(非静态内部类)、局部内部类和匿名内部类。 1. **静态内部类**: 静态...
Java内部类是Java语言中一个独特且强大的特性,它允许在一个类的定义内定义另一个类。内部类可以分为四种类型:成员内部类、局部内部类、匿名内部类和静态内部类。下面我们将深入探讨内部类的使用方法和优势。 首先...
在某些情况下,一个类需要根据不同的条件表现出不同的行为,这时可以使用内部类来实现多态性和代码的复用。 **代码示例:** ```java public class Calculator { public interface Operation { int execute(int a...
1. **分类**:成员内部类分为两种,静态内部类(Static Inner Class)和非静态内部类(Non-static Inner Class)。非静态内部类可以直接访问外部类的实例变量和方法,而静态内部类不能直接访问,需要通过外部类的...
本教程"Java4Android 35_内部类和匿名内部类"深入探讨了这两个概念,旨在帮助开发者更好地理解和运用它们。 **内部类** 内部类,也称为嵌套类,是在另一个类的定义内部声明的类。它有以下几种类型: 1. **成员...
在Java中,我们可以用两个`double`类型的实例变量来表示这两个部分。 ```java public class Complex { private double realPart; // 实部 private double imagPart; // 虚部 // 构造函数 public Complex...
Java 内部类是 Java 语言的一个特性,它允许在一个类的定义内部定义另一个类。这种设计模式在处理某些特定情况时非常有用,比如当一个类的实例与另一个类紧密关联,或者需要实现某种形式的多继承。在这个实验中,...
Java内部类是Java语言的一个重要特性,它允许我们在一个类的内部定义另一个类。这种设计模式使得代码结构更加紧凑,同时也提供了更高级的封装和抽象。内部类主要有两种类型:成员内部类和局部内部类。 1. 成员内部...
1. **内部类**:内部类是一种特殊的类,定义在另一个类(外部类)的内部。它可以访问外部类的所有成员(包括私有成员),同时也可以被外部类所访问。 2. **静态成员变量**:静态成员变量是类级别的变量,可以通过...
总结,这个实验报告深入浅出地介绍了Java内部类的概念及其使用,以及异常处理的基本思想,通过实际的编程练习,有助于提高学生的编程技能和问题解决能力。通过扩展内部类的应用和异常处理的实践,学生可以更好地理解...
Java内部类是Java编程语言中的一个独特特性,它允许在一个类的内部定义另一个类。这种设计模式在处理一些复杂情况时特别有用,比如实现事件监听器或者创建匿名类。内部类分为四种类型:成员内部类、局部内部类、匿名...
5. 逻辑分组:有时,两个类之间存在紧密的关系,将一个类嵌套在另一个类中可以清晰地表示它们之间的关系。 示例代码中的 `TimerPrinter` 是 `Court` 类的一个成员内部类,实现了 `ActionListener` 接口。`...
Java内部类是一种定义在另一个类内部的类,它可以访问外部类的所有成员,包括私有成员。内部类分为四种类型:成员内部类、局部内部类、匿名内部类和静态嵌套类。其中,静态嵌套类是与外部类关联但不持有对外部类的...
**定义**:内部类是指在一个类的内部定义的类。它可以存在于任何位置,如类、方法甚至是条件语句中。内部类同样可以继承其他类或者实现接口,这为设计更为灵活且紧密耦合的组件提供了可能。 **意义**: - **数据...