首页 > 其他分享 >i++与++i字节码分析

i++与++i字节码分析

时间:2023-11-03 09:23:51浏览次数:29  
标签:分析 操作数 字节 ++ 指令 iconst iload

最近碰到几道关于i++与++i相关的题,我们从字节码角度来分析执行情况,该文章需要读者有字节码相关基础及了解方法调用机制。

分析

下面是一个题,请问下面代码输出什么?

  public static void f() {
    int i = 1;
    System.out.println(i++ + i++);
  }

答案是3。相信有小伙伴会回答2,有此想法的是不了解其运算过程。

我们用javap -c Test.class先反编译下这个类,找到这个方法的字节码,如下所示:

  public static void f();
    Code:
       0: iconst_1
       1: istore_0
       2: getstatic     #3                  // Field java/lang/System.out:Ljava/io/PrintStream;
       5: iload_0
       6: iinc          0, 1
       9: iload_0
      10: iinc          0, 1
      13: iadd
      14: invokevirtual #4                  // Method java/io/PrintStream.println:(I)V
      17: return

忽略2: getstatic14: invokevirtual这两个调用输出的指令,我们来分析下其他相关指令:

image

从图可以看出 在第一个i++之前,已经将数据从局部变量表加载到操作数栈了,如下指令:

5: iload_0
6: iinc          0, 1

6: iinc 执行完之后,局部变量表0位置的数改为2,然后第二个i++操作同样是这样操作的,先将局部变量表第0个位置的数加载到操作数栈,由于第一个i++已经将其改为2,此时再读取时,就是2。

操作数栈此时栈的元素为2,1。然后执行iadd指令,将栈顶两int型数值相加并将结果压入栈顶,此时栈顶元素就是3。进而输出3。

最后执行return,结束。

涉及到的字节码指令:

iconst

当int取值-1~5时,JVM采用iconst指令将常量压入操作数栈中
int 取值 0~5 时,JVM采用 iconst_0、iconst_1、iconst_2、iconst_3、iconst_4、iconst_5指令将常量压入操作数栈中;

取值-1时,采用iconst_m1指令将常量压入操作数栈中。

当int取值 -128~127 时,JVM采用 bipush 指令将常量压入操作数栈中。

iload

将一个局部变量加载到操作数栈
• 非静态方法:从iload_1开始的,默认第iload_0是this
• 静态方法:从iload_0开始的

istore

将一个数值从操作数栈存储到局部变量表
istore_n,n代表局部变量表第几个位置,从0开始。

iadd

将栈顶两int型数值相加并将结果压入栈顶

return

从当前方法返回,void


title: i++与++i字节码分析
author: Mingshan
tags: JVM
categories: [JVM, Bytecode]
date: 2021-06-01

标签:分析,操作数,字节,++,指令,iconst,iload
From: https://www.cnblogs.com/mingshan/p/17793559.html

相关文章

  • 实现一个极简的字节数组对象池
    .NET利用ArrayPoolPool<T>和MemoryPool<T>提供了针对Array/Memory<T>的对象池功能。最近在一个项目中需要使用到针对字节数组的对象池,由于这些池化的字节数组相当庞大,我希望将它们分配到POH上以降低GC的压力。由于ArrayPoolPool<T>没法提供支持,所以我提供了一个极简的实现。目录一......
  • 【专题】2022年新能源智能汽车及自动驾驶竞争分析白皮书-新四化浪潮来袭报告PDF合集分
    原文链接:https://tecdat.cn/?p=34111随着新一轮技术革命和产业变革的推动,以及国家政策的大力扶持,电动化、智能化、网联化已经成为汽车行业发展的新趋势。在这种背景下,各大企业纷纷争夺数字化人才,以推动产品的规模化落地和商业化创新应用。阅读原文,获取专题报告合集全文,解锁文末53......
  • C++ 移动构造函数详解
    目录移动构造函数是什么?复制构造和移动构造对比改进的拷贝构造移动构造实现移动构造优点左值、右值、左值引用、右值引用std::move参考移动构造函数是什么?移动构造是C++11标准中提供的一种新的构造方法。先举个生活例子,你有一本书,你已经不想看了,但我非常想看,那么我有哪......
  • 基于rk3588----i2c驱动框架学习(2)-总线驱动 algorithm 分析
    rk3588i2calgorithm分析来了来了,上次分析完i2c的驱动框架今天我们就看看i2c的algorithm是如何实现的staticconststructi2c_algorithmrk3x_i2c_algorithm={.master_xfer=rk3x_i2c_xfer,.master_xfer_atomic......
  • 技术方案不确定性分析错题集
    相关公式量本利模型:B=S-C销售收入:S=P×Q-TU×Q盈亏平衡产量点:Q=CF/(P-CU-TU)盈亏平衡点:BEP(%)=EBIT(Q)/Qd  ###生产能力利用率表示的盈亏平衡点BEP(%)=[年固定总成本/(年销售收入-年可变成本-年营业税金及附加)]/正常产量×100%###生产能力利用率表示的盈亏平衡点是指盈亏平......
  • 项目管理中实施风险定量分析案例
    假设一个项目经理正在负责一个信息系统项目,包括软件开发和部署。这个项目涉及到多个风险,例如技术风险、组织风险、市场风险等。在项目开始之前,项目经理需要进行风险的定量分析,以确定每个风险的发生概率和对项目目标的影响程度。以下是实施风险定量分析的步骤:确定风险因素:首先需要确......
  • Gamma函数的一些分析
    Gamma函数的一些分析前言最近在看数学的时候,看到了一个\({Γ(s)}\)(GammaFunction),感觉很有意思,所以赶紧写下来,记录一下。\(Γ(x)\)的定义\(Γ(s)\)=\(\int_0^{+\infty}{e^{-x}x^{s-1}}dx\),其中\(s>0\)看到这个定义,刚开始还是蛮头疼的,但是,后来随着对\(Γ(s)\)函数的分析......
  • C++_点云和C++函数处理
    点云问题原始点云拼接-运动畸变是指在一帧时间内,激光雷达或者其载体在发生运动后,产生的点云位置不一样的问题点云是没有畸变的,每条激光线束最终会形成一个闭合的圆形===利用运动模型来做运动畸变补偿和ICP方式这些数据包进行点云组帧激光雷达重叠区域......
  • c++ 程序打印 core dump 信息
    linux环境下c++程序打印coredump信息linux信号机制c++打印堆栈信息#include<signal.h>#include<execinfo.h>#include<dlfcn.h>#include<cxxabi.h>#include<QFile>#include<QTextStream>//捕获信号,对于这些信号都执行coreDumpHandlesignal(SIG......
  • AI智能分析网关高空抛物算法如何实时检测高楼外立面剥落?
    高楼外立面剥落是一种十分危险的行为,会造成严重的人身伤害和财产损失。TSINGSEE青犀智能分析网关利用高楼外立面剥落的信息,结合高空抛物算法来进行处理就可很好解决此问题。1.数据收集首先,需要收集关于高楼外立面剥落的数据。这可以通过安装EasyCVR智能监控平台来实现,可以感......