2012/10/23

alert('8' > '10'); // true?

在javascript內字串比較是依據長度,由左而右依序比較,規則是:
  • 相等則往下一位字元比較,反之則得出結果
  • 有值的比沒值的大

A的編碼是0041
B的編碼是0042
alert(‘A’ > ‘AB’); // false,因為最高位(最左邊)字元相等,而AB比較長
alert(‘B’ > ‘AB’); // true,最高位字元B比A大

再來看 ‘8’,‘1’,‘0’
0的編碼為0030
1的編碼為0031
8的編碼為0038
alert(‘8’ > ‘10’); // true
由於最高位’8’比’1’來的大,所以結果為true

2012/04/16

ResouseBundle.getBundle(String)在static情境下的問題


如果在一個static block或是static變數中呼叫ResourseBundle.getBundle(String)
在某些特定的情況下可能會造成MissingResourceException

其原因出在官方文件中敘述此method等同於呼叫
getBundle(baseName, Locale.getDefault(), this.getClass().getClassLoader())

問題在於this.getClass().getClassLoader()的部分,this在static內是取不到參照的
而實際上底層的實作是透過下列這段code取得ClassLoader
/*
 * Automatic determination of the ClassLoader to be used to load
 * resources on behalf of the client.  N.B. The client is getLoader's
 * caller's caller.
 */
private static ClassLoader getLoader() {
    Class[] stack = getClassContext();
    /* Magic number 2 identifies our caller's caller */
    Class c = stack[2];
    ClassLoader cl = (c == null) ? null : c.getClassLoader();
    if (cl == null) {
        // When the caller's loader is the boot class loader, cl is null
        // here. In that case, ClassLoader.getSystemClassLoader() may
        // return the same class loader that the application is
        // using. We therefore use a wrapper ClassLoader to create a
        // separate scope for bundles loaded on behalf of the Java
        // runtime so that these bundles cannot be returned from the
        // cache to the application (5048280).
        cl = RBClassLoader.INSTANCE;
    }
    return cl;
}

這樣會導致你取得的ClassLoader跟預期的結果不同
進而取不到目標resource

若要在static中使用ResourceBundle.getBundle(String)最好的方式還是自行呼叫
ResourseBundle.getBundle(baseName, Locale.getDefault(), [TargetClass].class.getClassLoader())