码农知识堂 - 1000bd
  •   Python
  •   PHP
  •   JS/TS
  •   JAVA
  •   C/C++
  •   C#
  •   GO
  •   Kotlin
  •   Swift
  • 优化代码,提升代码性能


    文章目录

    • 一、 方法
      • 1. 尽量指定类、方法的final修饰符
    • 二、 变量
      • 1. 循环内不要不断创建对象引用
      • 2. 基本类型转换成字符串
      • 3. 如果变量的初值会被覆盖,就没有必要给变量赋初值
      • 4. 尽量使用基本数据类型,避免不必要的装箱、拆箱和空指针判断
    • 三、常量
      • 1. 将常量声明为static final,并以大写命名
      • 2. 禁止使用JSON转化对象
    • 四、对象
      • 1. 尽量重用对象
    • 五、循环
      • 1. 不要在循环中使用try…catch…,应该把其放在最外层
      • 2. for、增强for、iterator的选择
    • 六、集合
      • 1. ArrayList和LinkedList
      • 2. 如果能估计到待添加的内容长度,尽量为指定初始长度
    • 七、字符串
      • 1. 尽量避免使用split
      • 2. 基本类型转换成字符串
      • 3. 在字符串相加的时候,使用 ‘ ‘ 代替 " ",如果该字符串只有一个字符的话
    • 八、方法
      • 1. 把跟类成员变量无关的方法声明成静态方法

    一、 方法

    1. 尽量指定类、方法的final修饰符

    如果指定了一个类为final,则该类所有的方法都是final的。Java编译器会寻找机会内联所有的final方法,内联对于提升Java运行效率作用重大,具体参见Java运行期优化。此举能够使性能平均提高50%。

    二、 变量

    1. 循环内不要不断创建对象引用

    例如:

    for (int i = 1; i <= count; i++){
    	Object  obj = new Object;
    }
    
    • 1
    • 2
    • 3

    这种做法会导致内存中有count份Object对象引用存在,count很大的话,就耗费内存了,建议为改为:

    Object obj = null;
    for (int i = 0; i <= count; i++) {
    	obj = new Object; 
    }
    
    • 1
    • 2
    • 3
    • 4

    这样的话,内存中只有一份Object对象引用,每次new Object的时候,Object对象引用指向不同的Object罢了,但是内存中只有一份,这样就大大节省了内存空间了。

    2. 基本类型转换成字符串

    把一个基本数据类型转为字符串,基本数据类型.toString是最快的方式、String.valueOf次之、数据+””最慢

    3. 如果变量的初值会被覆盖,就没有必要给变量赋初值

    反例:

    List<UserDO> userList = new ArrayList<>();
    if (isAll) {
        userList = userDAO.queryAll();
    } else {
        userList = userDAO.queryActive();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6

    正例:

    List<UserDO> userList;
    if (isAll) {
        userList = userDAO.queryAll();
    } else {
        userList = userDAO.queryActive();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6

    4. 尽量使用基本数据类型,避免不必要的装箱、拆箱和空指针判断

    反例:

    public static double sum(Double value1, Double value2) {
        double double1 = Objects.isNull(value1) ? 0.0D : value1;
        double double2 = Objects.isNull(value2) ? 0.0D : value2;
        return double1 + double2;
    }
    double result = sum(1.0D, 2.0D);
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6

    正例:

    public static double sum(double value1, double value2) {
        return value1 + value2;
    }
    double result = sum(1.0D, 2.0D);
    
    • 1
    • 2
    • 3
    • 4

    三、常量

    1. 将常量声明为static final,并以大写命名

    这样在编译期间就可以把这些内容放入常量池中,避免运行期间计算生成常量的值。另外,将常量的名字以大写命名也可以方便区分出常量与变量

    2. 禁止使用JSON转化对象

    虽然在功能上没有问题,但是在性能上却存在问题。

    四、对象

    1. 尽量重用对象

    特别是String对象的使用,出现字符串连接时应该使用StringBuilder/StringBuffer代替。由于Java虚拟机不仅要花时间生成对象,以后可能还需要花时间对这些对象进行垃圾回收和处理,因此,生成过多的对象将会给程序的性能带来很大的影响。

    五、循环

    1. 不要在循环中使用try…catch…,应该把其放在最外层

    除非不得已。如果毫无理由地这么写了,那是不合理的。

    2. for、增强for、iterator的选择

    参考文章:List遍历:for,foreach Iterator 速度比较
    总结:iterator 性能更优

    // 遍历Set
    Set<String> set = new HashSet<>();
    set.add("a");
    set.add("a");
    set.add("b");
    Iterator<String> iterator = set.iterator();
    while(iterator.hasNext()){
        System.out.println(iterator.next());
    }
    
    // 遍历List
    List<String> list = new ArrayList<>();
    list.add("a");
    list.add("a");
    list.add("b");
    Iterator<String> iterator = list.iterator();
    while(iterator.hasNext()){
        System.out.println(iterator.next());
    }
    
    // 遍历Map
    Map<String, String> nameMap = new HashMap<>();
    nameMap.put("student1", "lihua");
    Set<Map.Entry<String, String>> entries = nameMap.entrySet();
    Iterator<Map.Entry<String, String>> iterator = entries.iterator();
    while(iterator.hasNext()){
    	Map.Entry<String, String> entry = iterator.next();
    	System.out.println(entry.getKey());
    	System.out.println(entry.getValue());
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30

    六、集合

    1. ArrayList和LinkedList

    顺序插入和随机访问比较多的场景使用ArrayList,元素删除和中间插入比较多的场景使用LinkedList

    2. 如果能估计到待添加的内容长度,尽量为指定初始长度

    比如ArrayList、LinkedLlist、StringBuilder、StringBuffer、HashMap、HashSet等等,以StringBuilder为例:

    (1)StringBuilder// 默认分配16个字符的空间

    (2)StringBuilder(int size) // 默认分配size个字符的空间

    (3)StringBuilder(String str) // 默认分配16个字符+str.length个字符空间

    (4)List 默认长度是10

    (5) Map 默认长度是16

    只要达到它的最大容量,它就不得不创建一个新的字符数组然后将旧的字符数组内容拷贝到新字符数组中—-这是十分耗费性能的一个操作

    七、字符串

    1. 尽量避免使用split

    除非是必须的,否则应该避免使用split,split由于支持正则表达式,所以效率比较低,如果是频繁的几十,几百万的调用将会耗费大量资源,如果确实需要频繁的调用split,可以考虑使用apache的StringUtils.split(string,char),频繁split的可以缓存结果。

    2. 基本类型转换成字符串

    把一个基本数据类型转为字符串,基本数据类型.toString是最快的方式、String.valueOf次之、数据+””最慢

    3. 在字符串相加的时候,使用 ‘ ‘ 代替 " ",如果该字符串只有一个字符的话

    例子:

    public class STR {
    	public void method(String s) {
    		String string = s + "d" // violation.
    		string = "abc" + "d" // violation.
    	}
    }
    
    // 更正: 将一个字符的字符串替换成' '
    public class STR {
    	public void method(String s) {
    		String string = s + "d // violation.
    		string = "abc" + 'd' // violation.
    	}
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    八、方法

    1. 把跟类成员变量无关的方法声明成静态方法

    静态方法的好处就是不用生成类的实例就可以直接调用。静态方法不再属于某个对象,而是属于它所在的类。只需要通过其类名就可以访问,不需要再消耗资源去反复创建对象。即便在类内部的私有方法,如果没有使用到类成员变量,也应该声明为静态方法。

    反例:

    public int getMonth(Date date) {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        return calendar.get(Calendar.MONTH) + 1;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5

    正例:

    public static int getMonth(Date date) {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        return calendar.get(Calendar.MONTH) + 1;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
  • 相关阅读:
    8. Go的函数
    基于 SPICE 协议的硬编推流整合方案在云游戏中的应用
    解读2022年度敏捷教练行业现状报告
    导航【mysql高级】【java提高】
    【文本检测与识别白皮书-3.2】第二节:基于注意力机制和CTC的场景文本识别方法的对比
    微服务之 consul
    竞赛选题 深度学习手势识别 - yolo python opencv cnn 机器视觉
    我的前端成长之路:中医药大学毕业的业务女前端修炼之路
    ThePASS 研究院|探索 Aragon:开创性的 DAO 基础设施实现全面治理
    FL Studio21版本水果全新功能介绍AI编曲时代或将来临
  • 原文地址:https://blog.csdn.net/m0_46638350/article/details/132445880
  • 最新文章
  • 攻防演习之三天拿下官网站群
    数据安全治理学习——前期安全规划和安全管理体系建设
    企业安全 | 企业内一次钓鱼演练准备过程
    内网渗透测试 | Kerberos协议及其部分攻击手法
    0day的产生 | 不懂代码的"代码审计"
    安装scrcpy-client模块av模块异常,环境问题解决方案
    leetcode hot100【LeetCode 279. 完全平方数】java实现
    OpenWrt下安装Mosquitto
    AnatoMask论文汇总
    【AI日记】24.11.01 LangChain、openai api和github copilot
  • 热门文章
  • 十款代码表白小特效 一个比一个浪漫 赶紧收藏起来吧!!!
    奉劝各位学弟学妹们,该打造你的技术影响力了!
    五年了,我在 CSDN 的两个一百万。
    Java俄罗斯方块,老程序员花了一个周末,连接中学年代!
    面试官都震惊,你这网络基础可以啊!
    你真的会用百度吗?我不信 — 那些不为人知的搜索引擎语法
    心情不好的时候,用 Python 画棵樱花树送给自己吧
    通宵一晚做出来的一款类似CS的第一人称射击游戏Demo!原来做游戏也不是很难,连憨憨学妹都学会了!
    13 万字 C 语言从入门到精通保姆级教程2021 年版
    10行代码集2000张美女图,Python爬虫120例,再上征途
Copyright © 2022 侵权请联系2656653265@qq.com    京ICP备2022015340号-1
正则表达式工具 cron表达式工具 密码生成工具

京公网安备 11010502049817号