第10章 内部类(java编程思想)

【Java笔记】第11章:内部类 各位小伙伴大家好!上期小编给大家讲解了Java中的接口,接下来讲讲Java中的内部类!至此,Java的内部类讲解完毕。互三必回!持续更新中~! 阅读详情

10.1 创建内部类

典型的应用情况是,外部类将会有一个方法,该方法返回以内部类的引用。就像在to()和content()中看到的那样。

//: innerclasses/Parcel2.java
// Returning a reference to an inner class.

public class Parcel2 {
  class Contents {
    private int i = 11;
    public int value() { return i; }
  }
  class Destination {
    private String label;
    Destination(String whereTo) {
      label = whereTo;
    }
    String readLabel() { return label; }
  }
  public Destination to(String s) {
    return new Destination(s);
  }
  public Contents contents() {
    return new Contents();
  }
  public void ship(String dest) {
    Contents c = contents();
    Destination d = to(dest);
    System.out.println(d.readLabel());
  }
  public static void main(String[] args) {
    Parcel2 p = new Parcel2();
    p.ship("Tasmania");
    Parcel2 q = new Parcel2();
    // Defining references to inner classes:
    Parcel2.Contents c = q.contents();
    Parcel2.Destination d = q.to("Borneo");
  }
} /* Output:
Tasmania
*///:~

10.2 链接到外部类

当生成一个内部类的对象是,此对象与制造他的外围对象之间就有一种联系,所以他能访问其外围对象的所有成员,而不需要任何特殊条件,此外,内部类还拥有其外围类的所有元素的访问权。下面的例子就说明了这一点。

 //: innerclasses/Sequence.java
// Holds a sequence of Objects.

interface Selector {
  boolean end();
  Object current();
  void next();
}	

public class Sequence {
  private Object[] items;
  private int next = 0;
  public Sequence(int size) { items = new Object[size]; }
  public void add(Object x) {
    if(next < items.length)
      items[next++] = x;
  }
  private class SequenceSelector implements Selector {
    private int i = 0;
    public boolean end() { return i == items.length; }
    public Object current() { return items[i]; }
    public void next() { if(i < items.length) i++; }
  }
  public Selector selector() {
    return new SequenceSelector();
  }	
  public static void main(String[] args) {
    Sequence sequence = new Sequence(10);
    for(int i = 0; i < 10; i++)
      sequence.add(Integer.toString(i));
    Selector selector = sequence.selector();
    while(!selector.end()) {
      System.out.print(selector.current() + " ");
      selector.next();
    }
  }
} /* Output:
0 1 2 3 4 5 6 7 8 9
*///:~

内部类的对象只能在与其外部类对象相关联的情况下才可以被创建(就像所看到的,当内部类不是static时),创建内部类需要一个指向其外部类的引用,如果编译器访问不到这个引用就会报错。

10.4 内部类和向上转型

因为不能访问其名字,private内部类给类的设计则提供了一种途径,通过这种方式可以完全阻止依赖于此类型的编码,并且完全隐藏了实现的细节,此外,从客户端程序员的角度来康,由于不能访问任何新增的,原本不属于公共接口的方法,所以扩展接口是没有任何价值的,这也给java编译器生成了更高效代码的机会。
外部类可以访问内部类的private方法。

//: innerclasses/TestParcel.java

class Parcel4 {
  private class PContents implements Contents {
    private int i = 11;
    public int value() { return i; }
  }
  protected class PDestination implements Destination {
    private String label;
    private PDestination(String whereTo) {
      label = whereTo;
    }
    public String readLabel() { return label; }
  }
  public Destination destination(String s) {
    return new PDestination(s);
  }
  public Contents contents() {
    return new PContents();
  }
}

public class TestParcel {
  public static void main(String[] args) {
    Parcel4 p = new Parcel4();
    Contents c = p.contents();
    Destination d = p.destination("Tasmania");
    // Illegal -- can't access private class:
    //! Parcel4.PContents pc = p.new PContents();
  }
} ///:~

10.5 在方法和作用域内的内部类

你可以在一个方法或任意的作用域内定义内部类,这么做有两个理由:
1)你实现了某类型的接口,于是可以创建并返回他的引用。
2)你要解决一个复杂的问题,想创建一个类来辅助解决你的方案,但是又不希望这个类是公共可用的。
第一个例子展现了在方法的作用域内(而不是类的作用域内),创建一个完整的类,这被称为局部内部类。

//: innerclasses/Parcel5.java
// Nesting a class within a method.

public class Parcel5 {
  public Destination destination(String s) {
    class PDestination implements Destination {
      private String label;
      private PDestination(String whereTo) {
        label = whereTo;
      }
      public String readLabel() { return label; }
    }
    return new PDestination(s);
  }
  public static void main(String[] args) {
    Parcel5 p = new Parcel5();
    Destination d = p.destination("Tasmania");
  }
} ///:~

PDestination是destination()方法的一部分,而不是Parcel5的已不够,除了destination()方法外不能访问PDestination,你可以在同一个子目录下的任意类中对某个内部类使用类标识符PDestination,这样不会有命名冲突。

10.6 匿名内部类

package SourceCode;

//: innerclasses/Parcel8.java
//Calling the base-class constructor.

public class Parcel8 {
public Wrapping wrapping(int x) {
 // Base constructor call:
 return new Wrapping(x) { // Pass constructor argument.
   public int value() {
     return super.value() * 47;
   }
 }; // Semicolon required
}
public static void main(String[] args) {
 Parcel8 p = new Parcel8();
 Wrapping w = p.wrapping(10);
}
} ///:~

//: innerclasses/Wrapping.java
public class Wrapping {
  private int i;
  public Wrapping(int x) { i = x; }
  public int value() { return i; }
} ///:~

在匿名内部类的末尾的分号,并不是用来标记此内部类结束的,实际上,他标记的是表达式的结束,只不过这个表达式正巧包含了内部匿名类罢了,因此,这与别的地方使用的分号是一致的。
在匿名类中定义字段时,还可以对其进行初始化操作。

在这里插入代码片

如果定义一个匿名内部类,并且希望它使用一个定义在其外部定义的对象,那么编译器会要求这个对象的参数引用是final的,就像你在destination()的参数引用中看到的那样,如果你忘记了,那么编译器会报错。
10.6.1 再返工厂方法
现在用于Implementation1和Implementation2的构造器都可以是private,并且没有任何必要去创建作为工厂的别名。

//: innerclasses/Factories.java
import static net.mindview.util.Print.*;

interface Service {
  void method1();
  void method2();
}

interface ServiceFactory {
  Service getService();
}	

class Implementation1 implements Service {
  private Implementation1() {}
  public void method1() {print("Implementation1 method1");}
  public void method2() {print("Implementation1 method2");}
  public static ServiceFactory factory =
    new ServiceFactory() {
      public Service getService() {
        return new Implementation1();
      }
    };
}	

class Implementation2 implements Service {
  private Implementation2() {}
  public void method1() {print("Implementation2 method1");}
  public void method2() {print("Implementation2 method2");}
  public static ServiceFactory factory =
    new ServiceFactory() {
      public Service getService() {
        return new Implementation2();
      }
    };
}	

public class Factories {
  public static void serviceConsumer(ServiceFactory fact) {
    Service s = fact.getService();
    s.method1();
    s.method2();
  }
  public static void main(String[] args) {
    serviceConsumer(Implementation1.factory);
    // Implementations are completely interchangeable:
    serviceConsumer(Implementation2.factory);
  }
} /* Output:
Implementation1 method1
Implementation1 method2
Implementation2 method1
Implementation2 method2
*///:~

10.7 嵌套类

如果不需要内部对象与外围对象有任何联系,可以将内部对象声明为static,这通常称为嵌套类,想要理解static应用于内部类是的含义,就必须记住,普通的内部类对象隐式地保存了一个引用,指向创建它的外围类对象,然而,当内部类是static时,就不是这样了,嵌套类意味着
1)要创建嵌套类的对象,并不需要外围类的对象。
2)不能从嵌套类的对象中访问非静态的外围类对象。

10.8 为什么需要内部类

内部类提供了可以继承多个具体或抽象的类的能力,内部类使多重继承的功能变得完整,接口解决了部分问题,而内部类有效的实现了多重继承,也就是说,内部类允许继承多个非接口类型,内部了的特性:
1)内部类可以有多个实例,每个实例都有自己的状态信息,并且与其外围·对象的信息相独立。
2) 在单个外围类中可以让多个内部类一不同的方式实现同一个接口,或继承同一个类。
3)创建内部类的时刻并不依赖于外围类对象的创建。
10.8.1 闭包与回调

每天一个优秀提示词学习收藏 - 文本创作篇(二) 宝子们,今天不藏私啦!我把这段时间四处搜罗、潜心钻研出来的文本创作 Prompt 提示词大礼包双手奉上,这可都是能让你的 AI 创作水平原地起飞的干货!走过路过不要错过,赶紧码住,开启你的 AI 创作进阶之旅吧! 阅读详情

相关推荐

spring-ai学习(四)-MCP

创建一个springai项目1.依赖。

zql1455890112的博客 1384

《java编程思想》第10章 内部类

内部类:将一个类的定义放在另一个类的定义内部。内部类与组合是完全不同的概念。10.8之后一般用不上。 10.1创建内部类 创建一个内部类: //: innerclasses/Parcel1.java // Creating inner classes. public class Parcel1 { class Contents { private int i = 11; ...

Hello_JavaScript的博客 276

Unity - gamma space下还原linear space效果

还有头发之后的 (头发没有处理完整,因为使用 ASE 连连看练出来的,使用 surface shader,虽然可以生成一下 vert, frag 的方式在修改,但是我懒得去修改了,这样就是 PBR 的 BRDF 里面的部分曲线是不一样的,所以可以看到头发有一些差异)其实上面的代码判断 是否有分量 > 1.0f 的方式来判断是否 HDR 是不太合理的,因为不同的贴图格式的编码方式不同。还有比较隐蔽的一些颜色相关的常量值 (比如PBR中的 绝缘体的 F0 常量值,等等)

Jave.Lin 的学习笔记 2830

《JAVA编程思想》学习笔记:第10章(内部类)

目录Java编程思想(一)第1~4章:概述Java编程思想(二)第5章:初始化和清理Java编程思想(三)第6章:访问权限Java编程思想(四)第7章:复用类Java编程思想(五)第8章:多态Java编程思想(六)第9章:接口Java编程思想(七)第10章:内部类Java编程思想(八)第11章:持有对象Java编程思想(九)第12章:异常Java编程思想(十)第13章:字符串Java编程思想(十一...

caobaokang的专栏 4743

紫光同创国产FPGA学习之Fabric Debugger

文章从紫光同创参考书拷贝过来的。因为我用的时候,看了一下就会用了(纯粹只是会用了,默认和xilinx的一样),没有看教程。先更新点文本,后面在写程序。 一、      软件简介 Fabric Debugger是一款界面化的FPGA芯片调试工具,能够针对公司目前以及未来的FPGA芯片进行在线调试。本软件直接与JtagHub、DebugCore交互,能够实时的配置目标FPGA、设置触发条件并且观测结...

my_share的专栏 6390

地震勘探中的频谱分析:从基础到应用

本文深入探讨了地震勘探中的频谱分析技术,从基础原理到实际应用。通过傅里叶变换等工具,频谱分析能有效识别不同地震波的频率特征,指导数据采集和处理。文章结合油田勘探案例,展示了如何利用振幅谱和相位谱提升信噪比,并介绍了智能滤波等前沿技术在地震数据处理中的应用。

weixin_42557830的博客 406

java编程思想_第10章_内部类

1.内部类可以直接调用外部类的成员属性以及方法,但是外部类不可以直接调用内部类的成员属性以及方法,必须通过对象形式调用。 2.在拥有外部类的对象之前是不能创建内部类对象的,因为内部类可能会连接到外部类的对象上;但如果创建的是静态内部类就可以直接创建内部类对象。 3.内部类创建对象方式:1)创建外部类对象,在外部类中用一个方法返回内部类对象                           ...

ycllycll的博客 248

浮点数运算的陷阱与启示:FP16加法器/乘法器开发中的常见误区

本文深入探讨FP16加法器和乘法器开发中的常见误区,包括FP16格式解析、阶码对齐陷阱、尾数运算风险及规格化处理。通过Verilog实战代码展示防御性编程技巧,帮助开发者避免边界条件处理和异常状态管理中的错误,提升硬件设计的可靠性和效率。

dell8的博客 249

java编程思想 第10章 内部类 笔记

如果想从外部类的非静态方法之外的任意位置创建某个内部类的对象,那么就必须像在main()方法中那样,具体地指明这个对象的类型:OuterClassName.InnerClassName。当生成一个内部类的对象时,此对象与制造它的外围对象之间就有了一种联系,所以它能访问 其外围对象的所有成员,而不需要任何特殊条件。要想直接创建内部类的对象,必须使用外部类的对象来创建内部类对象。如果需要生成对外部类对象的引用,可以使用外部类的名字后面紧跟圆点和this。在拥有外部类对象之前是不可能创建内部类对象的。

weixin_42199601的博客 136

信道估计准则演进:从LS、MMSE到LMMSE的工程权衡

本文深入探讨了信道估计准则的演进历程,从LS、MMSE到LMMSE的工程权衡。通过对比分析三大经典算法的数学本质、工程实现及适用场景,揭示了在计算复杂度、实时性和性能之间的关键取舍。文章结合4G/5G基站项目实战经验,提供了算法选型的三维决策模型和前沿发展建议,为无线通信系统设计提供实用指导。

weixin_29327525的博客 282

手把手教你学simulink(90.1)--直流电动机实例:基于Simulink的基本模型的直流电动机(DC Motor)建模

直流电动机(DC Motor)因其结构简单、控制方便和良好的调速性能,广泛应用于各种工业自动化、机器人技术、家用电器以及航空航天等领域。为了更好地理解和应用直流电动机的工作原理及其控制系统,本项目旨在通过Simulink对直流电动机进行基本模型的建模与仿真。

MHD0815的博客 439

Java编程思想 第10章 内部类

Java编程思想 第10章 内部类 标签(空格分隔): JAVA学习 可以将一个类的定义放在另一个类的定义内部,这就是内部类。 10.1 创建内部类 public class Parcell { class Contents { private int i = 11; public int value() { r...

当初游的快了一点 432

uniapp - 微信支付报错 requestPayment:fail:HBuilder mainifest.json中配置的支付appid和生成订单使用的appid不一致,如果是HB调试请在线打包

uni-app,h5移动端网页,微信小程序,支付宝小程序,Android安卓,苹果ios,app,nvue,微信支付,报错,errMsg,requestPayment:fail:HBuildermainifest.json中配置的支付appid和生成订单使用的appid不一致,如果是HB调试请在线打包,http://ask.dcloud.net.cn/article/282,已经都检查了还是报错,如何解决这个问题,还是不行,错误,苹果微信支付报错,安卓app微信支付出错,打包,在线打包也不行,本地打包,支

🏆 前端领域优质创作者 3500

《Java编程思想》读书笔记 —— 第10章 内部类

内部类的定义可以从字面上理解,即一个定义在一个类内部的类,基本上就是“套娃”的意思,和前面一章所提到的嵌套接口其实是差不多的东西,但是语法上要比嵌套接口复杂很多。内部类的特点是允许程序员把逻辑相关的类组织在一起,前一章的简介部分也提到,内部类和接口都是使接口和实现方法分离的结构化方法。 就我的个人体验看来,内部类的语法相较于前面的内容确实是比较复杂的,语法点有点多,上个暑假读过一遍之后现在脑袋中的...

banqinghe的博客 247

怀旧版电脑GBC模拟器

再现原版GBC掌机的界面,电脑运行连游戏界面都一样大小,很怀旧,很真实,(英文版)强烈推荐,很小的文件,很难才找到的。

jdk-8u144-linux-x64.tar.gz.

该资源为搭建Linux系统Java环境用,资源的后缀为tar.gz格式的压缩包

JAVA 编程思想第10章--内部类概要

1 内部类可以访问外部内所有成员,无访问权限的限制 2 内部类对象实例化必须依赖外部类的实例,静态内部类无需依赖 3 不能直接引用外部类名称来实例化内部类 4 外部类A不能访问类B的private内部类 5 局部内部类---方法里的内部类

xuxinyl的博客 378

ET2012新版免狗免安装绿色软件

ET2012新版免狗免安祖昂绿色软件。,新界面,新视觉,

【笔记】《Java编程思想(第四版)》第10章-内部类

第10章 内部类 可以将一个类定义放在另一个类的定义内部,这就是内部类。 在最初,内部类看起来就像是一种代码隐藏机制:将类置于其他类的内部。但是,你将会了解到,内部类远不止如此,它了解外围类,并能与之通信;而且你用内部类写出的代码更加优雅而清晰,尽管并不总是这样。 10.1 创建内部类 创建内部类的方式就如同你想的一样——把类的定义置于外围类的里面。 //:innerclasses/Parcel1...

ZeromaXHe的博客 553

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

《JAVA编程思想》阅读笔记 第10章 内部类

在外部类的非静态方法中使用内部类时,用法与普通类的使用方式相同,但是在其余的任意地方创建内部类对象时,就必须用 OuterClassName.InnerClassName 的方式进行声明。 内部类能够访问外部类的所有元素,而且其对象能够访问外部类对象的所有成员。 ...

搬砖咸鱼 208

java编程思想第10章内部类 总结(1)

一、内部类的定义:将一个类的定义放在另外一个类的定义内部 10.1.创建内部类 a.一个基本的内部类的代码编写 10.2链接到外部类 a.内部类可以范文外部类的的成员 10.3使用.this与new a.当前类的的对象的引用使用 类名.this b.创建内部类,采用(外部类.内部类  变量= 外部类的引用.new  内部类名) 10.4内部类与向上转型 a.可以采用内部类的方式实

xiaocao000o的博客 272

Java编程思想阅读笔记(第10章内部类)

内部类 内部类是指在一个外部类的内部再定义一个类。内部类作为外部类的一个成员,并且依附于外部类而存在的 可以将一个类的定义放在另一个类定义内部,这就是内部类 内部类自动拥有对包裹它的基类所有成员的访问权限 内部类可为静态,可用protected和private修饰(而外部类只能使用public和缺省的包访问权限) 内部类主要有以下几类:成员内部类、局部内部类、静态内部类、匿名内部类 内...

u010391342的博客 220

[学习笔记][Java编程思想]第10章:内部类

内部类允许你把一些逻辑相关的类组织在一起,并控制位于内部的类的可视性。 1 创建内部类 创建内部类的方式是把类的定义置于外围类的里面。 外部类可以有一个方法,该方法返回一个指向内部类的引用。 从外部类的非静态方法之外的任意位置创建某个内部类的对象,需要具体地指明这个对象的类型:OuterClassName.InnerClassName。 2 链接到外部类 内部类还拥有其外围类的所有元素的访问权。 内

lbt_never的博客 419

Java编程思想,读书笔记八(第10章 内部类)

      第10章 内部类      可以将一个类的定义放到另一个类的定义内部,这就是内部类。内部类是一种非常有用的特性,因为它允许你把一些逻辑相关的类组织在一起,并控制位于内部的类的可视性。然而必须要了解,内部类和组合是完全不同的概念。在最初,内部类看起来像是一种代码隐藏机制:将类置于其他类的内部。但是,你将会了解到,内部类远不止如此,它了解外部类,并能与之通信;而且你用内部类写出的代码更加优...

闫玉林的博客 477

Java编程思想学习笔记(九) 第10章 内部类

创建内部类 可以将一个类的定义放在另一个类的定义内部,这就是内部类。 2.

143

Java编程思想(第四版) - 第10章 内部类

内部类

overkill 133

《Java编程思想》读书笔记一

  在美剧《硅谷》中有这样一个经典镜头,主人公 Richard 与同为开发工程师的女友闹分手,理由是两人对缩进方式有着截然不同的编程习惯,互相鄙视对方的代码风格。Richard 认为" one tab saves four spaces ”,缩进使用 Tab 键操作更快,更节省存 储空间,而女友坚持使用空格缩进,连续四次敲击空格的声音,把 Richard 折磨到几近崩溃,认为这是种精神折磨。 Richard 觉得难以相处,吵完架下楼梯时,不小心摔倒了 还淡定地说,"I just tried to go do

程序员波特 1029

《java编程思想》第十章内部类

1.嵌套类  如果不需要内部类对象与其外围类对象之间的联系,那么可以将内部类声明为static。这通常称为嵌套类。想要理解static应用于内部类时的含义,就必须记住,普通的内部类对象隐式地保存了一个引用,指向创建它的外围类的对象。然而,当内部类时static时,就不是这样了。  嵌套类意味着:要创建嵌套类的对象,并不需要其外围类的对象;不能从嵌套类的对象中访问非静态的外围类对象。  嵌套类

一吻成痴 338

【Java编程思想读书笔记】第十章:内部类+匿名类

参考书目:《Java编程思想》(第四版)、《Java2 实用教程》(第5版) 友链:【读书笔记】Java重要知识点整理与汇总 阅读《Java编程思想》(第四版)一书收获颇多,之所以想通过用博客记笔记的方式来读书,是因为这样可以倒逼自己仔细、反复地阅读书中的知识,找相对意义上的重点,并且由于人脑更适合输出型的学习,通过将内容边看、边记、边理解和边打字写文,相比直接反复阅读更有效益(当然这本书后续仍需反复阅读几十遍甚至百遍以上都不为过),而另一个原因就是这样也能够在阅读中通过博客来记录自己的学习历程,博客记录

Zhou_LC的博客 365
上一篇: 第9章接口(java编程思想)
下一篇: 第11章 持有对象(容器 java编程思想)
printf_myself
博客等级 码龄7年 1粉丝 19原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值