关于静态方法与非静态方法的执行效率
2016-03-08 10:42
190 查看
以前看到许多网友认为静态方法要比实例方法在执行效率上要快一些,当初不敢苟同。自己亲自试了一把,发现静态方法确实要快一些。
想要比较静态方法与非静态方法的执行效率,需要对CLR在调用静态方法与非静态方法时的不同之处要有一个了解。
静态方法是与类相关联的,CLR在调用一个静态方法时需要做的事情就是找到定义该方法的类型即可实现调用;而在调用非静态方法时,为了保证运行安全,CLR会对我们的源代码进行验证并额外的生成一些IL中间代码来确保运行安全,所以在调用一个非静态方法时,CLR首先是判定被调用对象是否为NULL,如果为NULL,则引发一个异常,反之,则根据对象推荐出其类型,最后实现调用。可以看出来,在调用静态方法来非静态方法时,后者比前者多做了一些工作,这将造成性能上的损失。所以,静态方法在执行效率上可能要比非静态方法要好一些。IL中可以看到非静态方法执行的是callvirt 指令:
![](http://images.cnitblog.com/blog/282056/201308/15102315-716a939a61874728bc4197c8678079f3.png)
CLR via C#的解释:调用一个静态方法时,CLR会定位与定义静态方法的类型对应的类型对象。然后,JIT编译器在类型对象的方法表中查找与被调用的方法对应的记录项,对方法进行JIT编译(如果需要的话),再调用JIT编译的代码。过程图如下:
![](http://images.cnitblog.com/blog/282056/201308/15102442-6917a2ae76554ea697bc7c2bd2f6ee80.png)
一般情况下声明静态方法的类大多是工具类,并且这些静态方法不需要访问类型中的非静态字段和事件,也就是说静态方法与该类型中的非静态字段和事件不具有逻辑上的关联性。如果一个方法声明为静态方法,也意味着不能被重写,该方法失去面向对象的扩展和多态的特性。
总结:静态方法与实例方法在性能和占用内存上没有明显的区别,是否声明为静态方法需要从类型的非静态字段、事件、面向对象扩展和多态这三方面来考虑。
想要比较静态方法与非静态方法的执行效率,需要对CLR在调用静态方法与非静态方法时的不同之处要有一个了解。
静态方法是与类相关联的,CLR在调用一个静态方法时需要做的事情就是找到定义该方法的类型即可实现调用;而在调用非静态方法时,为了保证运行安全,CLR会对我们的源代码进行验证并额外的生成一些IL中间代码来确保运行安全,所以在调用一个非静态方法时,CLR首先是判定被调用对象是否为NULL,如果为NULL,则引发一个异常,反之,则根据对象推荐出其类型,最后实现调用。可以看出来,在调用静态方法来非静态方法时,后者比前者多做了一些工作,这将造成性能上的损失。所以,静态方法在执行效率上可能要比非静态方法要好一些。IL中可以看到非静态方法执行的是callvirt 指令:
![](http://images.cnitblog.com/blog/282056/201308/15102315-716a939a61874728bc4197c8678079f3.png)
CLR via C#的解释:调用一个静态方法时,CLR会定位与定义静态方法的类型对应的类型对象。然后,JIT编译器在类型对象的方法表中查找与被调用的方法对应的记录项,对方法进行JIT编译(如果需要的话),再调用JIT编译的代码。过程图如下:
![](http://images.cnitblog.com/blog/282056/201308/15102442-6917a2ae76554ea697bc7c2bd2f6ee80.png)
一般情况下声明静态方法的类大多是工具类,并且这些静态方法不需要访问类型中的非静态字段和事件,也就是说静态方法与该类型中的非静态字段和事件不具有逻辑上的关联性。如果一个方法声明为静态方法,也意味着不能被重写,该方法失去面向对象的扩展和多态的特性。
总结:静态方法与实例方法在性能和占用内存上没有明显的区别,是否声明为静态方法需要从类型的非静态字段、事件、面向对象扩展和多态这三方面来考虑。
相关文章推荐
- 前端开发框架对比
- Eclipse和Eclipse SDK区别 ;SDK和JDK区别
- 《从零开始学Swift》学习笔记(Day 64)——Cocoa Touch设计模式及应用之目标与动作
- android倒计时控件示例
- 在linux下安装jdk环境
- 个人平时总结(不定时更新)
- 对其中某元素进行排序
- 数组转list三种方法
- HttpClient 大量连接等待异常的处理
- 将URL中的中文转为UTF-8编码
- 普通java类获取 spring中的bean方法
- 一个让我比较郁闷的需求、、
- android:layout_weight权重分析
- mysql 错误代码 1045 解决
- KVC/KVO简单用法
- L版本自动背光调节,从亮到暗比较慢的问题
- 安卓Service组件使用系列2:使用Service下载网络图片并存储于sdCard卡上
- inputtype
- 三星I9023用数据线连接到电脑上怎么没反应,只有充电的显示
- Android 壁纸设置代码 详解