1.java的类和对象
类是对象的蓝图或模板,它定义了对象的属性和行为。类可以看作是一种自定义的数据类型,描述了具有相同特征和行为的对象。
类的组成部分:
- 属性(成员变量):类中的变量,用于描述对象的状态或特征。例如,一个
Car
类可能有color
、brand
、speed
等属性。 - 方法(成员函数):类中的函数,用于定义对象的行为或操作。例如,
Car
类可以有accelerate()
、brake()
等方法。 - 构造方法(Constructor):用于创建对象时初始化对象的状态。构造方法与类名相同,没有返回类型。
- 代码块:静态代码块和实例代码块,用于在类加载或对象创建时执行一些操作。
- 内部类:定义在类内部的类。
对象是类的实例,是根据类的定义创建的具体实体。每个对象都有自己的状态(属性值)和行为(方法)。
使用new
关键字可以创建类的对象。创建对象时,会调用类的构造方法进行初始化
面向对象的特性
Java的面向对象编程有四大特性:
- 封装(Encapsulation):将数据(属性)和行为(方法)封装在类中,隐藏内部实现细节,只暴露必要的接口。
- 继承(Inheritance):子类可以继承父类的属性和方法,实现代码复用和扩展。
- 多态(Polymorphism):同一个方法在不同对象中有不同的实现方式。
- 抽象(Abstraction):通过抽象类和接口定义通用的行为,隐藏复杂的实现细节。
当在一个源文件中定义多个类,并且还有import语句和package语句时,要特别注意这些规则。
- 一个源文件中只能有一个 public 类
- 一个源文件可以有多个非 public 类
- 源文件的名称应该和 public 类的类名保持一致。例如:源文件中 public 类的类名是 Employee,那么源文件应该命名为Employee.java。
- 如果一个类定义在某个包中,那么 package 语句应该在源文件的首行。
- 如果源文件包含 import 语句,那么应该放在 package 语句和类定义之间。如果没有 package 语句,那么 import 语句应该在源文件中最前面。
- import 语句和 package 语句对源文件中定义的所有类都有效。在同一源文件中,不能给不同的类不同的包声明。
2.JAVA包
Java包是Java语言中一种非常重要的组织代码的方式。可以将包理解为文件夹,用于组织和管理相关的类和接口。就像我们用电脑的文件夹来整理文件一样,Java包用来整理Java代码文件,使其结构清晰,易于管理和维护。
从概念上讲,Java包主要有以下几个方面的作用:
- 命名空间管理 (Namespace Management):
- 在Java开发中,随着项目规模的增大,可能会出现类名冲突的问题。比如,你可能在不同的地方定义了两个都叫做
MyClass
的类。如果没有包,Java编译器就无法区分你要使用的是哪个MyClass
。 - 包通过创建唯一的命名空间来解决这个问题。每个包都代表一个独立的命名空间,在同一个包内的类名是唯一的。即使不同的包中存在同名的类,由于它们属于不同的命名空间,Java编译器也能通过包名来区分它们,从而避免了类名冲突。
- 例如,你可以创建一个名为
com.example.myapp.ui
的包来存放用户界面相关的类,再创建一个名为com.example.myapp.data
的包来存放数据处理相关的类。这样,即使两个包中都有一个名为Button
的类,由于包名不同 (com.example.myapp.ui.Button
和com.example.myapp.data.Button
),它们也是不同的类。
- 在Java开发中,随着项目规模的增大,可能会出现类名冲突的问题。比如,你可能在不同的地方定义了两个都叫做
- 代码组织和管理 (Code Organization and Management):
- 大型Java项目通常包含成千上万个类和接口。如果没有包来组织代码,所有的类都散落在同一个目录下,这将非常混乱,难以维护和管理。
- 包可以将功能相关的类和接口组织在一起,形成逻辑上的模块。例如,可以将所有处理输入/输出的类放在
java.io
包中,将所有处理集合的类放在java.util
包中。 - 这种模块化的组织方式使得代码结构更加清晰,易于查找、理解、重用和维护。开发者可以更容易地找到需要的类,也更容易理解代码的功能和结构。
- 访问控制 (Access Control):
- Java包提供了一种包级别的访问控制机制。在Java中,除了
public
、private
和protected
这三种常用的访问修饰符外,还有一种默认的访问修饰符(也称为包私有或package-private)。 - 当一个类成员(例如,字段、方法、构造器)没有使用任何访问修饰符时,它的访问权限就是包私有。这意味着只有同一个包内的类才能访问这个成员,不同包的类无法直接访问。
- 包级别的访问控制可以帮助开发者隐藏实现细节,限制不必要的访问,从而提高代码的安全性和模块化程度。
- Java包提供了一种包级别的访问控制机制。在Java中,除了
如何创建和使用Java包:
-
创建包: 要创建一个Java包,你需要在你的Java源文件(
.java
文件)的第一行使用package
语句声明包名。包名通常采用反向域名的格式,例如com.example.myapp
。例如:package com.example.myapp; public class MyClass { // ... 类的内容 ... }
-
目录结构和包名: Java包的命名和目录结构是紧密相关的。包名中的每一部分都对应着文件系统中的一个目录层级。例如,包名
com.example.myapp
就对应着目录结构com/example/myapp/
。你的Java源文件应该放在与包名对应的目录下。- 例如,如果你的包名是
com.example.myapp
,那么MyClass.java
文件应该放在com/example/myapp/
目录下。 - 编译器会根据包名和目录结构来查找和组织类文件。
- 例如,如果你的包名是
-
导入包: 当你想在一个类中使用来自其他包的类时,你需要使用
import
语句导入目标类所在的包。有两种导入方式:- 导入单个类: 使用
import 包名.类名;
语句导入指定的类。例如:
import java.util.ArrayList; // 导入 java.util 包中的 ArrayList 类 public class MyClass { public static void main(String[] args) { ArrayList
list = new ArrayList<>(); // 可以直接使用 ArrayList 类 // ... } } - 导入整个包: 使用
import 包名.*;
语句导入整个包中的所有类。例如:
import java.util.*; // 导入 java.util 包中的所有类 public class MyClass { public static void main(String[] args) { ArrayList
list = new ArrayList<>(); // 可以直接使用 ArrayList 类 HashMap map = new HashMap<>(); // 可以直接使用 HashMap 类 // ... } } 注意: 虽然导入整个包很方便,但有时会降低代码的可读性,并且可能增加编译时间。建议只导入你真正需要的类。
- 导入单个类: 使用
-
默认包 (Default Package): 如果你的Java源文件没有使用
package
语句声明包名,那么该文件中的类就属于默认包。默认包是一个匿名的包,它没有名字。- 不建议使用默认包进行大型项目开发,因为它会使代码难以组织和管理,并且容易造成命名冲突。通常只在小型示例程序或学习代码中使用默认包。
- 在默认包中的类,只能被同一个默认包中的类访问,不同包的类无法访问默认包中的类。
Java标准库中的包 (Predefined/Standard Java Packages):
Java标准库提供了大量的预定义包,也称为标准Java包或 Java API 包,这些包包含了各种各样的类和接口,用于完成各种常见的任务。这些包极大地扩展了Java的功能,开发者可以直接使用这些包中的类来构建应用程序,而无需从零开始编写所有代码。
- 避免命名冲突: 通过创建唯一的命名空间,防止类名冲突。
- 组织代码结构: 将相关的类和接口组织在一起,提高代码的模块化和可读性。
- 代码重用: 包使得代码更易于重用,开发者可以利用已有的包来构建新的应用程序。
- 访问控制: 提供包级别的访问控制,增强代码的安全性和模块化程度。
- 简化开发: Java标准库提供了大量的预定义包,极大地简化了开发过程。
3.JAVA基本数据类型
变量就是申请内存来存储值。也就是说,当创建变量的时候,需要在内存中申请空间。
内存管理系统根据变量的类型为变量分配存储空间,分配的空间只能用来储存该类型数据
数据类型 | 默认值 |
---|---|
int | 0 |
long | 0L |
short | 0 |
char | ‘\u0000′(空字符) |
byte | 0 |
float | 0.0f |
double | 0.0d |
boolean | false |
引用类型(类、接口、数组) | null |
Java中的引用类型 (Reference Types)
Java中的引用类型 (Reference Types) 是Java语言中数据类型的一个重要组成部分,与基本类型 (Primitive Types) 相对。 理解引用类型对于掌握Java内存管理、对象操作以及面向对象编程至关重要。
核心概念:引用 vs. 对象
引用类型的核心在于 "引用" 这个词。引用 (Reference) 本身不是对象,而是一个指向对象在内存中位置的地址。 你可以把引用想象成一个遥控器,而对象就是被遥控的电视机。遥控器本身不是电视机,但通过遥控器你可以控制电视机。
关键点:
- 引用变量存储的是对象的内存地址,而不是对象本身的数据。
- 多个引用变量可以指向同一个对象。 就像多个遥控器可以控制同一台电视机。
- 对对象的操作是通过引用进行的。 你通过遥控器来换台、调音量,而不是直接去碰电视机。
Java 中的引用类型主要包括:
-
类 (Class):
- 这是最常见的引用类型。你自定义的每一个类都定义了一个新的引用类型。
- 例如:
String
,Date
,Scanner
, 以及你自定义的Person
,Car
,Student
等类都是引用类型。 - 当你声明一个类类型的变量时,你创建了一个引用变量,它可以指向该类的对象。
String str; // 声明一个 String 类型的引用变量 str str = new String("Hello"); // 创建一个新的 String 对象,并将它的地址赋值给 str
-
接口 (Interface):
- 接口也定义了一种引用类型。接口本身不能被实例化 (不能
new
一个接口),但接口类型的变量可以指向实现了该接口的类的对象。 - 例如:
List
,Set
,Map
,Comparable
等都是接口类型。
List
list; // 声明一个 List 接口类型的引用变量 list list = new ArrayList<>(); // 创建一个 ArrayList 对象 (实现了 List 接口),并将它的地址赋值给 list - 接口也定义了一种引用类型。接口本身不能被实例化 (不能
-
数组 (Array):
- 数组也是引用类型,即使数组存储的是基本类型的数据。
- 数组变量存储的是数组对象在内存中的起始地址。
int[] numbers; // 声明一个 int 数组类型的引用变量 numbers numbers = new int[5]; // 创建一个包含 5 个 int 元素的数组对象,并将它的地址赋值给 numbers
-
枚举 (Enum):
- 枚举类型也是引用类型,它是一种特殊的类,用于定义一组命名的常量。
enum Color { RED, GREEN, BLUE } Color myColor; // 声明一个 Color 枚举类型的引用变量 myColor myColor = Color.RED; // 将 Color 枚举类型的常量 RED 的引用赋值给 myColor
引用类型与基本类型的对比:
特性 | 基本类型 (Primitive Types) | 引用类型 (Reference Types) |
---|---|---|
数据存储 | 直接存储值 | 存储对象的内存地址 (引用) |
内存分配 | 在栈 (Stack) 中分配 | 对象在堆 (Heap) 中分配,引用在栈或堆中 |
默认值 | 有默认值 (如 int 的 0 , boolean 的 false ) |
默认值为 null |
大小 | 大小固定 (例如 int 始终是 4 字节) |
大小不固定,取决于对象内容 |
传递方式 | 按值传递 (Pass-by-value) | 按引用传递 (Pass-by-reference 的值) |
类型 | byte , short , int , long , float , double , char , boolean |
类, 接口, 数组, 枚举 |
内存分配:堆 (Heap) 和 栈 (Stack)
- 堆 (Heap): 所有引用类型的对象都存储在堆内存中。堆内存是动态分配的,Java 虚拟机 (JVM) 在运行时根据需要分配堆内存给对象。堆内存由垃圾回收器 (Garbage Collector) 自动管理。
- 栈 (Stack): 栈内存主要用于存储基本类型的变量和引用类型的引用变量 (局部变量)。栈内存是后进先出 (LIFO) 的,方法调用时会在栈中创建栈帧,方法执行完毕栈帧会被弹出。
引用类型变量的声明和初始化:
-
声明: 声明引用类型变量时,需要指定变量的类型 (类名、接口名、数组类型等) 和变量名。
ClassName variableName; InterfaceName variableName; DataType[] variableName; EnumName variableName;
-
初始化: 引用类型变量在声明后,默认值为
null
。要使引用变量指向一个实际的对象,需要使用new
关键字创建对象,并将返回的对象引用赋值给变量。variableName = new ClassName(constructorArguments); // 创建类的对象 variableName = new DataType[arraySize]; // 创建数组对象 variableName = EnumName.CONSTANT_NAME; // 枚举类型的常量已经是对象引用
也可以将一个已经指向对象的引用变量赋值给另一个引用变量:
String str1 = new String("Hello"); String str2 = str1; // str2 和 str1 指向同一个 String 对象
null
引用:
null
是一个特殊的字面量,表示引用变量没有指向任何对象。- 引用类型变量的默认值就是
null
。 - 如果尝试通过
null
引用访问对象的成员 (例如调用方法或访问字段),会抛出NullPointerException
(空指针异常)。这是Java程序中常见的运行时错误。
引用传递 (按引用传递的值 – Pass-by-reference value):
Java 中对于引用类型,实际上是 按引用传递的值 (Pass-by-reference value) 或者更准确地说,按共享对象传递 (Pass-by-sharing)。 这意味着:
- 当将引用类型变量作为参数传递给方法时,方法接收到的是引用变量值的副本。
- 这个副本仍然指向与原始引用变量相同的对象。
- 因此,在方法内部通过引用副本修改对象的内容,会影响到方法外部通过原始引用变量访问到的对象。
- 但是,如果在方法内部改变引用变量副本的指向 (例如让它指向一个新的对象或
null
),不会影响到原始引用变量的指向。
示例:
class Person {
String name;
Person(String name) {
this.name = name;
}
void changeName(String newName) {
this.name = newName;
}
}
public class ReferenceTypeExample {
public static void main(String[] args) {
Person person1 = new Person("Alice");
Person person2 = person1; // person2 和 person1 指向同一个 Person 对象
System.out.println("person1's name: " + person1.name); // 输出: person1's name: Alice
System.out.println("person2's name: " + person2.name); // 输出: person2's name: Alice
person2.changeName("Bob"); // 通过 person2 修改对象的名字
System.out.println("person1's name after change through person2: " + person1.name); // 输出: person1's name after change through person2: Bob (person1 的名字也被改变了)
System.out.println("person2's name after change: " + person2.name); // 输出: person2's name after change: Bob
person2 = new Person("Charlie"); // person2 指向新的 Person 对象 (但 person1 仍然指向原来的对象)
System.out.println("person1's name after person2 points to a new object: " + person1.name); // 输出: person1's name after person2 points to a new object: Bob (person1 的名字仍然是 Bob)
System.out.println("person2's name after pointing to a new object: " + person2.name); // 输出: person2's name after pointing to a new object: Charlie
}
}
==
运算符和 equals()
方法:
==
运算符: 对于引用类型变量,==
比较的是两个引用变量是否指向同一个对象 (内存地址是否相同)。equals()
方法:equals()
方法是Object
类中定义的方法,子类可以重写它来定义对象内容相等的判断标准。 默认情况下,equals()
方法的行为与==
相同 (比较引用)。 但很多类 (如String
,Integer
,Date
等) 都重写了equals()
方法,使其比较对象的内容是否相等。
示例:
String str1 = new String("Hello");
String str2 = new String("Hello");
String str3 = str1;
System.out.println(str1 == str2); // 输出: false (str1 和 str2 指向不同的 String 对象,即使内容相同)
System.out.println(str1 == str3); // 输出: true (str1 和 str3 指向同一个 String 对象)
System.out.println(str1.equals(str2)); // 输出: true (String 类的 equals() 方法比较的是字符串内容)
垃圾回收 (Garbage Collection):
- 当一个对象不再被任何引用变量指向时 (或者说,变得 "不可达" 时),JVM 的垃圾回收器会定期回收这些对象所占用的内存空间。
- 垃圾回收器会自动管理堆内存,程序员不需要手动释放对象占用的内存 (像 C++ 中那样)。这大大简化了内存管理,并减少了内存泄漏的风险。
Java 常量
常量在程序运行时是不能被修改的。
在 Java 中使用 final 关键字来修饰常量,声明方式和变量类似:
final double PI = 3.1415927;
自动类型转换
整型、实型(常量)、字符型数据可以混合运算。运算中,不同类型的数据先转化为同一类型,然后进行运算。
低 ————————————> 高
byte,short,char—> int —> long—> float —> double
数据类型转换必须满足如下规则:
-
- 不能对boolean类型进行类型转换。
-
- 不能把对象类型转换成不相关类的对象。
-
- 在把容量大的类型转换为容量小的类型时必须使用强制类型转换。
-
- 转换过程中可能导致溢出或损失精度
- 浮点数到整数的转换是通过舍弃小数得到,而不是四舍五入
4.JAVA变量
局部变量(Local Variables):局部变量是在方法、构造函数或块内部声明的变量,它们在声明的方法、构造函数或块执行结束后被销毁,局部变量在声明时需要初始化,否则会导致编译错误。
实例变量(Instance Variables):实例变量是在类中声明,但在方法、构造函数或块之外,它们属于类的实例,每个类的实例都有自己的副本,如果不明确初始化,实例变量会被赋予默认值(数值类型为0,boolean类型为false,对象引用类型为null)。
静态变量或类变量(Class Variables):类变量是在类中用 static 关键字声明的变量,它们属于类而不是实例,所有该类的实例共享同一个类变量的值,类变量在类加载时被初始化,而且只初始化一次
public class ExampleClass {
static int classVar; // 类变量
}
参数变量(Parameters):参数是方法或构造函数声明中的变量,用于接收调用该方法或构造函数时传递的值,参数变量的作用域只限于方法内部
方法参数变量的值传递方式有两种:值传递和引用传递。
- 值传递:在方法调用时,传递的是实际参数的值的副本。当参数变量被赋予新的值时,只会修改副本的值,不会影响原始值。Java 中的基本数据类型都采用值传递方式传递参数变量的值。
- 引用传递:在方法调用时,传递的是实际参数的引用(即内存地址)。当参数变量被赋予新的值时,会修改原始值的内容。Java 中的对象类型采用引用传递方式传递参数变量的值。
Java 的参数传递机制核心理解: 始终是 “按值传递”
- 对于基本类型参数: 当你将基本类型变量作为参数传递给方法时,方法接收到的是该变量值的副本。 在方法内部对参数的任何修改,都只作用于这个副本,而不会影响到原始变量的值。
- 对于引用类型参数: 当您将引用类型变量(例如,一个对象引用)作为参数传递给方法时,方法接收到的是该引用变量值的副本。 关键在于,这个副本仍然指向与原始引用变量相同的对象。
- 这意味着,在方法内部,你可以通过这个引用副本来修改对象的内容 (状态)。 这些修改会反映到原始引用变量所指向的同一个对象上。 因此,看起来像是通过“引用”修改了外部的对象。
- 但是,如果你在方法内部改变引用变量副本的指向 (例如,让它指向一个新的对象,或者赋值为
null
),这只会改变副本的指向,而不会影响到原始引用变量的指向。原始引用变量仍然指向最初的对象(除非它本身就是null
,或者在方法外部被重新赋值)。
5.JAVA修饰符
Java语言提供了很多修饰符,主要分为以下两类:
- 访问修饰符
- 非访问修饰符
修饰符用来定义类、方法或者变量,通常放在语句的最前端
访问控制修饰符
Java中,可以使用访问控制符来保护对类、变量、方法和构造方法的访问。Java 支持 4 种不同的访问权限。
- default (即默认,什么也不写): 在同一包内可见,不使用任何修饰符。使用对象:类、接口、变量、方法。
- private : 在同一类内可见。使用对象:变量、方法。 注意:不能修饰类(外部类)
- public : 对所有类可见。使用对象:类、接口、变量、方法
- protected : 对同一包内的类和所有子类可见。使用对象:变量、方法。 注意:不能修饰类(外部类)
默认访问修饰符-不使用任何关键字
如果在类、变量、方法或构造函数的定义中没有指定任何访问修饰符,那么它们就默认具有默认访问修饰符。
默认访问修饰符的访问级别是包级别(package-level),即只能被同一包中的其他类访问。
如下例所示,变量和方法的声明可以不使用任何修饰符
方法继承的规则:
- 父类中声明为 public 的方法在子类中也必须为 public。
- 父类中声明为 protected 的方法在子类中要么声明为 protected,要么声明为 public,不能声明为 private。
- 父类中声明为 private 的方法,不能够被子类继承。
abstract 修饰符
抽象类:
抽象类不能用来实例化对象,声明抽象类的唯一目的是为了将来对该类进行扩充。
一个类不能同时被 abstract 和 final 修饰。如果一个类包含抽象方法,那么该类一定要声明为抽象类,否则将出现编译错误。
抽象类可以包含抽象方法和非抽象方法。
抽象方法
抽象方法是一种没有任何实现的方法,该方法的具体实现由子类提供。
抽象方法不能被声明成 final 和 static。
任何继承抽象类的子类必须实现父类的所有抽象方法,除非该子类也是抽象类。
如果一个类包含若干个抽象方法,那么该类必须声明为抽象类。抽象类可以不包含抽象方法。
synchronized 修饰符
synchronized 关键字声明的方法同一时间只能被一个线程访问。synchronized 修饰符可以应用于四个访问修饰符。
volatile 修饰符
volatile 修饰的成员变量在每次被线程访问时,都强制从共享内存中重新读取该成员变量的值。而且,当成员变量发生变化时,会强制线程将变化值回写到共享内存。这样在任何时刻,两个不同的线程总是看到某个成员变量的同一个值。
一个 volatile 对象引用可能是 null。
6.基础类型的包装
在实际开发过程中,我们经常会遇到需要使用对象,而不是内置数据类型的情形。为了解决这个问题,Java 语言为每一个内置数据类型提供了对应的包装类。
包装类 | 基本数据类型 |
---|---|
Boolean | boolean |
Byte | byte |
Short | short |
Integer | int |
Long | long |
Character | char |
Float | float |
Double | double |
7.String
创建字符串
String str = "Runoob";
String s1 = "Runoob"; // String 直接创建
String s2 = "Runoob"; // String 直接创建
String s3 = s1; // 相同引用
String s4 = new String("Runoob"); // String 对象创建
String s5 = new String("Runoob"); // String 对象创建
char[] helloArray = { 'r', 'u', 'n', 'o', 'o', 'b'};
String helloString = new String(helloArray);
System.out.println( helloString );
创建格式化字符串
String 类使用静态方法 format() 返回一个String 对象
String 类的静态方法 format() 能用来创建可复用的格式化字符串
String fs;
fs = String.format("浮点型变量的值为 " +
"%f, 整型变量的值为 " +
" %d, 字符串变量的值为 " +
" %s", floatVar, intVar, stringVar);
public class Main {
public static void main(String[] args) {
String s1 = "hello";
String s2 = "hello";
System.out.println(s1 == s2);
System.out.println(s1.equals(s2));
}
}
从表面上看,两个字符串用==
和equals()
比较都为true
,但实际上那只是Java编译器在编译期,会自动把所有相同的字符串当作一个对象放入常量池,自然s1
和s2
的引用就是相同的。
8.StringBuffer 和 StringBuilder
当对字符串进行修改的时候,需要使用 StringBuffer 和 StringBuilder 类。
和 String 类不同的是,StringBuffer 和 StringBuilder 类的对象能够被多次的修改,并且不产生新的未使用对象
在使用 StringBuffer 类时,每次都会对 StringBuffer 对象本身进行操作,而不是生成新的对象,所以如果需要对字符串进行修改推荐使用 StringBuffer。
StringBuilder 类在 Java 5 中被提出,它和 StringBuffer 之间的最大不同在于 StringBuilder 的方法不是线程安全的(不能同步访问)。
由于 StringBuilder 相较于 StringBuffer 有速度优势,所以多数情况下建议使用 StringBuilder 类。
public class RunoobTest{
public static void main(String[] args){
StringBuilder sb = new StringBuilder(10);
sb.append("Runoob..");
System.out.println(sb);
sb.append("!");
System.out.println(sb);
sb.insert(8, "Java");
System.out.println(sb);
sb.delete(5,8);
System.out.println(sb);
}
}
在Java中,有很多class
的定义都符合这样的规范:
- 若干
private
实例字段; - 通过
public
方法来读写实例字段。
JavaBean主要用来传递数据,即把一组数据组合成一个JavaBean便于传输。此外,JavaBean可以方便地被IDE工具分析,生成读写属性的代码,主要用在图形界面的可视化设计中。
通过IDE,可以快速生成getter
和setter
。例如,在Eclipse中,先输入以下代码:
public class Person {
private String name;
private int age;
}
然后,点击右键,在弹出的菜单中选择“Source”,“Generate Getters and Setters”,在弹出的对话框中选中需要生成getter
和setter
方法的字段,点击确定即可由IDE自动完成所有方法代码。
JavaBean是一种符合命名规范的class
,它通过getter
和setter
来定义属性;
属性是一种通用的叫法,并非Java语法规定;
可以利用IDE快速生成getter
和setter
;
使用Introspector.getBeanInfo()
可以获取属性列表。