最近碰到个场景,还蛮有普遍性的,如简单工厂方法,需要依据入参选择不同的业务逻辑进行对应的处理
马上想到两个方案
方案一:采用map存放对应入口的处理方法,然后请求进来后经过get就行,map.get(et);
方案二:采用switch语句,
switch (et) {
case API3:
return api3service;
case API4:
return api4service;
case API2:
return api2service;
……
if else这种就不予考虑了
明显采用map显的更优雅,代码更具可维护性,如果用switch每次需要硬编码
那性能呢?
但用map,也可以做些优化处理,比如我发现一些入参在map默认大小为16下,其桶位置发生了碰撞,这样每次get
的时候就需要遍历了,这是不好,当然有两种方案,一是改key值避免碰撞,二是改map大小,让其不发生碰撞,
我采用map大小为64,避免碰撞,当然后面如要继续添加时候,需要关注
经测试,性能可以提升44%,(本机场景,并且这个key在桶的最尾部,也就是需要全部遍历桶全部数据的场景,并且全部预先执行1w次,摒弃了jit对结果的影响)
但map的get操作,每次需要进行hash,位移操作,&操作,再比较操作,想想就需要很多的指令要执行完才能拿到
如果是switch呢?
Switch在编译后,有LookupSwitch 和 TableSwitch,其中TableSwitch是O(1)的,LookupSwitch是 O(log n)
TableSwitch情况
int chooseNear(int i) {
switch (i) {
case 0: return 0;
case 1: return 1;
case 2: return 2;
default: return -1;
}
}
编译后结果
Method int chooseNear(int)
0 iload_1 // Push local variable 1 (argument i)
1 tableswitch 0 to 2: // Valid indices are 0 through 2
0: 28 // If i is 0, continue at 28
1: 30 // If i is 1, continue at 30
2: 32 // If i is 2, continue at 32
default:34 // Otherwise, continue at 34
28 iconst_0 // i was 0; push int constant 0...
29 ireturn // ...and return it
30 iconst_1 // i was 1; push int constant 1...
31 ireturn // ...and return it
32 iconst_2 // i was 2; push int constant 2...
33 ireturn // ...and return it
34 iconst_m1 // otherwise push int constant -1...
35 ireturn // ...and return it
也就是TableSwitch只要计算一次偏移量,立即就能到case执行,其时间复杂度为O(1)
LookupSwitch
int chooseFar(int i) {
switch (i) {
case -100: return -1;
case 0: return 0;
case 100: return 1;
default: return -1;
}
}
编译后:
Method int chooseFar(int)
0 iload_1
1 lookupswitch 3:
-100: 36
0: 38
100: 40
default: 42
36 iconst_m1
37 ireturn
38 iconst_0
39 ireturn
40 iconst_1
41 ireturn
42 iconst_m1
43 ireturn
也就是LookupSwitch编译后会保证其顺序,并采用二分法查找对应的case,其时间复杂度为O(log n)
本机,全部预先执行1w次跳过jit的影响,采用map与switch各执行1亿次,执行时间是两位数的差距,map为400多ms,switch为5ms
当然测试的场景case都比较少,如果达到1k多个case条件呢? Jit还会把jvm指令缓存吗?,如果不缓存又是另外的情况了
大家可以把eclipse设置Xint,看看屏蔽jit后大量运行的效果
还有switch在什么场景下编译后会是TableSwitch,什么下会是LookupSwitch,毕竟两者的时间复杂度还是有差距
Java应用的性能,还是要详细分析其场景,至于要性能还是代码更优雅,要自己权衡了,呵呵,有更好的方案,还请分享哦
参考资料
http://stackoverflow.com/questions/10287700/difference-between-jvma-lookupswitch-and-tableswitch
http://docs.oracle.com/javase/specs/jvms/se7/html/jvms-3.html#jvms-3.10
相关推荐
Store multiple maps on your iPhone or iPad, and switch between them. With Bit Map, you can view your own choice of maps, instead of generic maps chosen by somebody else, making it ideal
Even if the pages switch frequently, the Map Component don't need to wait rendering. Basic Usage Install npm i react-fast-map // or yarn add react-fast-map 1. Import API file // 1. 在/public/index....
based on the IEEE 802.1D standard and Cisco proprietary extensions, or the rapid per-VLAN spanning-tree plus (rapid-PVST+) protocol based on the IEEE 802.1w standard. For information about the ...
*(This is not a matcap style reflection or cubemap.) - Outline: *(Can change the Color and Width) *(With noise/distort outline for sketch style outline and dynamic) *(You can choose to use outline or...
break,continue和return这三个语句的用法新手们经常弄混淆,至少在我学习c语言的时候经常把它们的用法给搞错。不过现在好了,我已彻底搞清楚它们之间的用法
ROM BIOS to version 1.21 or later. The ROM BIOS version number is displayed when you start your computer. 2.14 LANtastic -------------- If you use a LANtastic network, disable it before running Setup...
* added undocumented "-no2ndpass" switch to turn off 2nd pass processing * fixed: two pass processing sometimes produced superfluous sup files * fixed: MPG/EVO/VOB audio tracks with "PES extension 2" ...
or map) 二维数据结构 基础:树tree,图graph 高级:二叉搜索树binary search tree(red-black tree,AVL),堆heap,并查集disjoint set,字典树Trie 特殊数据结构 位运算Bitwise,布隆过滤器BloomFilter LRU Cache ...
Log Switch Frequency Map 194 Tablespace Map 194 TKProf Interface Wizard 196 Undo Advisor 198 Segment Advisor 200 LogMiner Interface 203 Health Check 207 Trace File Browser 226 CodeXpert 231 Database ...
MANIFEST_LOADING:"hlsManifestLoading",MANIFEST_LOADED:"hlsManifestLoaded",MANIFEST_PARSED:"hlsManifestParsed",LEVEL_SWITCH:"hlsLevelSwitch",LEVEL_SWITCHING:"hlsLevelSwitching",LEVEL_SWITCHED:...
or map), etc 二维 基础: 树tree, 图graph 二叉搜索树 binary search tree, 红黑树(red-black tree, AVL), 堆heap, 并查集disjoint set, 字典树 Trie, etc 特殊 位运算Bitwise, 布隆过滤器BloomFilter LRU Cache ...
Standard Template Library STL Basics Class List-A Set of Students Creating a Waiting List with the STL List Storing Grades in a STL Map Putting It All Together Practical Considerations When Using the...
\nplease press b or s or e.\n");getchar();break; } Star()函数:主要是显示一个界面,功能是提供查询路径选择和查看进入景点的主页面和退出该页面返回主界面。 switch(choose) {case '0':instruction();...
The logical switch varnorm (false | true) is used to instruct the code to perform variance normalization in addition to mean normalization. Examples In an example we plot the distribution (histogram...
Another useful rule of thumb: it's typically not cost effective to inline functions with loops or switch statements (unless, in the common case, the loop or switch statement is never executed)....
Call AfxInitRichEdit() in the InitInstance of the App class or in InitDialog. If it does not exist, copy OutLookRichEdit.cpp and OutLookRichEdit.h to the project directory. Click the menu choice ...
6.6.2 Karnaugh Map for Boolean Expressions with a Larger Number of Variables 222 6.6.3 Karnaugh Maps for Multi-Output Functions 225 Review Questions 230 Problems 230 Further Reading 231 7 Arithmetic ...
- GUI settings incorrect or not properly reflected in hardware. - Version fixed : v5.4 - CR#507334, CR#528369, CR#528370 / AR#32122 - The following register fields were corrected: Re-transmit ...
14.1 A Better Switch 198 14.2 Guards 199 14.3 Variables in Patterns 199 14.4 Type Patterns 200 14.5 Matching Arrays, Lists, and Tuples 201 14.6 Extractors 202 14.7 Patterns in Variable Declarations ...
to map a PCI BAR space directly to the application's virtual space. The application can then directly access the space via simple memory dereferencing, bypassing the PLX API/driver & resulting in ...