1.不一样的数字的宽类型和窄类型
2.令人崩溃的字符串常量池和subString
3.不正常的finally和null
4.equals()也不容易等问题
一、常规问题采用常规的方式处理
二、不确定问题可以增加一些特殊/特定的条件(比如while循环中增加一些强制退出机制)
for(Entry<String,String> e:TSession.getCookiesPool().entrySet())
clienetCookieList.append(e.getKey()+""+e.getValue()+"</br>");
三、变量名称永远不要用l
四、数字结尾永远不要用l,表示long使用L
Long num =0x11111111L;
五、byte与int进行比较时,会进行有符号扩展
六、窄类型与宽类型比较时特别需要注意符号扩展
b==(byte)0x99
(b&0xFF)==0x99
七、复合赋值表达自动地将它们所执行的计算的结果转型为其左侧变量的类型
八、赋值操作数据越界导致编译错误
九、复合赋值只能是基本类型,基本类型的包装类型以及String,String的复合操作左侧必须是String类型
十、使用原则:宽类型向低类型赋值一定不要复合操作
X=x=1与x+=1相同。
x=x+1最低,因为它的执行过程如下:
(1)读取右x的地址。
(2)x+1.
(3)读取左x的地址。
(4)将右值传给左边的x(编译器并不认为左右x的地址相同)。
x+=1其次,其执行过程如下:
(1)读取右x的地址。
(2)x+1.
(3)将得到的值传给x(因为x的地址已经读出)。
x++效率最高,其执行过程如下:
(1)读取右x的地址。
(2)x自增1。
十一、不要指望
十二、不要指望常量池、尽量不要用intern()
十三、不要往常量池扔过多的东西,会导致持久化OOM
十四、如果只是普通的比较、匹配、传参、临时变量等、可以直接使用subString()
十五、如果需要成为常驻内存对象,需要包装下new String(s.subString(from,to))
十六、永远不要用命令为java.lang下的类名、包名不能命名为java/javax/java.lang/java.util/javax.sql
等开头、永远不能类命名完全一致而实现不一致、尽可能的避免相同名称,尽量不使用默认包。
十七、非常正常输出、永远不要用Label
特性(多亏没有goto
)
十八、finally里面不允许有 return/break/continue/throw
等改变正常退出的逻辑
十九、Set/HashSet
换成List/ArrayList
或者Map/HashMap
二十、equals()和hashCode()
总是成对出现、equals有 自反性、对称性、传递性、一致性、非空性
二十一、override针对实例方法
二十二、hidden针对静态方法、属性、内部类
二十三、override父类方法不能被调用,除非在子类内部使用super
二十四、hidden父类属性、静态方法等可以通过强制类型转换被调用
二十五、研究遮蔽(shadow)
和遮掩(obscure)
二十六、集合:List/Set/Map/ConcurrentMap
、锁:synchronized/volatile/lock
、线程池:ThreadPool/Timer/Future
二十七、ArrayLsit特性:容量可变集合、随机访问、可克隆、可序列化。原理:数组、1.5倍扩容、modCount特性、注意点 静态引用防止内存泄漏:clear()/trimToSize()
、循环注意并发修改、带索引迭代:list.listIterator()
、循环删除方式
二十八、HashMap特性:任意key编码、快速定位元素、自动扩充容量、HashMap
实现 hashCode()、 indexFor()、resize()/rehash()
注意点:静态引用防止内存泄漏:clear()/capacity
、循环并发修改、循环使用entrySet()
二十九、指令重排序与volatile、原子操作与CAS、可重入锁与读写锁、条件变量与线程挂起、唤醒
三十、JUC
体系结构、COncurrentHashMap
的原理、徘徊BlockingQueue
、线程池的最佳实践
三十一、SRP、OCP、DIP、ISP、LSP