通过向下转换,性能/内存的好处是否无效?

ast*_*eri 6 java performance primitive downcast

我正在编写一个大型应用程序,我试图尽可能多地保存内存并提高性能.因此,当我有一个我知道的字段只有0 - 10或-100 - 100的值时,我尝试使用short数据类型而不是int.

但是,对于其余的代码来说,这意味着,当我调用这些函数时,我必须将简单的ints 转发为shorts.例如:

方法签名

public void coordinates(short x, short y) ...
Run Code Online (Sandbox Code Playgroud)

方法调用

obj.coordinates((short) 1, (short) 2);
Run Code Online (Sandbox Code Playgroud)

这就像我的整个代码中的所有代码一样,因为文字被视为ints并且不会根据函数参数自动向下转换或键入.

因此,一旦这种向下转发发生,任何性能或内存增益是否真的显着?或者转换过程如此高效,以至于我仍能获得一些收益?

Sec*_*att 10

在32位平台上使用short与int没有性能优势,除了short []与int []之外的所有情况 - 即使这样,缺点通常也超过了专业人士.

假设您在x64,x86或ARM-32上运行:

  • 在使用时,16位SHORT存储在整数寄存器中,这些寄存器的长度为32位或64位,与整数相同.即,当使用短线时,与int相比,你没有获得内存或性能优势.
  • 当在堆栈上时,16位SHORT存储在32位或64位"槽"中,以保持堆栈对齐(就像整数一样).对于局部变量,使用SHORT和INT不会获得性能或内存优势.
  • 当作为参数传递时,SHORT在被推入堆栈时会自动扩展为32位或64位(与刚刚推入的整数不同).这里的代码实际上性能稍差,并且比使用int时的内存占用量略大(代码).
  • 存储全局(静态)变量时,这些变量会自动扩展为占用32位或64位插槽,以保证指针(引用)的对齐.这意味着对于全局(静态)变量使用SHORTs与INTs没有任何性能或内存优势.
  • 存储字段时,它们存在于堆内存中的结构中,该结构映射到类的布局.在此类中,字段会自动填充为32位或64位,以维护堆上字段的对齐方式.通过对字段和INT使用SHORT,您不会获得性能或内存优势.

使用SHORT和INT 的唯一好处是在分配它们的数组的情况下.在这种情况下,N个短路的数组大约是N个 int 的数组的一半.

除了在大量短路中复杂但本地化数学的情况下将变量放在热循环中所带来的性能优势之外,您将永远不会看到使用SHORTS与INT相比的好处.

所有其他情况下 - 例如短路用于字段,全局,参数和本地,除了它可以存储的位数之外,SHORT和INT之间没有区别.

我的建议一如既往地建议在使代码更难以阅读和更人为限制之前,尝试使用BENCHMARKING代码来查看内存和CPU瓶颈的位置,然后解决这些问题.

我强烈怀疑,如果你曾经遇到过你的应用程序使用整数而不是短路的情况,那么你就可以在很长一段时间内抛弃Java以获得更少的内存/ CPU饥饿运行时间,所以提前完成所有这些工作是浪费精力.


NPE*_*NPE 7

据我所知,演员本身应该没有运行时成本(是否使用short而不是int实际提高性能是有争议的,并取决于您的应用程序的细节).

考虑以下:

public class Main {
    public static void f(short x, short y) {
    }

    public static void main(String args[]) {
        final short x = 1;
        final short y = 2;
        f(x, y);
        f((short)1, (short)2);
    }
}
Run Code Online (Sandbox Code Playgroud)

最后两行main()编译为:

  // f(x, y)
   4: iconst_1      
   5: iconst_2      
   6: invokestatic  #21                 // Method f:(SS)V

  // f((short)1, (short)2);
   9: iconst_1      
  10: iconst_2      
  11: invokestatic  #21                 // Method f:(SS)V
Run Code Online (Sandbox Code Playgroud)

如您所见,它们完全相同.演员阵容发生在编译时.

  • 为了反汇编字节码,我在编译的类上使用了`javap -c`. (3认同)