阅读String类源代码发现几个有趣的地方
翻阅String类源代码发现几个有趣的地方
1、看以下代码 Stirng类的hashcode 方法
s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1] *
这部分说明是这个string 的char数组的ascII拼接后31位进制的值。
不知道为什么是31,有什麽依据?。
2、1、看以下代码 Stirng类的toLowerCase方法片段
像是个1次循环,不过这种写法估计没怎么有人用过
何意?
我想在某些时候是可以减少点代码量的,不过貌似没多大意义
3、String 的intern 方法
其实该方法没多大用,但其说明String 在内部是缓存的。
才发现,其实臧圩人已经说得很清楚了 我就不多赘述了
"在JAVA虚拟机(JVM)中存在着一个字符串池,其中保存着很多String对象,并且可以被共享使用,因此它提高了效率。由于String类是final的,它的值一经创建就不可改变,因此我们不用担心String对象共享而带来程序的混乱。字符串池由String类维护,我们可以调用intern()方法来访问字符串池。"
参见
http://zangweiren.iteye.com/blog/216005
1、看以下代码 Stirng类的hashcode 方法
/** * Returns a hash code for this string. The hash code for a * <code>String</code> object is computed as * <blockquote><pre> * s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1] * </pre></blockquote> * using <code>int</code> arithmetic, where <code>s[i]</code> is the * <i>i</i>th character of the string, <code>n</code> is the length of * the string, and <code>^</code> indicates exponentiation. * (The hash value of the empty string is zero.) * * @return a hash code value for this object. */ public int hashCode() { int h = hash; if (h == 0) { int off = offset; char val[] = value; int len = count; for (int i = 0; i < len; i++) { h = 31*h + val[off++]; } hash = h; } return h; }
s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1] *
这部分说明是这个string 的char数组的ascII拼接后31位进制的值。
不知道为什么是31,有什麽依据?。
2、1、看以下代码 Stirng类的toLowerCase方法片段
/* Now check if there are any characters that need to be changed. */ scan: { int c; for (firstUpper = 0 ; firstUpper < count ; firstUpper += Character.charCount(c)) { c = codePointAt(firstUpper); if (c != Character.toLowerCase(c)) { break scan; } } return this; }
像是个1次循环,不过这种写法估计没怎么有人用过
何意?
我想在某些时候是可以减少点代码量的,不过貌似没多大意义
情况1: action:{ for(...){ if(..)break action } do something } 或 boolena flag =false; for(...){ if(..){ flag =true; break; } } if(flag) do something 情况2: action:{ do something 1 if(flag) break action do something 2 } 或 do Some thing 1 if(flag) do Some thing 2
3、String 的intern 方法
/** * Returns a canonical representation for the string object. * <p> * A pool of strings, initially empty, is maintained privately by the * class <code>String</code>. * <p> * When the intern method is invoked, if the pool already contains a * string equal to this <code>String</code> object as determined by * the {@link #equals(Object)} method, then the string from the pool is * returned. Otherwise, this <code>String</code> object is added to the * pool and a reference to this <code>String</code> object is returned. * <p> * It follows that for any two strings <code>s</code> and <code>t</code>, * <code>s.intern() == t.intern()</code> is <code>true</code> * if and only if <code>s.equals(t)</code> is <code>true</code>. * <p> * All literal strings and string-valued constant expressions are * interned. String literals are defined in §3.10.5 of the * <a href="http://java.sun.com/docs/books/jls/html/">Java Language * Specification</a> * * @return a string that has the same contents as this string, but is * guaranteed to be from a pool of unique strings. */ public native String intern();
其实该方法没多大用,但其说明String 在内部是缓存的。
才发现,其实臧圩人已经说得很清楚了 我就不多赘述了
"在JAVA虚拟机(JVM)中存在着一个字符串池,其中保存着很多String对象,并且可以被共享使用,因此它提高了效率。由于String类是final的,它的值一经创建就不可改变,因此我们不用担心String对象共享而带来程序的混乱。字符串池由String类维护,我们可以调用intern()方法来访问字符串池。"
参见
http://zangweiren.iteye.com/blog/216005
1 楼
抛出异常的爱
2009-05-07
s[0]*31^(n-1) + s[1]*31^(n-2) + ... + s[n-1] *
这部分说明是这个string 的char数组的ascII拼接后31位进制的值。
不知道为啥不是32或30 貌似没什么区别。
如果算子是个质数的话
在hash算法时
数据更趋向正态分布
好像是说:
向一个hash树上挂时能更充分的使用空间,
不用挂一个就要扩一次.
这部分说明是这个string 的char数组的ascII拼接后31位进制的值。
不知道为啥不是32或30 貌似没什么区别。
如果算子是个质数的话
在hash算法时
数据更趋向正态分布
好像是说:
向一个hash树上挂时能更充分的使用空间,
不用挂一个就要扩一次.