七:Java基础类库
引言:String类是所有项目开发之中一定会使用到的一个功能类,且特点如下:
1)每一个字符串的常量都属于一个String类的匿名对象,并且不可更改;
2)String有两个常量池:静态常量池和运行时常量池;
3)String类对象实例化使用直接赋值的形式完成,这样可以直接将对象保存在对象池之中,方便取用。
而String类的最大弊端是内容不允许修改,所以为了解决String字符串不能修改的缺点,Java程序提供了一个StringBuffer类来实现字符串内容的修改。
范例:String与StringBuffer类的对比
代码 | 结果 | 描述 | |
String类 | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { public static void change(String temp) { } | hello | 内容没改 |
StringBuffer类 | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { public static void change(StringBuffer temp) { } | hello world! | 利用StringBuffer类里的方法可以改变字符串的内容 |
1、StringBuffer类
StringBuffer类并没有拥有两个对象实例化方式,StringBuffer必须像普通类那样首先进行对象实例化才能可以调用方法处理。StringBuffer类中修改字符可以使用的方法如下:
定义 | 描述 | ||
构造方法 | 无参构造 | public StringBuffer() | |
有参构造 | public StringBuffer(String str) | 接收初始化字符串内容 | |
数据追加 | public StringBuffer append(各种数据类型 b) | 相当于字符型串中的“+” |
注意:字符的拼接“+”号在编译之后都变成了StringBuffer类中的append()方法,且在程序之中StringBuffer与String类对象之间是可以互相转换的:
1)String类对象变成StringBuffer可以依靠StringBuffer类的构造方法或者使用append()方法;
2)所有的类对象都可以通过toString()方法将其变为String类型。
在StringBuffer类里面除了可以支持有字符串内容的修改之外,还具有一些String类不具备的方法,如下:
方法 | 定义 | 代码 | 正常结果 | 结果 |
插入数据 | public StringBuffer insert(int offset, 数据类型 str) | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { } | hello world! | www.cn.csdn |
删除指定范围的数据 | public StringBuffer delete(int start, int end) | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { } | hello | |
字符串内容反转 | public StringBuffer reverse() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { } | !dlrow olleh |
与StringBuffer类类似的还有个类似的功能类——StringBuilder类,该类中提供的方法与StringBuffer类中的功能相同,而从观察源码得知,它们的最大区别在于,StringBuffer类中的方法与线程安全有关,全都是使用了synchronized的关键字进行标注,而StringBuilder类属于非线程安全的。
面试题:请解释String、StringBuffer、StringBuilder的区别?
1)String类是字符串的首选类型,其最大的特点是内容不可修改;
2)StringBuffer类和StringBuilder类中的内容允许修改;
3)StringBuffer是在JDK1.0的时候提供的,属于线程安全的操作,StringBuilder是在JDK1.5之后提供的,属于非线程安全的操作。
2、CharSequence接口
CharSequence是一个描述字符串结构的接口,在这个接口里面一般有三种常用子类:
CharSequence子类 | 定义结构 |
String类 | public final class String extends Object implements Serializable, Comparable<String>, CharSequence |
StringBuffer类 | public final class StringBuffer extends Object implements Serializable, CharSequence |
StringBuilder类 | public final class StringBuilder extends Object implements Serializable, CharSequence |
从上面可以看出,CharSequence常用的三个子类很熟悉,分别是:String、StringBuffer、StringBuilder,它们的结构定义都实现了CharSequence接口。而StringBuffer、StringBuilder中的方法都可以接收CharSequence类型的参数。
CharSequence接口中的操作方法如下:
方法 | 定义 | 代码 | 结果 |
获取指定索引字符 | char charAt(int index) | ||
获取字符串长度 | int length() | ||
截取部分字符串 | CharSequence subSequence(int start, int end) | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { CharSequence str = "www.csdn.cn"; } } | csdn |
总结:从本质上来讲,CharSequence描述的就是字符串。
3、AutoCloseable接口
AutoCloseable主要是用于日后进行资源开发的处理,实现资源的自动关闭(释放资源)。
AutoCloseable中只有一个方法如下:
关闭方法 | void close() throws Exception |
范例:通过下面两个程序代码的对比,理解AutoCloseable接口的使用。
模拟消息发送过程 | 代码 | 结果 | 分析 | ||
手工实现资源处理 | package cn.demos; interface IMessage { class NetMessage implements IMessage { public NetMessage(String msg) { public boolean open() { public void close() { @Override } public class JavaAPIDemo { public static void main(String[] args) { // 定义发送内容 } } | OPEN获取消息发送连接资源 *****发送消息*****www.csdn.cn CLOSE关闭消息发送通道 | 需要手动写代码关闭,比较繁琐 | ||
AutoCloseable | package cn.demos; interface IMessage extends AutoCloseable { class NetMessage implements IMessage { public NetMessage(String msg) { public boolean open() { public void close() throws Exception { @Override } public class JavaAPIDemo { public static void main(String[] args) throws Exception { try (IMessage nm = new NetMessage("www.csdn.cn")) { } } } | *****发送消息*****www.csdn.cn CLOSE关闭消息发送通道 | 通过继承AutoCloseable接口,实现了消息发送的自动关闭 |
注意:要想实现自动关闭处理,处理要实现AutoCloseable接口之外,还需要结合异常处理语句。
4、Runtime类
Runtime类描述的是运行时的状态,且是一个与JVM运行状态有关的类,系统也会默认提供一个Runtime的实例化对象,Runtime类的构造方法私有化是由于在每一个JVM进程里面,只允许提供有一个Runtime类的对象,所以它的构造方法被私有化,使用的是单例设计模式,且提供一个static方法获取实例化对象。
所以,如果要获取Runtime类的实例化对象,可以使用类中的getRuntime()方法:
方法 | 定义 | 代码 | 结果 |
获取实例化对象 | public static Runtime getRuntime() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 获取实例化对象 } | 12 |
获取本机cpu内核数 | public int availableProcessors() |
除了上面的方法外,Runtime还提供了以下四种重要的操作方法:
定义 | 代码 | 描述 | |
获取最大可用内存空间 | public long maxMemory() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { Runtime run = Runtime.getRuntime(); System.out.println("**1**MAX_MEMORY:" + run.maxMemory()); } } | 默认情况为本机系统内存的四分之一 |
获取可用内存空间 | public long totalMemory() | 默认的配置为本机系统内存的六十四分之一 | |
获取空闲内存空间 | public long freeMemory() | ||
手工进行GC处理 | public void gc() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 获取实例化对象 // 产生垃圾空间 // 休眠0.2s } } | **1**MAX_MEMORY:3779067904 **1**TOTAL_MEMORY:255328256 **1**FREE_MEMORY:252664840 **2**MAX_MEMORY:3779067904 **2**TOTAL_MEMORY:255328256 **2**FREE_MEMORY:247338088 **3**MAX_MEMORY:3779067904 **3**TOTAL_MEMORY:255328256 **3**FREE_MEMORY:253447360 |
注意:totalMemory的值在垃圾回收后,版本1.9之后会发生改变,由于我使用的是1.8版本,所以值在垃圾回收后没有发生变化。
面试题:请问什么是GC?如何处理?
GC(Garbafe Collector)垃圾收集器,是可以由系统自动调用的垃圾释放功能,或者使用Runtime类中的gc()方法手工调用。
5、System类
在程序中的系统输出采用的就是System类中的方法,它的一些其他处理方法如下:
方法 | 定义 | 代码 | 描述 |
数组拷贝 | public static void arraycopy(Object src, int srcPos, Object dest, int destPos, int length) | 参数使用Object类型表示可以接收各种类型的数据 | |
获取当前的日期时间数值 | public static long currentTimeMillis() | 观察耗时时间 | 可以获得程序代码执行的耗时时长 |
package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 获取开始时间 // 产生垃圾空间 // 获取结束时间 // 输出总耗时 } | |||
进行垃圾回收 | public static void gc() | 可以进行垃圾回收 |
注意:虽然System类中也有一个gc()方法,但是调用这个gc()等价于:Runtime.getRuntime().gc()。即,System类中的gc方法并不是重新定义的,而是实现了Runtime里的gc操作。
6、Cleaner类
Cleaner类是一个对象清理操作,其主要的功能是进行finialize()方法的替代,而这个方法的主要作用是在对象进行回收前的一些操作。
范例:观察传统回收
代码 | 结果 |
package cn.demos; class Member { @Override public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 诞生对象 } } | 【构造】小老鼠TT诞生 生活继续 【回收】TT会死的 |
但在JDK1.9之后,这个方法已经不在使用,对于对象的回收释放。从JDK1.9之后一般使用Cleaner类或者AutoCloseable接口进行回收处理。
范例:Cleaner类回收处理对象(注意,JDK版本必须在1.9及之后)
package cn.demos;class Member implements Runnable {public Member() {System.out.println("【构造】小老鼠TT诞生");}@Overridepublic void run() {// 执行清除的是此操作System.out.println("TT总是会是**的");}}class MemberCleaning implements AutoCloseable {// 实现清除处理// 创建一个清除处理private static final Cleaner cleaner = Cleaner.create();private final Member member;private final Cleaner.Cleanable cleanable;public MemberCleaning() {this.member = new Member();// 创建新对象// 这个对象若想被清除需要使用一个注册方法this.cleanable = this.cleaner.register(this, this.member);// 注册使用对象}@Overridepublic void close() throws Exception {this.cleanable.clean();// 使用清除处理相当于启动多线程。}}public class JavaAPIDemo {public static void main(String[] args) throws Exception {try (MemberCleaning mc = new MemberCleaning()) {// 中间可以写一些相关代码} catch (Exception e) {}}}
在最新的清理过程中,更多的情况下考虑的是多线程的使用,即:为了防止有可能造成的延迟处理,所以很多对象回收前的处理都是单独通过一个线程完成的。
7、对象克隆
对象克隆指的就是对象的复制,而且属于全新的复制。即:使用已有对象的内容,创建一个新的对象。对象的克隆需要使用到Object类中提供的clone()方法。
方法 | 定义 |
克隆 | protected Object clone() throws CloneNotSupportedException |
因为所有的类都会继承Object父类,所以所有的类都有clone()方法,但是并不是所有的类都希望被克隆。所以,若要实现对象克隆,那么对象所在的类需要实现一个接口——Cloneable,但是该接口中没有一个方法,是由于它描述的是一种能力。
范例:实现对象克隆
代码 | 结果 |
package cn.demos; class Member implements Cloneable { public Member(String name, int age) { @Override return "【" + super.toString() + "】name = " + this.name + "、age = " + this.age; @Override public class JavaAPIDemo { public static void main(String[] args) throws Exception { Member memberA = new Member("张三", 24); } } | 【cn.demos.Member@15db9742】name = 张三、age = 24 【cn.demos.Member@6d06d69c】name = 张三、age = 24 |
若想在外面实现对象克隆,那么所在的类需要重写clone()方法,这样对象才可以克隆。一般会很少使用对象克隆。
七:Java基础类库
引言:String类是所有项目开发之中一定会使用到的一个功能类,且特点如下:
1)每一个字符串的常量都属于一个String类的匿名对象,并且不可更改;
2)String有两个常量池:静态常量池和运行时常量池;
3)String类对象实例化使用直接赋值的形式完成,这样可以直接将对象保存在对象池之中,方便取用。
而String类的最大弊端是内容不允许修改,所以为了解决String字符串不能修改的缺点,Java程序提供了一个StringBuffer类来实现字符串内容的修改。
范例:String与StringBuffer类的对比
代码 | 结果 | 描述 | |
String类 | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { public static void change(String temp) { } | hello | 内容没改 |
StringBuffer类 | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { public static void change(StringBuffer temp) { } | hello world! | 利用StringBuffer类里的方法可以改变字符串的内容 |
1、StringBuffer类
StringBuffer类并没有拥有两个对象实例化方式,StringBuffer必须像普通类那样首先进行对象实例化才能可以调用方法处理。StringBuffer类中修改字符可以使用的方法如下:
定义 | 描述 | ||
构造方法 | 无参构造 | public StringBuffer() | |
有参构造 | public StringBuffer(String str) | 接收初始化字符串内容 | |
数据追加 | public StringBuffer append(各种数据类型 b) | 相当于字符型串中的“+” |
注意:字符的拼接“+”号在编译之后都变成了StringBuffer类中的append()方法,且在程序之中StringBuffer与String类对象之间是可以互相转换的:
1)String类对象变成StringBuffer可以依靠StringBuffer类的构造方法或者使用append()方法;
2)所有的类对象都可以通过toString()方法将其变为String类型。
在StringBuffer类里面除了可以支持有字符串内容的修改之外,还具有一些String类不具备的方法,如下:
方法 | 定义 | 代码 | 正常结果 | 结果 |
插入数据 | public StringBuffer insert(int offset, 数据类型 str) | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { } | hello world! | www.cn.csdn |
删除指定范围的数据 | public StringBuffer delete(int start, int end) | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { } | hello | |
字符串内容反转 | public StringBuffer reverse() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { } | !dlrow olleh |
与StringBuffer类类似的还有个类似的功能类——StringBuilder类,该类中提供的方法与StringBuffer类中的功能相同,而从观察源码得知,它们的最大区别在于,StringBuffer类中的方法与线程安全有关,全都是使用了synchronized的关键字进行标注,而StringBuilder类属于非线程安全的。
面试题:请解释String、StringBuffer、StringBuilder的区别?
1)String类是字符串的首选类型,其最大的特点是内容不可修改;
2)StringBuffer类和StringBuilder类中的内容允许修改;
3)StringBuffer是在JDK1.0的时候提供的,属于线程安全的操作,StringBuilder是在JDK1.5之后提供的,属于非线程安全的操作。
2、CharSequence接口
CharSequence是一个描述字符串结构的接口,在这个接口里面一般有三种常用子类:
CharSequence子类 | 定义结构 |
String类 | public final class String extends Object implements Serializable, Comparable<String>, CharSequence |
StringBuffer类 | public final class StringBuffer extends Object implements Serializable, CharSequence |
StringBuilder类 | public final class StringBuilder extends Object implements Serializable, CharSequence |
从上面可以看出,CharSequence常用的三个子类很熟悉,分别是:String、StringBuffer、StringBuilder,它们的结构定义都实现了CharSequence接口。而StringBuffer、StringBuilder中的方法都可以接收CharSequence类型的参数。
CharSequence接口中的操作方法如下:
方法 | 定义 | 代码 | 结果 |
获取指定索引字符 | char charAt(int index) | ||
获取字符串长度 | int length() | ||
截取部分字符串 | CharSequence subSequence(int start, int end) | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) { CharSequence str = "www.csdn.cn"; } } | csdn |
总结:从本质上来讲,CharSequence描述的就是字符串。
3、AutoCloseable接口
AutoCloseable主要是用于日后进行资源开发的处理,实现资源的自动关闭(释放资源)。
AutoCloseable中只有一个方法如下:
关闭方法 | void close() throws Exception |
范例:通过下面两个程序代码的对比,理解AutoCloseable接口的使用。
模拟消息发送过程 | 代码 | 结果 | 分析 | ||
手工实现资源处理 | package cn.demos; interface IMessage { class NetMessage implements IMessage { public NetMessage(String msg) { public boolean open() { public void close() { @Override } public class JavaAPIDemo { public static void main(String[] args) { // 定义发送内容 } } | OPEN获取消息发送连接资源 *****发送消息*****www.csdn.cn CLOSE关闭消息发送通道 | 需要手动写代码关闭,比较繁琐 | ||
AutoCloseable | package cn.demos; interface IMessage extends AutoCloseable { class NetMessage implements IMessage { public NetMessage(String msg) { public boolean open() { public void close() throws Exception { @Override } public class JavaAPIDemo { public static void main(String[] args) throws Exception { try (IMessage nm = new NetMessage("www.csdn.cn")) { } } } | *****发送消息*****www.csdn.cn CLOSE关闭消息发送通道 | 通过继承AutoCloseable接口,实现了消息发送的自动关闭 |
注意:要想实现自动关闭处理,处理要实现AutoCloseable接口之外,还需要结合异常处理语句。
4、Runtime类
Runtime类描述的是运行时的状态,且是一个与JVM运行状态有关的类,系统也会默认提供一个Runtime的实例化对象,Runtime类的构造方法私有化是由于在每一个JVM进程里面,只允许提供有一个Runtime类的对象,所以它的构造方法被私有化,使用的是单例设计模式,且提供一个static方法获取实例化对象。
所以,如果要获取Runtime类的实例化对象,可以使用类中的getRuntime()方法:
方法 | 定义 | 代码 | 结果 |
获取实例化对象 | public static Runtime getRuntime() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 获取实例化对象 } | 12 |
获取本机cpu内核数 | public int availableProcessors() |
除了上面的方法外,Runtime还提供了以下四种重要的操作方法:
定义 | 代码 | 描述 | |
获取最大可用内存空间 | public long maxMemory() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { Runtime run = Runtime.getRuntime(); System.out.println("**1**MAX_MEMORY:" + run.maxMemory()); } } | 默认情况为本机系统内存的四分之一 |
获取可用内存空间 | public long totalMemory() | 默认的配置为本机系统内存的六十四分之一 | |
获取空闲内存空间 | public long freeMemory() | ||
手工进行GC处理 | public void gc() | package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 获取实例化对象 // 产生垃圾空间 // 休眠0.2s } } | **1**MAX_MEMORY:3779067904 **1**TOTAL_MEMORY:255328256 **1**FREE_MEMORY:252664840 **2**MAX_MEMORY:3779067904 **2**TOTAL_MEMORY:255328256 **2**FREE_MEMORY:247338088 **3**MAX_MEMORY:3779067904 **3**TOTAL_MEMORY:255328256 **3**FREE_MEMORY:253447360 |
注意:totalMemory的值在垃圾回收后,版本1.9之后会发生改变,由于我使用的是1.8版本,所以值在垃圾回收后没有发生变化。
面试题:请问什么是GC?如何处理?
GC(Garbafe Collector)垃圾收集器,是可以由系统自动调用的垃圾释放功能,或者使用Runtime类中的gc()方法手工调用。
5、System类
在程序中的系统输出采用的就是System类中的方法,它的一些其他处理方法如下:
方法 | 定义 | 代码 | 描述 |
数组拷贝 | public static void arraycopy(Object src, int srcPos, Object dest, int destPos, int length) | 参数使用Object类型表示可以接收各种类型的数据 | |
获取当前的日期时间数值 | public static long currentTimeMillis() | 观察耗时时间 | 可以获得程序代码执行的耗时时长 |
package cn.demos; public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 获取开始时间 // 产生垃圾空间 // 获取结束时间 // 输出总耗时 } | |||
进行垃圾回收 | public static void gc() | 可以进行垃圾回收 |
注意:虽然System类中也有一个gc()方法,但是调用这个gc()等价于:Runtime.getRuntime().gc()。即,System类中的gc方法并不是重新定义的,而是实现了Runtime里的gc操作。
6、Cleaner类
Cleaner类是一个对象清理操作,其主要的功能是进行finialize()方法的替代,而这个方法的主要作用是在对象进行回收前的一些操作。
范例:观察传统回收
代码 | 结果 |
package cn.demos; class Member { @Override public class JavaAPIDemo { public static void main(String[] args) throws Exception { // 诞生对象 } } | 【构造】小老鼠TT诞生 生活继续 【回收】TT会死的 |
但在JDK1.9之后,这个方法已经不在使用,对于对象的回收释放。从JDK1.9之后一般使用Cleaner类或者AutoCloseable接口进行回收处理。
范例:Cleaner类回收处理对象(注意,JDK版本必须在1.9及之后)
package cn.demos;class Member implements Runnable {public Member() {System.out.println("【构造】小老鼠TT诞生");}@Overridepublic void run() {// 执行清除的是此操作System.out.println("TT总是会是**的");}}class MemberCleaning implements AutoCloseable {// 实现清除处理// 创建一个清除处理private static final Cleaner cleaner = Cleaner.create();private final Member member;private final Cleaner.Cleanable cleanable;public MemberCleaning() {this.member = new Member();// 创建新对象// 这个对象若想被清除需要使用一个注册方法this.cleanable = this.cleaner.register(this, this.member);// 注册使用对象}@Overridepublic void close() throws Exception {this.cleanable.clean();// 使用清除处理相当于启动多线程。}}public class JavaAPIDemo {public static void main(String[] args) throws Exception {try (MemberCleaning mc = new MemberCleaning()) {// 中间可以写一些相关代码} catch (Exception e) {}}}
在最新的清理过程中,更多的情况下考虑的是多线程的使用,即:为了防止有可能造成的延迟处理,所以很多对象回收前的处理都是单独通过一个线程完成的。
7、对象克隆
对象克隆指的就是对象的复制,而且属于全新的复制。即:使用已有对象的内容,创建一个新的对象。对象的克隆需要使用到Object类中提供的clone()方法。
方法 | 定义 |
克隆 | protected Object clone() throws CloneNotSupportedException |
因为所有的类都会继承Object父类,所以所有的类都有clone()方法,但是并不是所有的类都希望被克隆。所以,若要实现对象克隆,那么对象所在的类需要实现一个接口——Cloneable,但是该接口中没有一个方法,是由于它描述的是一种能力。
范例:实现对象克隆
代码 | 结果 |
package cn.demos; class Member implements Cloneable { public Member(String name, int age) { @Override return "【" + super.toString() + "】name = " + this.name + "、age = " + this.age; @Override public class JavaAPIDemo { public static void main(String[] args) throws Exception { Member memberA = new Member("张三", 24); } } | 【cn.demos.Member@15db9742】name = 张三、age = 24 【cn.demos.Member@6d06d69c】name = 张三、age = 24 |
若想在外面实现对象克隆,那么所在的类需要重写clone()方法,这样对象才可以克隆。一般会很少使用对象克隆。