内部类

article/2025/9/14 10:51:18

一、非静态内部类。

1、修饰符

非静态内部类有四个作用域,所以有四个修饰符。

                     private :   只能在外部类的内部使用。

                      protected :  可被与外部类处于同一个包中的其他类和外部类的子类所访问。

                     省略 :  只能被与外部类处于同一个包中的其他类访问。

                      public :  可以在任何地方被访问。

                      static:

2、特点

a) 非静态内部类成员可以直接访问外部类的私有成员(反过来是不成立的),外部类不能访问内部类的实现细节,例如内部类的成员变量。

b) 非静态内部类不可以拥有静态成员。

c) 局部内部类和匿名内部类不是类成员。

d) 在非静态内部类对象里,保存了一个它所寄生的外部类对象的引用。(当调用非静态内部类的实例方法时,必须有一个非静态内部类实例,非静态内部类实例必须寄生在外部类实例里)

public class Cow{private double weight;// 外部类的两个重载的构造器public Cow(){System.out.println("Cow.Cow()");}public Cow(double weight){System.out.println("Cow.Cow(double weight)");this.weight = weight;}// 定义一个非静态内部类class CowLeg{// 非静态内部类的两个实例变量private double length;private String color;// 非静态内部类的两个重载的构造器public CowLeg(){System.out.println("Cow.CowLeg.CowLeg()");}public CowLeg(double length , String color){this.length = length;this.color = color;System.out.println("Cow.CowLeg.CowLeg(double length , String color)");}// 下面省略length、color的setter和getter方法public void setLength(double length){this.length = length;}public double getLength(){return this.length;}public void setColor(String color){this.color = color;}public String getColor(){return this.color;}// 非静态内部类的实例方法public void info(){System.out.println("当前牛腿颜色是:"+ color + ", 高:" + length);// 直接访问外部类的private修饰的成员变量System.out.println("本牛腿所在奶牛重:" + weight);   //①}}public void test(){CowLeg cl = new CowLeg(1.12 , "黑白相间");cl.info();}public static void main(String[] args){Cow cow = new Cow(378.9);cow.test();//CowLeg cowleg = new Cow().new CowLeg();}
}

 e) 非静态内部类直接范围外部类的private访问权限的实例变量。

 

f) 在内部类方法中如何访问同名的变量

          外部类类名.this.变量     访问的是外部类的成员变量

           this.变量                        访问内部类的成员变量

           变量                               方法里面定义的变量

public class DiscernVariable{private String prop = "外部类的实例变量";private class InClass{private String prop = "内部类的实例变量";public void info(){String prop = "局部变量";// 通过 外部类类名.this.varName 访问外部类实例变量System.out.println("外部类的实例变量值:"+ DiscernVariable.this.prop);// 通过 this.varName 访问内部类实例的变量System.out.println("内部类的实例变量值:" + this.prop);// 直接访问局部变量System.out.println("局部变量的值:" + prop);}}public void test(){InClass in = new InClass();in.info();}public static void main(String[] args){new DiscernVariable().test();}
}
public class Outer{private int outProp = 9;public class Inner{private int inProp = 5;public void acessOuterProp(){// 非静态内部类可以直接访问外部类的private成员变量System.out.println("外部类的outProp值:"+ outProp);}}public void accessInnerProp(){// 外部类不能直接访问非静态内部类的实例变量,// 下面代码出现编译错误// System.out.println("内部类的inProp值:" + inProp);// 如需访问内部类的实例变量,必须显式创建内部类对象System.out.println("内部类的inProp值:"+ new Inner().inProp);}public static void main(String[] args){// 执行下面代码,只创建了外部类对象,还未创建内部类对象Outer out = new Outer();      //①out.accessInnerProp();}
}

g) 如需访问内部类的实例变量,必须显式创建内部类对象
                 new Inner().inProp

h)非静态内部类对象必须寄生在外部类对象里,而外部类对象则不一定有非静态内部类对象寄生其中。

i)   静态成员不能访问非静态成员

外部类的静态方法,静态代码块不能访问非静态内部类(包括不能使用非静态内部类定义变量,创建实例等),总之,不允许在外部类的静态成员中直接使用非静态内部类。

public class StaticTest{// 定义一个非静态的内部类,是一个空类private class In{}// 外部类的静态方法 public static void main(String[] args){// 下面代码引发编译异常,因为静态成员(main()方法)// 无法访问非静态成员(In类)//new In();}
}

j) Java不允许在非静态内部类里定义静态成员

public class InnerNoStatic{private class InnerClass{/*下面三个静态声明都将引发如下编译错误:非静态内部类不能有静态声明*/static{System.out.println("==========");}private static int inProp;private static void test(){}}
}

非静态内部类里不能有静态方法,静态成员变量,静态初始化快(但可以包含普通初始化快,非静态内部类普通初始化快的作用与外部类初始化快的作用完全相同)。

 

二、静态内部类(类内部类)

1、特点

a) 静态内部类属于外部类本身,而不属于外部类的某个对象。

static关键字的作用是把类的成员变量变成类相关,而不是实例相关,即static修饰的成员属于整个类,而不属于单个对象。内部类的上一级程序单元是外部类,使用static修饰可以将内部类变成外部类相关,而不是外部类实例相关。

public class StaticInnerClassTest{private int prop1 = 5;private static int prop2 = 9;static class StaticInnerClass{// 静态内部类里可以包含静态成员private static int age;public void accessOuterProp(){// 下面代码出现错误:// 静态内部类无法访问外部类的实例变量//	System.out.println(prop1);// 下面代码正常System.out.println(prop2);}}
}

b) 外部类依然不能直接访问静态内部类的成员。

c) 使用静态内部类的类名作为调用者来访问静态内部类的类成员。

d) 使用静态内部类对象作为调用者来访问静态内部类的实例成员。

public class AccessStaticInnerClass{static class StaticInnerClass{private static int prop1 = 5;private int prop2 = 9;}public void accessInnerProp(){// System.out.println(prop1);// 上面代码出现错误,应改为如下形式:// 通过类名访问静态内部类的类成员System.out.println(StaticInnerClass.prop1);// System.out.println(prop2);// 上面代码出现错误,应改为如下形式:// 通过实例访问静态内部类的实例成员System.out.println(new StaticInnerClass().prop2);}
}

三、接口里定义内部类

接口里定义的内部类默认使用public static 修饰(写不写都是,也只能这样写),也就是说,接口内部类只能是静态内部类。

四、使用内部类

1、在外部类以外使用非静态内部类

a) 非静态内部类的构造器必须使用外部类对象来调用。

class Out{// 定义一个内部类,不使用访问控制符,// 即只有同一个包中其他类可访问该内部类class In{public In(String msg){System.out.println(msg);}}
}
public class CreateInnerInstance{public static void main(String[] args){Out.In in = new Out().new In("测试信息");/*上面代码可改为如下三行代码:使用OutterClass.InnerClass的形式定义内部类变量Out.In in;创建外部类实例,非静态内部类实例将寄存在该实例中Out out = new Out();通过外部类实例和new来调用内部类构造器创建非静态内部类实例in = out.new In("测试信息");*/}
}

在外部类以外的地方创建非静态内部类的子类。

public class SubClass extends Out.In{//显示定义SubClass的构造器public SubClass(Out out){//通过传入的Out对象显式调用In的构造器out.super("hello");}
}

2、在外部类以外使用静态内部类

class StaticOut{// 定义一个静态内部类,不使用访问控制符,// 即同一个包中其他类可访问该内部类static class StaticIn{public StaticIn(){System.out.println("静态内部类的构造器");}}
}
public class CreateStaticInnerInstance{public static void main(String[] args){StaticOut.StaticIn in = new StaticOut.StaticIn();/*上面代码可改为如下两行代码:使用OutterClass.InnerClass的形式定义内部类变量StaticOut.StaticIn in;通过new来调用内部类构造器创建静态内部类实例in = new StaticOut.StaticIn();*/}
}

从上面代码可以看出,不管是静态内部类还是非静态内部类,它们声明变量的语法完全一样。区别只是在创建内部类对象时,静态内部类只需使用外部类即可调用构造器,而非静态内部类必须使用外部类对象来调用构造器

因为调用静态内部类的构造器时无需使用外部类对象,所以创建静态内部类的子类也比较简单。

public class StaticSubClass extends StaticOut.StaticIn{public static void main(String[] args) {new StaticSubClass();}
}

 使用静态内部类比使用非静态内部类要简单很多,使用静态内部类时,只要把外部类当成静态内部类的包空间即可


http://chatgpt.dhexx.cn/article/LsD4Z8tq.shtml

相关文章

python的类作用_python中类的作用是什么

简单来说,类是一种高级抽象,就是一种高级的数据类型,是对象的蓝图,就是用来定义你要用的对象的属性和行为的。 以下是面向对象简介 类(Class): 用来描述具有相同的属性和方法的对象的集合。它定义了该集合中每个对象所共有的属性…

C# 内部类的作用

作用一:限制对类的可访问性 有时候会遇到这样的需求,希望一个类仅能被另一个类(以及其派生类)访问。 代码 class BaseClass {public class PublicNestedClass { }protected class ProtectedNestedClass { }private class Priva…

内部类详解

1.成员内部类 1.样例 class OutClass {class InnerClass {public String SayHi() {return "你好";}} }2.特点 内部类能够无条件的访问外部类的成员变量,外部类要访问内部类成员变量需要使用new。内部类和外部类有相同名称的变量或者是方法,…

Java 静态内部类作用

需要了解2个概念:内部类和静态修饰符static 1)首先,用内部类是因为内部类与所在外部类有一定的关系,往往只有该外部类调用此内部类。所以没有必要专门用一个Java文件存放这个类。 2)静态都是用来修饰类的内部成员的。…

java内部类的四大作用

一、内部类的作用 我们为什么需要内部类?或者说内部类为啥要存在?其主要原因有如下几点: 内部类方法可以访问该类定义所在作用域中的数据,包括被 private 修饰的私有数据内部类可以对同一包中的其他类隐藏起来内部类可以解决java …

Flink--- 批处理 / 流处理

目录 Flink的主要特点 Flink 和 Spark Streaming 搭建maven工程 FlinkTutorial 添加Scala框架 和 Scala文件夹 Flink-批处理wordcount Flink---流处理wordcount Flink 是一个框架和分布式的处理引擎,用于对无界和有界数据流进行状态计算。 传统数据处理架构 事…

流数据处理利器

流处理 (Stream processing) 是一种计算机编程范式,其允许给定一个数据序列 (流处理数据源),一系列数据操作 (函数) 被应用到流中的每个元素。同时流处理工具可以显著提高程序员的开发效率,允许他们编写有效、干净和简洁的代码。 流数据处理在…

流处理(Stream)和批处理(Batch)

1 流处理和批处理的概念 在程序计算当中,同一节点或者不同节点之间的数据的传递是实时传递还是延迟传递,这就引出了两个概念。其实在非大数据领域这两个概念所起的作用也是很有限,但是在大数据领域,处理上亿级别的时候&#xff0…

管道模式 流处理

(一)介绍 管道这个名字源于自来水厂的原水处理过程。原水要经过管道,一层层地过滤、沉淀、去杂质、消毒,到管道另一端形成纯净水。我们不应该把所有原水的过滤都放在一个管道中去提纯,而应该把处理过程进行划分&#…

Flink流处理API大合集:掌握所有flink流处理技术,看这一篇就够了

大家好,我是百思不得小赵。 创作时间:2022 年 5 月 18 日 博客主页: 🔍点此进入博客主页 —— 新时代的农民工 🙊 —— 换一种思维逻辑去看待这个世界 👀 今天是加入CSDN的第1172天。觉得有帮助麻烦&#x…

Python流处理

转自 :https://www.toutiao.com/a6589000256896107015/?tt_frommobile_qq&utm_campaignclient_share&timestamp1534156143&appnews_article&utm_sourcemobile_qq&iid40708017633&utm_mediumtoutiao_ios&group_id6589000256896107015 F…

Stream流式处理

Stream流的三类方法 获取Stream:流创建一条流水线,并把数据放到流水线上准备。 中间方法:流水线上的操作一次操作完毕之后,还可以继续进行其他操作。 终结方法:一个Stream流只能有一个终结方法是流水线上的最后一个操作。 生成Stream流的…

流数据处理与分析

环境 名称 版本 系统 Ubuntu 18.04.4 LTS 内存 7.5GiB 处理器 Intel Core i7-8565U CPU 1.80GHz *8 图形 Intel UHD Graphics(Whiskey Lake 3*8 GT2) GNOME 3.28.2 操作系统类型 64位 磁盘 251.0 GB Storm 2.1.0 Zookeeper…

流处理系统

文章目录 引言如何发送事件流流处理不可靠的时钟容错总结 引言 清楚数据的类型有助于我们设计一个性能更高,更有针对性的数据系统,比如在线系统,离线系统(批处理)。近实时系统(流处理)等等。比如说批处理系统&#xf…

流处理简介

一. 流式处理简介 在我接触到java8流式处理的时候,我的第一感觉是流式处理让集合操作变得简洁了许多,通常我们需要多行代码才能完成的操作,借助于流式处理可以在一行中实现。比如我们希望对一个包含整数的集合中筛选出所有的偶数,…

【节点流和处理流】

节点流和处理流 基本介绍 节点流可以从特定数据源读取数据,如FileReader、FileWriter处理流:是对一个已存在的流的连接和封装,通过所封装的流的功能调用实现数据读写。如BufferedReader.处理流的构造方法总是要带一个其他的流对象做参数。一…

流数据处理

流数据处理strom 在2011年Storm开源之前,由于Hadoop的火红,整个业界都在喋喋不休地谈论大数据。Hadoop的高吞吐,海量数据处理的能力使得人们可以方便地处理海量数据。但是,Hadoop的缺点也和它的优点同样鲜明——延迟大&#xff0…

一. 流式处理简介

https://www.cnblogs.com/shenlanzhizun/p/6027042.html Java技术学习 https://www.itkc8.com 一. 流式处理简介 在我接触到java8流式处理的时候,我的第一感觉是流式处理让集合操作变得简洁了许多,通常我们需要多行代码才能完成的操作,借助…

Kafka基础-流处理

1. 什么是流处理? 首先,让我们说一下什么是数据流(也称为事件流)?它是无边界数据集的抽象说法,无边界意味着无限且不断增长,因为随着时间的推移,新数据会不断地到来。 除了无边界的…

流处理基本介绍

1. 什么是流处理 一种被设计来处理无穷数据集的数据处理系统引擎 2. 流处理的几个概念 1. 无穷数据(Unbounded data):一种持续生成,本质上是无穷尽的数据集。它经常会被称为“流数据”。然而,用流和批次来定义…