java 优化

本文分享了Java编码优化的全面指南,包括对象与基本类型的优化、集合类的最佳实践、字符串处理技巧以及引用类型的理解。深入探讨了clone()创建对象、boolean判断优化、静态方法使用、局部变量优势、运算符选择等话题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

目录

 

编码优化

(一)、对象与基本类型

1. clone() 方式创建对象的选择

2.避免对boolean判断

3.静态方法的选择

4.多使用局部变量

5.运算符的选择

6.数据维数的选择

7.表达式优化

8.避免重复初始化变量

9.数值字面量的改进

10.赋空变量

(二)、集合类

1.subList 方法

2.asList 方法

(三)、字符串

1.使用 ' ' 代替 " "

2.charAt代替startsWith

3.使用StringTokenizer  类进行短字符串分割

4.字符串拼接

(四)、引用类型

1.强引用

2.软引用

3.弱引用

4.虚引用


编码优化

 

(一)、对象与基本类型

 

1. clone() 方式创建对象的选择

    private static Person per = new Person();
    public static Person getPerson() throws CloneNotSupportedException{
        return (Person) per.clone();
    }

 注意:该方式是浅拷贝,类需要实现 Cloneable 接口,拷贝的新对象会包含一些原来对象的信息,当构造器中有复杂逻辑执行时,clone()方式创建对象才比new快(clone() 是对内存中数据块的拷贝,没有调用构造器)。

2.避免对boolean判断

当表达式结果为Boolean类型时,避免将表达式结果再与‘true’或‘false’进行比较。

        if( str.endsWith("a"));  //推荐
        if(str.endsWith("a") == true );  //不推荐

3.静态方法的选择

如果不需要去访问对象的外部,那么就把方法声明为static的,如工具类中的方法。 静态方法通过“类名.方法名”的方式调用,无须创建对象,不需要虚拟导向表,可以更快的调用。

4.多使用局部变量

局部变量的访问速度远高于成员变量

5.运算符的选择

使用 || 代替 | ,使用 && 代替 & ,使用 >> 、<< 、>>> 代替部分算术运算

6.数据维数的选择

二维数组的访问速度优于一维数组,但二维数组比一维数组要占用更多的内存。

7.表达式优化

    int a1,a2,a3;
    
    //方式1
    int b1 = a1*a2*a3*13;
    int b2 = a1*a2*a3*17;
    int b3 = a1*a2*a3*19;
    
    //优化方式
    int c0 = a1*a2*a3;
    int b1 = c0*13;
    int b2 = c0*17;
    int b3 = c0*19;

8.避免重复初始化变量

java会把变量初始化为一个确定的值,对象为null,整数类型为0,浮点类型为0.0,布尔类型为false,

9.数值字面量的改进

        int a = 0b10;  //二进制,数字前加"0b"或"0B"
        System.out.println(a);  //2
        
        int b = 017; //八进制,数字前加"0"
        System.out.println(b); //15
        
        int c = 0x15; //十六进制,数字前加"0x"或"0X"
        System.out.println(c); //21
        
        int d = 50_000_000; //加"_"增加可读性,相当于50,000,000
        System.out.println(d);  //50000000

10.赋空变量

赋空变量是指将null值显示的赋给变量。这样使该变量的引用失去作用域,不再有对该变量的引用,它就可以被当做垃圾收集了。(对于局部变量,当方法执行完毕,局部变量就失去了作用域,栈就会删除对该变量的引用)

(二)、集合类

 

List原理同步性重复值null 元素初始大小数据增长读写速度
LinkedList基于链表不同步允许允许0每次都新建Entry对象
ArrayList基于数组不同步允许允许创建时为0,添加第一个元素时为10不足时增加50%
Vector基于数组同步允许允许创建时为0,添加第一个元素时为10不足时增加一倍——

对于ArrayList,若能提前估算容量,设定初始大小,避免在添加数据过程中进行扩容操作,可提高性能

Set原理同步性重复值null 元素初始大小数据增长读写速度内存占用有序性
HashSetHashMap不同步不允许允许16达到0.75时增加一倍无序
TreeSetTreeMap (基于红黑树)不同步不允许不允许16达到0.75时增加一倍有序性
Map原理同步性null 元素初始大小数据增长
HashMap哈希表不同步允许16达到0.75时增加一倍
Hashtable哈希表同步不允许11达到0.75时增加一倍

集合在遍历过程中需要进行元素的增减操作,使用迭代器,否则会出现ConcurrentModificationException。

1.subList 方法

subList() 方法可以获取原来集合的一部分数据,但这两个集合间存在关联,对子集合的修改会相应的反映到原集合上;对原集合的修改,若是对元素值的改变,子集合也会相应改变,如是对集合元素的增减,子集合会抛出ConcurrentModificationException。

2.asList 方法

判断某个元素是否在数组中时,可以使用 Arrays.asList(T[] array).contains(T obj),避免迭代循环。

(三)、字符串

1.使用 ' ' 代替 " "

例: String a  = "abc" + "d";   优化为 :  String a  = "abc" + 'd'; 

2.charAt代替startsWith

例如: if(str.startsWith("a"));  优化为: if('a' == str.charAt(0));

3.使用StringTokenizer  类进行短字符串分割

对于长度在几十个字符以内的字符串,使用StringTokenizer 时效率较高

        String str = "abc*bdd*sd";
        StringTokenizer t = new StringTokenizer(str, "*");
        while(t.hasMoreTokens()){
            System.out.println(t.nextToken());
        }

4.字符串拼接

对长字符串进行拼接时,使用 StringBuffer 或 StringBuilder 效率更高。

这两个类都是AbstractStringBuilder的子类,StringBuffer的方法几乎都是synchronized的,而StringBuilder的方法都是不同步的。

(四)、引用类型

java中提供了四个级别的引用,即强引用(FinalReference)、软引用(SoftReference)、弱引用(WeakReference)、虚引用(PhantomReference)。

1.强引用

系统中最常见的一种引用,无需引用就可以直接使用的对象。JVM宁可抛出OOM,也不会清理强引用对象。

String str = "Hello World";

2.软引用

JVM在抛出OOM之前,会清理所有的软引用对象。

        List<Object> list = new ArrayList<>();//对象
        SoftReference<List<Object>> soft = new SoftReference<>(list); //标记为软引用
        list = soft.get();//从软引用中获取对象

补充:将软引用用于对象缓存,将导致更高的堆占用,相应导致了更频繁的GC。另外,不同JVM对于软引用的策略不同,同一JVM中不同的垃圾收集器对于软引用的策略也不同,这将导致使用软引用的java程序在可移植性上造成限制)【《java性能调优指南》P63 】

3.弱引用

JVM在执行GC时,会清理所有的弱引用。

    WeakReference<Object> weak = new WeakReference<>(obj);

4.虚引用

又叫“幽灵引用”,随时都会被GC清理掉,并且虚引用的get方法总返回null,因此无法通过虚引用获取被引用的对象。主要目的是在一个对象被实际回收之前得到通知,从而进行一些相关的清理工作,可以作为finalize方法的辅助使用。

        Object obj = new Object();
        ReferenceQueue<Object> que = new ReferenceQueue<>();
        PhantomReference<Object> phantom = new PhantomReference<Object>(obj, que);

JVM对该对象进行GC时,会调用该对象的finalize方法,finalize方法运行之后,虚引用才会被添加到队列中。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值