3

理解できない奇妙な JavaScript を見つけました。for サイクルには奇妙な構文 (多くのパラメーター) があります。どのように機能するのか説明してもらえますか? ありがとう

decode: function(s){
        for(var a, b, i = -1, l = (s = s.split("")).length, o = String.fromCharCode, c = "charCodeAt"; ++i < l;
            ((a = s[i][c](0)) & 0x80) &&
            (s[i] = (a & 0xfc) == 0xc0 && ((b = s[i + 1][c](0)) & 0xc0) == 0x80 ?
            o(((a & 0x03) << 6) + (b & 0x3f)) : o(128), s[++i] = "")
        );
        return s.join("");
    }
4

4 に答える 4

5

これは通常のforループですが、最初の部分に非常に長いvarステートメントがあります。

まるで

var a, b, c;

また、for ループの iterator ステートメントには、実際に本体を持つループではなく、多くの操作が含まれています。

この関数は、可読コードを考慮しないひどいプログラマーによって書かれたか、意図的に縮小され難読化されています。

于 2012-05-04T20:17:47.053 に答える
2

興味深い機能で、明らかに特定の文字セットをトランスコーディングし、一種の難解で、ASCIIコードでのみ機能しますが、内訳は次のとおりです。

    for (var i = 0; i < s.length; i++) {
        var a = s.charCodeAt(i);

        if (a & 0x80) { // (a >= 128) if extended ascii

            var b = s.charCodeAt(i + 1);

            var specialA = (a & 0xfc) === 0xc0; // a IS [À, Á, Â or Ã] essentially [192, 193, 194, 195]
            var specialB = (b & 0xc0) === 0x80; // b >= 128 & b <= 191 eg. b is not a special Latin Ascii Letter

            if (specialA && specialB) {

                var txA = (a & 0x03) << 6; // [0, 64, 128, 192]
                var txB = b & 0x3f; // 0 - 63

                s[i] = String.fromCharCode(txA + txB);

            } else {
                s[i] = String.fromCharCode(128);
                s[++i] = "";
            }
        }
    }

これが役に立てば幸いです。どちらにしても、デコードが興味深いと感じました。生のアセンブラを読んだことを思い出します。笑 -ck

于 2012-05-04T21:22:23.673 に答える
1

for ループのさまざまな部分がすべてあり、セミコロン ( ) で区切られてい;ます。

変数部分:

var a, b, i = -1, l = (s = s.split("")).length, o = String.fromCharCode, c = "charCodeAt";

チェック部分:

++i < l;

更新部分:

((a = s[i][c](0)) & 0x80) &&
        (s[i] = (a & 0xfc) == 0xc0 && ((b = s[i + 1][c](0)) & 0xc0) == 0x80 ?
        o(((a & 0x03) << 6) + (b & 0x3f)) : o(128), s[++i] = "")

つまり、ループには本体がありませんが、var-、check-、および update 部分のすべてのステートメントは、チェックが終了するまで実行されfor()ます。;true

誰かが自分のコードを読みやすくしたくないようです。とにかく、どこでそれを見つけましたか?

于 2012-05-04T20:26:16.260 に答える
1

ループをより読みやすいものに分割します。

  • ループパラメータの再配置
  • (...)&&(...)で変更if(...){(...)}
  • lに変更len
  • s = s.split(...)外に移動したlen

.

var a, b, s = s.split(""), o = String.fromCharCode, c = "charCodeAt";

for(var i = -1, len = s.length; ++i < len;){
    if((a = s[i][c](0)) & 0x80){
        (s[i] = (a & 0xfc) == 0xc0 && ((b = s[i + 1][c](0)) & 0xc0) == 0x80 ? o(((a & 0x03) << 6) + (b & 0x3f)) : o(128), s[++i] = "");
    }
}

  • i初期値とそれがどのように/どこで増加するかを変更しました
  • a = s[i][c](0)外に引っ越した

.

var a, b, s = s.split(""), o = String.fromCharCode, c = "charCodeAt";

for(var i = 0, len = s.length; i < len; i++){
    a = s[i][c](0);

    if(a & 0x80){
        s[i] = (a & 0xfc);
        (s[i] == 0xc0 && ((b = s[i + 1][c](0)) & 0xc0) == 0x80 ? o(((a & 0x03) << 6) + (b & 0x3f)) : o(128), s[++i] = "");
    }
}

  • tmp読みやすくするために作成された
  • 三項演算結果を格納tmp
  • (s[i] == 0xc0 && tmp, s[++i] = "");で 分割if(...){s[++i] = "";}
  • あなたの例の中の新しいループを置き換えました

.

decode: function(s){
    var tmp, a, b, s = s.split(""), o = String.fromCharCode, c = "charCodeAt";

    for(var i = 0, len = s.length; i < len; i++){
        a = s[i][c](0);

        if(a & 0x80){
            s[i] = (a & 0xfc);

            if(((b = s[i + 1][c](0)) & 0xc0) == 0x80){
                tmp = o(((a & 0x03) << 6) + (b & 0x3f));
            }else{
                tmp = o(128);
            }

            if(s[i] == 0xc0 && tmp){
                s[++i] = "";
            }
        }
    }

    return s.join("");
}

最終結果/\

于 2012-05-04T21:20:45.677 に答える