java 期末考试 小结
封装(Encapsulation):封装是将数据和对数据的操作封装在一个单独的单元中,通过访问修饰符(如private、public等)来控制对数据的访问。每个线程都有自己的栈,栈中存储的是基本数据类型的变量和对象的引用。Java虚拟机(JVM)有四种主要的内存存储区域,分别是堆(Heap)、栈(Stack)、方法区(Method Area)和程序计数器(Program Counter Regis
1.Java的三个版本
Java ee 平台标准版 java se 平台企业版 java me 平台微机版
2.Java 跨平台性
通常是指Java程序可以在不同的操作系统和硬件平台上运行,而无需对代码进行修改。这是由于Java的跨平台性是通过Java虚拟机(JVM)实现的。
Java程序首先被编译成字节码,这是一种与特定平台无关的中间代码。然后,JVM将字节码解释或编译成特定平台的机器代码,以便在该平台上运行。这使得Java程序可以在任何具有适当JVM的平台上运行。
3.Java程序运行机制
-
编写Java代码:你需要使用Java编程语言编写代码。Java代码是面向对象的,以类和方法的形式组织。
-
编译Java代码:使用Java编译器(javac)将Java代码编译成字节码文件(.class文件)。字节码是一种中间形式,可以在Java虚拟机(JVM)上运行。
-
加载字节码:Java虚拟机(JVM)负责加载字节码文件。它将字节码文件加载到内存中,并将其转换为机器可以理解的指令。
-
解释和执行:JVM解释并执行字节码指令。它逐行解释字节码指令,并将其转换为底层操作系统可以执行的机器代码。
-
运行时环境:JVM提供运行时环境,包括内存管理、垃圾回收和线程管理等。它负责管理程序的内存使用和执行过程中的资源。
4.JDK JRE JVM 三个开发平台
-
JDK(Java Development Kit)是Java开发工具包,提供了编译、调试和运行Java程序所需的工具和库。它包含了JRE以及编译器(javac)、调试器(jdb)、打包工具(jar)等开发工具。
-
JRE(Java Runtime Environment)是Java运行环境,用于执行Java程序。它包含了JVM和Java类库,可以在计算机上运行Java应用程序,但不包含用于开发Java程序的工具。
-
JVM(Java Virtual Machine)是Java虚拟机,是Java程序运行的核心组件。它负责将Java字节码翻译成机器码并执行。JVM是跨平台的,可以在不同操作系统上运行Java程序。
5.Java的开发流程
编辑:生成.java 文件
编译:(jvm) 生成 .class 字节码文件
运行:运行是指使用Java解释器将字节码文件翻译成机器代码,执行并显示结果
6.Java程序执行入口的主方法
java程序的执行入口是通过一个特定的方法来定义的,这个方法被称为"main"方法。在Java程序中,main方法是程序的起点,程序从这个方法开始执行。
main方法的定义格式如下:
public static void main(String[] args) {
// 执行的代码
}
7.合法的标识符
- 标识符是用于命名变量、方法、类等的名称。
- 标识符可以由字母、数字、下划线和美元符号组成。
- 标识符必须以字母、下划线或美元符号开头。
- 标识符区分大小写,例如"myVariable"和"myvariable"是不同的标识符。
- 标识符不能是Java关键字,如"public"、"class"等。
- 标识符的长度可以是任意的,但最好保持简洁和有意义。
- 标识符不能包含空格或特殊字符,如@、#、%等。
8.java 数据类型(8 + 3)
Java数据类型:
-
基本数据类型(Primitive Data Types)八种基本数据类型:
- 整数类型:byte、short、int、long
- 浮点类型:float、double
- 字符类型:char
- 布尔类型:boolean
-
引用数据类型(Reference Data Types)三种引用数据类型:
- 类(Class)
- 接口(Interface)
- 数组(Array)
// 声明整数类型变量
int age = 25;
// 声明浮点类型变量
double salary = 5000.50;
// 声明字符类型变量
char grade = 'A';
// 声明布尔类型变量
boolean isStudent = true;
// 声明类类型变量
String name = "John Smith";
// 声明数组类型变量
int[] numbers = {1, 2, 3, 4, 5};
9. 8种数据类型
类型 | 字节 | 取值范围 |
byte | 1 | -2^7 ~ 2^7 -1 |
short | 2 | -2 ^ 15~ 2^15 - 1 |
int | 4 | -2 ^ 31 ~ 2 ^ 31 -1 |
float | 4 | -2 ^ 31 ~ 2 ^ 31 -1 |
long | 8 | -2 ^ 63 ~ 2 ^ 63 -1 |
double | 8 | -2 ^ 63 ~ 2 ^ 63 -1 |
char | 2 | 0 ~ 2^ 16 -1 |
boolean | 1 | true ,false |
10.整型常量的三种表达式
Java整型常量有以下三种表达式:
-
十进制表达式:使用十进制数字表示整型常量。例如:int x = 10;
-
八进制表达式:使用前缀0表示整型常量为八进制。例如:int y = 012;
-
十六进制表达式:使用前缀0x或0X表示整型常量为十六进制。例如:int z = 0xA;
11.浮点数常量的两种表达式
-
十进制表示: 浮点数可以直接使用十进制表示,例如:
double num1 = 3.14;
float num2 = 2.71828f;
-
科学计数法表示: 浮点数也可以使用科学计数法表示,使用字母E(或e)表示指数部分,例如:
double num3 = 2.5e6; // 2.5乘以10的6次方,即2500000.0
float num4 = 1.23e-4f; // 1.23乘以10的-4次方,即0.000123
12.Java字符型的四种表达式是指以下四种形式:
-
直接赋值表达式: char c = 'a';
-
转义字符表达式: char c = '\n'; // 表示换行符
-
Unicode 表达式: char c = '\u0061'; // 表示字符 'a' 的 Unicode 编码
-
字符型变量运算表达式: char c = 'a'; int i = c + 1; // 将字符 'a' 的 ASCII 值加 1,得到整数 98
以下是一个简单的示例代码,演示了这四种表达式的使用:
public class CharExpressions {
public static void main(String[] args) {
// 直接赋值表达式
char c1 = 'a';
System.out.println("直接赋值表达式: " + c1);
// 转义字符表达式
char c2 = '\n';
System.out.println("转义字符表达式: " + c2);
// Unicode 表达式
char c3 = '\u0061';
System.out.println("Unicode 表达式: " + c3);
// 字符型变量运算表达式
char c4 = 'a';
int i = c4 + 1;
System.out.println("字符型变量运算表达式: " + i);
}
}
输出结果:
直接赋值表达式: a
转义字符表达式:
Unicode 表达式: a
字符型变量运算表达式: 98
13.字符串常量
字符串连接
String str1 = "Hello";
String str2 = "World";
String result = str1 + " " + str2; // "Hello World"
表达式中包含变量:
String name = "Alice";
int age = 25;
String message = "My name is " + name + " and I am " + age + " years old."; // "My name is Alice and I am 25 years old."
表达式中包含转义字符
String filePath = "C:\\Users\\Alice\\Documents\\file.txt";
String message = "The file is located at: " + filePath; // "The file is located at: C:\Users\Alice\Documents\file.txt"
表达式中包含方法调用:
String str = "Hello";
String result = str.concat(" World"); // "Hello World"
14.变量的定义和赋值
当在Java中定义变量时,需要指定变量的类型,然后给变量赋予一个值。以下是Java中定义和赋值变量的示例代码:
// 定义一个整数类型的变量,并赋值为10
int num = 10;
// 定义一个字符串类型的变量,并赋值为"Hello World"
String message = "Hello World";
// 定义一个布尔类型的变量,并赋值为true
boolean flag = true;
// 定义一个浮点数类型的变量,并赋值为3.14
float pi = 3.14f;
在上面的示例中,我们使用关键字int,String boolean和 float来定义变量的类型,然后使用 = 赋值运算符将值赋给变量。
15.用户输入的方法
1.使用Scanner类:Scanner类是Java中用于读取用户输入的常用类。以下是使用Scanner类获取用户输入的示例代码:
import java.util.Scanner;
public class UserInputExample {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
System.out.print("请输入一个整数:");
int number = scanner.nextInt();
System.out.println("您输入的整数是:" + number);
System.out.print("请输入一个字符串:");
String text = scanner.nextLine();
System.out.println("您输入的字符串是:" + text);
scanner.close();
}
}
2.使用BufferedReader类:BufferedReader类也可以用于读取用户输入。以下是使用BufferedReader类获取用户输入的示例代码:
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public class UserInputExample {
public static void main(String[] args) throws IOException {
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
System.out.print("请输入一个整数:");
int number = Integer.parseInt(reader.readLine());
System.out.println("您输入的整数是:" + number);
System.out.print("请输入一个字符串:");
String text = reader.readLine();
System.out.println("您输入的字符串是:" + text);
reader.close();
}
}
16.Java的三种注释方式
-
单行注释:以双斜杠(//)开头,用于注释单行代码。注释内容会被编译器忽略。
// 这是一个单行注释 int x = 10; // 这是另一个单行注释
-
多行注释:以斜杠星号(/)开头,以星号斜杠(/)结尾,用于注释多行代码。注释内容会被编译器忽略。
/* * 这是一个多行注释 * 可以跨越多行 */ int x = 10; /* 这是另一个多行注释 */
-
文档注释:以斜杠星号(/**)开头,以星号斜杠(*/)结尾,用于生成API文档。注释内容会被编译器和工具解析,并生成文档。
/** * 这是一个文档注释 * 可以包含对类、方法、参数等的描述 */ public class MyClass { /** * 这是一个文档注释 * @param x 参数x * @return 返回值 */ public int myMethod(int x) { return x; } }
17.三种转义字符
在Java中,有三种常用的转移语句,分别是:
1.break语句:用于终止当前循环或者switch语句,并跳出循环或者switch语句的执行。可以在循环或者switch语句内部的任何位置使用break语句。
例如,以下是使用break语句终止循环的示例:
for (int i = 0; i < 10; i++) {
if (i == 5) {
break; // 当i等于5时,终止循环
}
System.out.println(i);
}
2.continue语句:用于跳过当前循环的剩余部分,并继续下一次循环的执行。continue语句会立即跳到循环的下一次迭代。
例如,以下是使用continue语句跳过某次循环迭代的示例:
for (int i = 0; i < 10; i++) {
if (i == 5) {
continue; // 当i等于5时,跳过本次循环迭代,继续下一次迭代
}
System.out.println(i);
}
3.return语句:用于从方法中返回值,并终止方法的执行。return语句可以在方法的任何位置使用,用于提前结束方法的执行。
例如,以下是使用return语句返回值并终止方法的示例
public int add(int a, int b) {
return a + b; // 返回a和b的和,并终止方法的执行
}
18.一维数组二维数组的声明和创建
当声明和创建Java数组时,需要指定数组的类型、名称和大小(对于一维数组)或行数和列数(对于二维数组)。
一维数组的声明和创建:
// 声明一个整数类型的一维数组
int[] arr;
// 创建一个大小为5的整数类型的一维数组
arr = new int[5];
// 声明并创建一个大小为3的字符串类型的一维数组
String[] names = new String[3];
二维数组的声明和创建:
// 声明一个整数类型的二维数组
int[][] matrix;
// 创建一个3行4列的整数类型的二维数组
matrix = new int[3][4];
// 声明并创建一个2行3列的字符串类型的二维数组
String[][] grid = new String[2][3];
19.Java数组内存结构是什么
在Java中,数组是一个固定大小的连续内存块,用于存储相同类型的元素。数组的内存结构可以分为两部分:数组对象和数组元素。
数组对象:在Java中,数组是一个对象,它包含了有关数组的元数据,如数组的长度等。数组对象本身存储在堆内存中,并且它的引用存储在栈内存中。
数组元素:数组元素是实际存储数据的部分。元素的类型可以是任何Java数据类型,包括基本类型和引用类型。数组元素按照顺序存储在内存中,可以通过索引访问。
下面是一个示例代码,演示了Java数组的内存结构:
public class ArrayMemoryStructure {
public static void main(String[] args) {
// 创建一个整数数组
int[] numbers = new int[5];
// 数组对象存储在堆内存中
// 数组对象的引用存储在栈内存中
// 数组元素存储在堆内存中
// 设置数组元素的值
numbers[0] = 10;
numbers[1] = 20;
numbers[2] = 30;
numbers[3] = 40;
numbers[4] = 50;
// 访问数组元素的值
System.out.println(numbers[0]); // 输出: 10
System.out.println(numbers[1]); // 输出: 20
System.out.println(numbers[2]); // 输出: 30
System.out.println(numbers[3]); // 输出: 40
System.out.println(numbers[4]); // 输出: 50
}
}
20.java 虚拟机主要四种内存存储区(堆,栈,程序计数器,方法区)
Java虚拟机(JVM)有四种主要的内存存储区域,分别是堆(Heap)、栈(Stack)、方法区(Method Area)和程序计数器(Program Counter Register)。
-
堆(Heap):堆是Java虚拟机管理的最大的一块内存区域,用于存储对象实例和数组。堆是所有线程共享的,它在JVM启动时被创建,并且在JVM关闭时销毁。堆被划分为新生代(Young Generation)和老年代(Old Generation)两部分,新生代又被划分为Eden空间、Survivor1空间和Survivor2空间。
-
栈(Stack):栈是用于存储局部变量、方法参数和方法调用的信息的内存区域。每个线程在执行过程中都会创建一个栈帧(Stack Frame),用于存储方法的局部变量和操作数栈。栈帧随着方法的调用和返回而入栈和出栈。
-
方法区(Method Area):方法区用于存储类的结构信息,包括类的字段、方法、构造器、运行时常量池等。方法区是所有线程共享的,它在JVM启动时被创建,并且在JVM关闭时销毁。
-
程序计数器(Program Counter Register):程序计数器是一块较小的内存区域,它可以看作是当前线程所执行的字节码的行号指示器。每个线程都有一个独立的程序计数器,用于记录线程当前执行的位置。
21.堆和栈存储的数据类型和特点
-
堆(Heap):堆是用于动态分配内存的区域,存储的是对象和数组。在堆中分配的内存需要手动释放,否则会造成内存泄漏。堆是线程共享的,可以被多个线程访问和修改。
-
栈(Stack):栈是用于存储局部变量和方法调用的信息的区域。每个线程都有自己的栈,栈中存储的是基本数据类型的变量和对象的引用。栈是自动分配和释放的,当一个方法执行完毕后,栈中的变量会自动被销毁。
22.数组的下标遍历
- 使用普通的for循环:
int[] array = {1, 2, 3, 4, 5}; for (int i = 0; i < array.length; i++) { System.out.println("Index: " + i + ", Value: " + array[i]); }
- 使用增强型for循环(也称为for-each循环)
int[] array = {1, 2, 3, 4, 5}; for (int element : array) { int index = Arrays.asList(array).indexOf(element); System.out.println("Index: " + index + ", Value: " + element); }
23.冒泡排序
import java.util.Arrays;
/**
* @author tian
*/
public class test2 {
public static void bubbleSort(int[] arr){
for (int i = 0; i < arr.length-1; i++) {
for (int j = 0; j < arr.length-1-i; j++) {
if (arr[j]>arr[j+1]){
int tmp = arr[j];
arr[j] = arr[j+1];
arr[j+1] = tmp;
}
}
}
}
public static void main(String[] args) {
int[] arr1 = {12,13,1,31,3,13,1123};
bubbleSort(arr1);
System.out.println(Arrays.toString(arr1));
}
}
24.对象创建的语法
在Java中,对象的创建和使用涉及以下几个方面的语法和用法:
- 创建对象:使用
new
关键字创建对象,并调用构造函数初始化对象的属性。例如:ClassName objectName = new ClassName(); // 创建一个对象
- 访问对象的属性:使用对象名加点操作符
.
来访问对象的属性。例如:objectName.propertyName = value; // 设置对象的属性值 System.out.println(objectName.propertyName); // 输出对象的属性值
- 调用对象的方法:使用对象名加点操作符
.
来调用对象的方法。例如:objectName.methodName(); // 调用对象的方法
- 构造函数:构造函数用于初始化对象的属性。它与类名相同,没有返回类型,并可以有参数。例如:
public class ClassName { public ClassName() { // 构造函数代码 } }
- 对象的引用:Java中的对象是通过引用来访问的。对象变量存储的是对象的引用,而不是对象本身。例如:
ClassName object1 = new ClassName(); // 创建对象并将引用赋值给变量 ClassName object2 = object1; // 将object1的引用赋值给object2
- 对象的销毁:Java的垃圾回收机制会自动回收不再被引用的对象。当一个对象不再被任何引用变量引用时,它就成为垃圾,会被垃圾回收器回收。
25.对象的生命周期
Java对象的生命周期是指对象从创建到销毁的整个过程。下面是Java对象的生命周期的一些关键点:
- 创建对象:使用关键字
new
来创建一个对象,例如:MyClass obj = new MyClass();
- 初始化对象:在创建对象后,会调用对象的构造方法来进行初始化操作。
- 使用对象:可以通过对象引用来访问对象的属性和方法,进行各种操作。
- 对象可达性:对象在被引用时是可达的,当对象不再被引用时,它变得不可达。
- 垃圾回收:当对象不再可达时,Java的垃圾回收机制会自动回收这些不可达对象的内存空间。
- 销毁对象:在垃圾回收时,对象的
finalize()
方法会被调用,可以在该方法中进行一些资源释放的操作。
26.销毁对象的方法
在Java中,对象的销毁是由垃圾回收器(Garbage Collector)自动处理的,开发人员无需手动销毁对象。当对象不再被引用时,垃圾回收器会自动回收该对象的内存。
Java中的垃圾回收器使用了不同的算法来确定对象是否可回收,最常用的是基于引用计数和可达性分析的算法。当对象不再被引用时,垃圾回收器会将其标记为可回收,并在适当的时候释放其占用的内存。
以下是一些与Java对象销毁相关的概念和方法:
-
引用计数:每个对象都有一个引用计数器,当有新的引用指向对象时,计数器加一,当引用被删除时,计数器减一。当计数器为零时,对象被认为是不可达的,可以被回收。
-
可达性分析:通过从根对象(如线程栈、静态变量等)开始,通过引用链追踪对象的引用关系,判断对象是否可达。如果对象不可达,则可以被回收。
-
finalize()方法:这是一个在对象被垃圾回收前调用的方法。它可以被重写以在对象被销毁前执行一些清理操作。然而,由于finalize()方法的执行时间是不确定的,不建议过度依赖它。
需要注意的是,虽然开发人员无需手动销毁对象,但可以通过将对象引用设置为null来显式地释放对象所占用的内存。这样一来,对象就变得不可达,垃圾回收器会在适当的时候回收对象。
27.构造方法的定义和使用
当我们创建一个对象时,构造方法用于初始化对象的状态。在Java中,构造方法是一个特殊的方法,它具有与类相同的名称,并且没有返回类型。以下是关于Java构造方法的定义和使用的一些重要事项:
- 构造方法的命名必须与类名完全相同。
- 构造方法没有返回类型,包括void。
- 如果我们没有显式地定义构造方法,编译器将自动提供一个默认的无参构造方法。
- 如果我们定义了一个或多个构造方法,则默认构造方法将不再提供。
- 构造方法可以具有参数,这些参数用于初始化对象的成员变量。
- 构造方法可以重载,即在同一个类中可以有多个构造方法,只要它们的参数类型或数量不同即可。
- 使用
new
关键字调用构造方法来创建对象。
以下是一个示例,展示了如何定义和使用构造方法:
public class Person {
private String name;
private int age;
// 无参构造方法
public Person() {
name = "John Doe";
age = 0;
}
// 带参数的构造方法
public Person(String name, int age) {
this.name = name;
this.age = age;
}
// getter和setter方法
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
在上面的示例中,我们定义了一个Person
类,它具有两个构造方法:一个是无参构造方法,另一个是带有参数的构造方法。我们可以使用这些构造方法来创建Person
对象,并通过getter和setter方法访问和修改对象的属性。
28.面向对象的三个特征(分装,继承,多态)
Java面向对象的三个特征是封装、继承和多态。
-
封装(Encapsulation):封装是将数据和对数据的操作封装在一个单独的单元中,通过访问修饰符(如private、public等)来控制对数据的访问。封装可以隐藏实现细节,使代码更加模块化和易于维护。
-
继承(Inheritance):继承是指一个类可以继承另一个类的属性和方法。通过继承,子类可以重用父类的代码,并可以添加自己的特定功能。继承可以创建类的层次结构,使得代码更加可扩展和可重用。
-
多态(Polymorphism):多态是指同一个方法可以在不同的对象上产生不同的行为。多态允许使用一个父类类型的引用来引用子类对象,从而实现动态绑定和方法的重写。多态可以提高代码的灵活性和可扩展性。
29.类
当谈到Java编程时,类是一个重要的概念。类是Java中的基本构建块,用于创建对象。它是一个模板,用于定义对象的属性和行为。以下是关于Java类的一些重要信息:
- 类的定义:在Java中,类是使用关键字
class
定义的。以下是一个简单的类定义的示例:public class MyClass { // 类的成员变量 private int myVariable; // 类的构造方法 public MyClass(int value) { myVariable = value; } // 类的成员方法 public void myMethod() { System.out.println("Hello, World!"); } }
- 对象的创建:类用于创建对象。使用
new
关键字可以实例化一个类,并创建该类的对象。以下是一个创建MyClass
对象的示例:MyClass obj = new MyClass(10);
-
成员变量:类可以包含成员变量,它们用于存储对象的状态。成员变量可以是任何数据类型,例如整数、字符串等。在上面的示例中,
myVariable
是一个成员变量。 -
构造方法:类可以包含构造方法,用于初始化对象的属性。构造方法的名称必须与类的名称相同。在上面的示例中,
MyClass
类有一个接受一个整数参数的构造方法。 -
成员方法:类可以包含成员方法,用于定义对象的行为。成员方法可以访问和操作类的成员变量。在上面的示例中,
myMethod
是一个成员方法。 -
封装性:类支持封装性,这意味着它可以隐藏对象的内部实现细节,并通过公共方法来访问和操作对象。在上面的示例中,
myVariable
被声明为私有(private
),因此只能通过公共方法来访问。
类的种类:
当谈论Java类的种类时,可以从不同的角度进行分类。以下是一些常见的Java类的种类:
-
Object类:Object是所有类的父类,它定义了一些常用的方法,如equals()、hashCode()和toString()等。
-
抽象类(Abstract Class):抽象类是不能被实例化的类,它可以包含抽象方法和非抽象方法。抽象类通常用作其他类的基类。
-
接口(Interface):接口是一种抽象类型,它定义了一组方法的签名,但没有实现。类可以实现一个或多个接口,并提供接口中定义的方法的具体实现。
-
枚举类(Enum Class):枚举类是一种特殊类型的类,它限制实例的数量,并提供一组预定义的常量。枚举类通常用于表示一组相关的常量。
-
内部类(Inner Class):内部类是定义在另一个类内部的类。它可以访问外部类的成员,包括私有成员。
-
匿名类(Anonymous Class):匿名类是没有显式名称的类,它通常用于创建临时的、只使用一次的类实例。
-
泛型类(Generic Class):泛型类是具有类型参数的类。它可以在定义类时指定类型参数,并在实例化时提供实际的类型。
这只是一些常见的Java类的种类,还有其他一些特殊类型的类,如单例类、异常类等。
30.对象
Java对象是Java程序中的基本单元,它是类的一个实例。对象具有状态和行为,并且可以通过调用其方法来执行操作。每个对象都有其自己的唯一标识符,可以用于在程序中引用它。
以下是一个简单的Java代码示例,演示了如何创建一个对象:
public class MyClass {
private String name;
public MyClass(String name) {
this.name = name;
}
public void printName() {
System.out.println("Name: " + name);
}
public static void main(String[] args) {
MyClass myObject = new MyClass("John");
myObject.printName();
}
}
在上面的示例中,MyClass
是一个类,myObject
是MyClass
的一个对象。通过new
关键字和类的构造函数,我们创建了一个新的对象,并将其赋值给myObject
变量。然后,我们可以调用对象的方法来执行操作。
31.类和对象的关系
当谈到Java类和对象的关系时,对象是类的实例化。类是一个模板或蓝图,用于创建对象。类定义了对象的属性和行为。
以下是一些关于Java类和对象关系的重要事实:
-
类是对象的模板:类是一个抽象的概念,它定义了对象的属性和行为。它描述了对象应该具有的状态和行为。
-
对象是类的实例:对象是根据类定义创建的实体。可以使用关键字“new”创建对象。
-
类是对象的模板:可以根据类创建多个对象。每个对象都有自己的状态和行为,但它们共享相同的属性和方法。
-
类的成员:类可以包含成员变量和成员方法。成员变量是类的属性,它们用于存储对象的状态。成员方法是类的行为,它们用于执行操作。
-
对象的引用:可以使用对象的引用变量来访问对象的属性和方法。引用变量是指向对象的内存地址。
-
对象之间的交互:对象可以通过调用彼此的方法来进行交互。一个对象可以调用另一个对象的方法,以便共享信息和执行操作。
以下是一个简单的Java代码示例,演示了类和对象之间的关系:
// 定义一个类
class Person {
// 成员变量
String name;
int age;
// 成员方法
void display() {
System.out.println("Name: " + name);
System.out.println("Age: " + age);
}
}
// 创建对象并使用
public class Main {
public static void main(String[] args) {
// 创建对象
Person person1 = new Person();
// 设置对象的属性
person1.name = "John";
person1.age = 25;
// 调用对象的方法
person1.display();
}
}
32.访问修饰符
当在Java中定义类、方法或变量时,可以使用访问修饰符来控制对它们的访问权限。Java中有四种访问修饰符:public、private、protected和default(默认)。
- public:被public修饰的类、方法或变量可以从任何地方访问。
- private:被private修饰的类、方法或变量只能在同一个类中访问,其他类无法直接访问。
- protected:被protected修饰的类、方法或变量可以在同一个包中的其他类中访问,或者在不同包中的子类中访问。
- default(默认):如果没有指定任何访问修饰符,则默认为default修饰符。被default修饰的类、方法或变量可以在同一个包中的其他类中访问。
例如:
// 使用public修饰符
public class MyClass {
public int publicVar; // 公共变量
public void publicMethod() { // 公共方法
// 代码逻辑
}
}
// 使用private修饰符
public class MyClass {
private int privateVar; // 私有变量
private void privateMethod() { // 私有方法
// 代码逻辑
}
}
// 使用protected修饰符
public class MyClass {
protected int protectedVar; // 受保护变量
protected void protectedMethod() { // 受保护方法
// 代码逻辑
}
}
// 默认访问修饰符
class MyClass {
int defaultVar; // 默认变量
void defaultMethod() { // 默认方法
// 代码逻辑
}
}
32.Java当中重写和重载的区别
当涉及到Java中的方法时,重写(Override)和重载(Overload)是两个常见的概念。
重写(Override)是指在子类中定义一个与父类中具有相同名称、参数列表和返回类型的方法。重写方法允许子类提供自己的实现,覆盖掉父类中的实现。重写方法必须具有相同的方法签名,包括方法名称、参数列表和返回类型。
以下是一个重写方法的示例:
class Animal {
public void sound() {
System.out.println("Animal makes sound");
}
}
class Dog extends Animal {
@Override
public void sound() {
System.out.println("Dog barks");
}
}
public class Main {
public static void main(String[] args) {
Animal animal = new Dog();
animal.sound(); // 输出 "Dog barks"
}
}
重载(Overload)是指在同一个类中定义多个方法,它们具有相同的名称但参数列表不同。重载方法允许使用不同的参数来执行相似的操作。在调用重载方法时,编译器会根据传递给方法的参数类型和数量来决定要调用的方法。
以下是一个重载方法的示例:
class Calculator {
public int add(int a, int b) {
return a + b;
}
public double add(double a, double b) {
return a + b;
}
}
public class Main {
public static void main(String[] args) {
Calculator calculator = new Calculator();
System.out.println(calculator.add(2, 3)); // 输出 5
System.out.println(calculator.add(2.5, 3.5)); // 输出 6.0
}
}
33.给定一个字符串求字母,空格个数
public class Main {
public static void main(String[] args) {
String str = "Hello World";
int letterCount = 0;
int spaceCount = 0;
for (int i = 0; i < str.length(); i++) {
char c = str.charAt(i);
if (Character.isLetter(c)) {
letterCount++;
} else if (Character.isWhitespace(c)) {
spaceCount++;
}
}
System.out.println("Letter count: " + letterCount);
System.out.println("Space count: " + spaceCount);
}
}
这段代码中,我们首先定义了一个字符串str
,然后使用一个循环遍历字符串中的每个字符。通过Character.isLetter(c)
方法判断字符是否为字母,如果是则字母计数器letterCount
加一;通过Character.isWhitespace(c)
方法判断字符是否为空格,如果是则空格计数器spaceCount
加一。最后输出字母和空格的个数。
34.缓冲区长度的计算
当涉及到Java缓冲区的长度计算时,通常是指计算缓冲区的容量或剩余空间。下面是一些与Java缓冲区长度计算相关的信息:
-
缓冲区容量计算:
- 对于数组类型的缓冲区(如
byte[]
),可以使用数组的length
属性来获取缓冲区的容量。 - 对于
ByteBuffer
等直接缓冲区,可以使用capacity()
方法获取缓冲区的容量。
- 对于数组类型的缓冲区(如
-
缓冲区剩余空间计算:
- 对于数组类型的缓冲区,可以使用
length - position
来计算剩余空间。 - 对于
ByteBuffer
等直接缓冲区,可以使用remaining()
方法获取剩余空间。
- 对于数组类型的缓冲区,可以使用
下面是一些示例代码:
- 缓冲区容量计算(数组类型缓冲区):
byte[] buffer = new byte[1024]; int capacity = buffer.length; System.out.println("缓冲区容量:" + capacity);
- 缓冲区容量计算(直接缓冲区):
ByteBuffer buffer = ByteBuffer.allocateDirect(1024); int capacity = buffer.capacity(); System.out.println("缓冲区容量:" + capacity);
- 缓冲区剩余空间计算(数组类型缓冲区):
byte[] buffer = new byte[1024]; int position = 512; int remaining = buffer.length - position; System.out.println("剩余空间:" + remaining);
- 缓冲区剩余空间计算(直接缓冲区):
ByteBuffer buffer = ByteBuffer.allocateDirect(1024); buffer.position(512); int remaining = buffer.remaining(); System.out.println("剩余空间:" + remaining);
35.String类和StringBuffer类和String Builder 类的不同点和相同点
String类、StringBuffer类和StringBuilder类都是用来处理字符串的类,它们有以下的不同点和相同点:
不同点:
- 可变性:String类是不可变的,即一旦创建就不能被修改。而StringBuffer类和StringBuilder类是可变的,可以对字符串进行增删改操作。
- 线程安全性:String类是线程安全的,因为它的方法都是同步的。而StringBuffer类是线程安全的,因为它的方法都是同步的。而StringBuilder类是非线程安全的,因为它的方法没有同步修饰符。
- 性能:由于String类是不可变的,每次对字符串进行修改时都会创建一个新的String对象,所以在频繁修改字符串时,使用StringBuffer类和StringBuilder类会更高效。
相同点:
- 都是用来处理字符串的类,提供了丰富的方法来操作字符串。
- 都可以使用"+"来进行字符串的拼接。
- 都继承自Object类,并且实现了CharSequence接口。
37.字符串的比较
- s1 == s2 c/c++
- s1.equals(s2); // 返回值是boolean
- s1.equalsIgnoreCase(s2) //忽略大小写,是否相同 返回值为boolean
- s1.compareTo(s2) //返回int 如果返回大于零 s1 > s2;如果返回值小于零 s1 < s2; 如果返回值等于零 即 s1 = s2
- s1.compareToIgnore(s2); s1和s2 忽略大小写
38.字符串查找
方法 | 功能 |
char charAt(int index) | 返回index位置上字符,如果index为负数或者越界,抛出indexoutofBoundsExcp |
int indexOf(int ch) | 返回ch第一次出现的位置,没有返回-1 |
int indexOf(int ch,int fromIndex) | 从fromIndex位置开始找ch第一次出现位置,没有返回-1 |
int indexOf(String str) | 返回str第一次出现的位置,没有返回-1 |
int indexOf(String str,String fromIndex) | 从fromIndex位置开始找str第一次出现位置,没有返回-1 |
int lastIndexOf(int ch) | 返回ch第一次出现的位置,没有返回-1 |
int lastIndexOF(int ch,int fromIndex) | 从fromIndex位置开始找ch第一次出现位置,没有返回-1 |
int lastIndexOf(String str) | 返回str第一次出现的位置,没有返回-1 |
int lastIndexOF(String str,String fromIndex) | 从fromIndex位置开始找str第一次出现位置,没有返回-1 |
39.数值和字符串转换 valueOf()
String str = String.valueOf(123);
将字符串转换为整数
int val1 = Integer.parseInt("123");
double val2 = Double.parseDouble("12.25");
40.大小写的转换
s1.toUpperCase(); //转大写
s2.toLowerCase(); //转小写
41.字符串转数组
//字符串转数组
char[ ] chars = str1.toCharArray();
//数组转字符串
String s2 = new String(ch);
42.StringBuilder和StringBuffer 区别
当涉及到字符串的拼接和修改时,Java提供了两个主要的类:StringBuilder和StringBuffer。它们的主要区别在于线程安全性和性能。
-
线程安全性:
- StringBuffer:StringBuffer是线程安全的,可以在多个线程中同时使用,因为它的方法都是同步的(synchronized)。
- StringBuilder:StringBuilder是非线程安全的,不能在多个线程中同时使用,因为它的方法不是同步的。
-
性能:
- StringBuffer:由于StringBuffer的方法都是同步的,所以在多线程环境下使用时,会有额外的开销。但是在单线程环境下,其性能与StringBuilder相当。
- StringBuilder:由于StringBuilder的方法不是同步的,所以在单线程环境下,其性能比StringBuffer更好。
所以,如果你的代码在单线程环境下使用,建议使用StringBuilder,因为它的性能更好。如果你的代码在多线程环境下使用,建议使用StringBuffer,因为它是线程安全的。
更多推荐
所有评论(0)