37-Java基础类库

Java基础类库

StringBuffer类

  String类是在所有项目开发中一定会使用到的一个功能类,并且这个类有如下特点:

  • 每一个字符串的常量都属于一个String类的匿名对象,并且不可更改;
  • String有两个常量池:静态常量池、运行时常量池;
  • String类对象实例化建议使用直接赋值的形式完成,这样可以直接将对象保存在对象池中以便下次重用;

  虽然String类很好使用,但是认真思考也会发现其最大的弊端:内容不允许修改,所以为了解决此问题专门提供StringBuffer类,可以实现字符串内容修改处理。
  StringBuffer类并不像String类那样拥有两种对象的实例化方式,StringBuffer类必须向普通类对象那个首先进行实例化,而后才可以调用方法进行处理。

  • 构造方法:public StringBuffer(String str)/();
  • 数据追加:public StringBuffer append(数据类型 变量);

对比

package per.lyz.StringBuffer_study;

public class JavaClassDemo {
	public static void main(String[] args) {
		String str = "hello";
		StringBuffer str_1 = new StringBuffer("hello");
		change(str);
		str_1.append("world");
		System.out.println(str);
		System.out.println(str_1.toString());
	}
	public static void change(String temp) {
		temp += "world";
	}
}

实际中很少出现字符串内容的改变,这种改变值得并不是针对于静态常量池的改变。
范例

String strA = "www.mldn.cn";
String strB = "www." + "mldn" + ".cn";
strA == strB (True)

此时strB的内容并不算一种改变,或者更严格来讲,对于strB当程序编译之后会变为如下形式:
str.append("www.").append("mldn").append(".cn");
所有的“+”在编译之后都变为了StringBuffer中的append()方法,在程序中StringBuffer与String类之间可以直接互相转换

  • String类对象变为StringBugffer可以依靠StringBuffer类的构造方法或使用append()方法;
  • 所有的类对象通过toString()方法变为String类型;

  在StringBuffer类除了可以支持有字符串内容的修改之外,实际上也提供有一些String类不具备的方法:

  • 插入数据:public StringBuffer insert(int offset, 数据类型 b);buf.append(".cn").insert(0,"www").insert(4,"mldn");
  • 删除指定范围数据:public StringBuffer delete(int start,int end);
  • 字符串内容反转:public StringBuffer reverse();

实际上与StringBuffer类类似的功能类:StringBuilder类(JDK1.5),该类提供的方法与StringBuffer提供的功能相同,但是最大的区别在于StringBuffer类中的方法属于线程安全的,全部使用了synchronized关键字进行标注,而StringBuilder类属于非线程安全的。

面试: 解释String、StringBuffer、StringBulider的区别?

  • String类是字符串的首选类型,最大的特点是内容不可更改;
  • StringBuilder与StringBuffer类的内容允许修改;
  • StringBuffer(JDK1.0)是线程安全的,而StringBuilder(JDK1.5)类属于非线程安全的。

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

rGNKzV.png
现在只要有字符串就可以为CharSequence接口实例化;
CharSequence str = "test!"; //子类实例像父接口转型

  CharSequence本身是一个接口,在该接口中也定义有如下操作方法,

  • 获取指定索引字符:public char charAt(int index);
  • 获取字符串长度:public int length();
  • 截取部分字符串:public CharSequence subSequence(int start, int end);
public class JavaClassDemo {
	public static void main(String[] args) {
		CharSequence str = "www.mldn.cn";
		CharSequence sub = str.subSequence(4, 8);
		System.out.println(sub);
	}
}

看见CharSequence描述的就是一个字符串。

AutoCloseable接口

  AutoCloseable主要适用于日后进行资源开发的处理上,以实现资源的自动关闭(释放),如:在以后文件、网络、数据库开发中由于服务器资源有限,所以使用之后一定要关闭资源,才可被更多用户使用;
范例: 为了更好的说明资源的问题,通过一个消息的发送处理来完成

interface IMessage{
	public void send();		//消息发送
}
class NetMessage implements IMessage{
	private String msg;
	public NetMessage(String msg) {
		this.msg = msg;
	}
	public boolean open() {		//获取资源链接
		System.out.println("获取消息发送连接资源");
		return true;
	}
	public void close() {
		System.out.println("关闭连接,释放资源");
	}
	@Override
	public void send() {
		if(this.open()) {
			System.out.println("发送消息" + this.msg);
		}
		
	}
	
}
public class JavaClassDemo {
	public static void main(String[] args) {
		NetMessage ns = new NetMessage("test");
		ns.send();
		ns.close();
	}
}

既然所有的资源完成处理之后都需进行关闭,则可以实现一种自动关闭的功能,于是推出了AutoCloseable访问接口,这个接口是在JDK1.7的时候提供的,且只有一个方法:

  • 关闭方法:public void close() throws Exception;

rJCVF1.png
  要想实现自动关闭处理,除了要使用AutoCloseable之外,还需结合异常处理语句完成。
实现自动关闭处理

interface IMessage extends AutoCloseable{
	public void send();		//消息发送
}
class NetMessage implements IMessage{
	private String msg;
	public NetMessage(String msg) {
		this.msg = msg;
	}
	public boolean open() {		//获取资源链接
		System.out.println("获取消息发送连接资源");
		return true;
	}
	public void close() throws Exception {
		System.out.println("关闭连接,释放资源");
	}
	@Override
	public void send() {
		if(this.open()) {
			System.out.println("发送消息" + this.msg);
		}
	}
}

public class JavaClassDemo {
	public static void main(String[] args) throws Exception{
		try (IMessage nm = new NetMessage("test")){
			nm.send();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}

后续章节中会接触到资源的关闭问题,往往都会见到AutoCloseable接口的使用。

Runtime类

  Runtime描述的是运行时的状态,在整个JVM中Runtime类是唯一一个与JVM运行状态有关的类,并且默认提供一个该类的实例化对象。
  由于在每一个JVM进程中只允许提供有一个Runtime类对象,所以这个类的构造方法被私有化,使用的是单例设计模式,并且单例设计模式一定会提供有一个static方法获取本类实例。
rJF57Q.png
由于Runtime类属于单例设计模式,要想获得实例化对象可以依靠类中方法获得:

  • 获取实例化对象:public static Runtime getRuntime();
  • 可用进程数:public int availableProcessors();

获取Runtime类对象

public class Runtime_study {
	public static void main(String[] args) {
		Runtime run = Runtime.getRuntime();
		System.out.println(run.availableProcessors());		//获取CPU内核数,
	}
}

还提供以下重要操作方法:

  • 获取最大可用内存空间:public long maxMemory();(默认配置为本机系统内存的1/4)
  • 获取可用内存空间:public long totalMemory();(默认配置为本机系统内存的1/64)
  • 获取空闲内存空间:public long freeMemory();
  • 手工进行GC处理:public void gc();

面试: 什么是GC?如何处理

  • GC(Garbage Collector)垃圾收集器,是可以由系统自动调用的垃圾释放功能,或使用Runtime类中gc()手工调用。

System类

定义的方法:

  • 数组拷贝:public static void arraycopy(Object src, int srcPos, Object dest, int destPos, int length);
  • 获取当前日期时间数值:public static long currentTimeMillis();
  • 进行垃圾回收:public static void gc();

gc方法是使用了Runtime中的gc处理。

Cleaner类

  Cleaner是在JDK1.9之后提供的一个对象的清理操作,其主要的功能是进行finialize()方法的替代。在C++中有两种特殊函数:构造函数,析构函数(对象手工回收),在Java中所有的垃圾空间都是通过GC自动回收的,所以大部分情况下无需使用析构函数,也正是因为如此,所有Java并未提供这方面的支持。
  但Java依然提供了给用户收尾的操作,每一个实例化对象再回收之前至少给他一个喘息的机会,最初实现对象收尾的方法是Object类中所提供的finalize()方法:@Deprecated(since='9') protected void finalizer() throws Exception;
该方法最大的特征是抛出了Throwable异常类型,这个异常类型分为两个子类型:Error、Exception,平常所处理的都是Exception。
观察传统回收

class Member{
	public Member() {
		System.out.println("构造方法");
	}
	@Override
	protected void finalize() throws Throwable {
		System.out.println("析构方法");
		throw new Exception("暂时不销毁");
	}
}
public class CleanerStudy {
	public static void main(String[] args) {
		Member mem = new Member();
		mem = null;		//成为垃圾
		System.gc();
	}
}

从JDK1.9开始这一操作不建议使用了,而对于对象的回收释放,从JDK1.9开始建议开发者使用AutoCloseable或java.lang.ref.Cleaner类(Cleaner也支持AutoCloseable处理)进行回收处理。

import java.lang.ref.Cleaner;

class Member implements Runnable{
	public Member() {
		System.out.println("构造方法");
	}
	@Override
	public void run() {		//清除对象
		System.out.println("析构对象");
	}
}
class MemberCleanning implements AutoCloseable{		//实现清除处理
	private static final Cleaner cleaner = Cleaner.create();		//创建一个清除处理
	private Member member;
	private Cleaner.Cleanable cleanable;
	public MemberCleanning() {
		this.member = new Member();		//创建新对象
		this.cleanable = this.cleaner.register(this, this.member);		//注册使用对象
	}
	@Override
	public void close() throws Exception {
		// TODO Auto-generated method stub
		this.cleanable.clean();		//启动多线程
	}		//实现清除处理
	
}

public class CleanerStudy {
	public static void main(String[] args) throws Exception {
		try(MemberCleanning mc = new MemberCleanning()){
			;
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}

在新一代的清除回收处理过程中,更多的情况下考虑的是多线程的使用,即:为了防止有可能造成的延迟处理,许多对象回收前的处理都是单独通过一个线程完成的。

对象克隆

  所谓的对象克隆指的是对象对象,而且属于全新的复制,使用使用已有对象内容创建一个新的对象,使用Object类中clone()方法;
protected Object clone() throws CloneNotSupportedException;
  所有的类都会默认继承Object父类,所以所有的类都一定会有clone()方法,但并不是所有的类都希望被克隆,所以要先实现对对象克隆,那么对象所在的类要实现一个Cloneable接口,此接口并无任何方法提供,是因为他描述的是一种能力
实现对象克隆

class Members_1 implements Cloneable{
	private String name;
	private int age;
	public Members_1(String name, int age) {
		super();
		this.name = name;
		this.age = age;
	}
	@Override
	public String toString() {
		return super.toString()+"Member [name=" + name + ", age=" + age + "]";
	}
	@Override
	protected Object clone() throws CloneNotSupportedException {
		// TODO Auto-generated method stub
		return super.clone();		//调用父类中提供的clone()方法
	}
}
public class CloneStudy {
	public static void main(String[] args) throws CloneNotSupportedException {
		Members_1 memberA = new Members_1("lyz", 18);
		Members_1 memberB = (Members_1)memberA.clone();
		System.out.println(memberA);
		System.out.println(memberB);
	}
}

开发中不是非常特别的需求下,很少出现对象克隆的需求。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值