JSのビット演算子(性能向上)

14044 ワード

  • のすべてのJavaScript数字は、10に基づく64(8ビット)の浮動小数点として記憶されている.JavaScrip tはタイプ言語ではありません.多くの他のプログラミング言語と違って、JavaScriptは、整数、短い、長い、浮動小数点などの異なるタイプの数字を定義しない.
  • 整数精度(小数点以下または指数関数を使用しない)は最大15桁です.小数精度の最大桁数は17ですが、浮動小数点演算は常に100%正確ではありません.
  • ビット演算は直接にバイナリビットを計算し、ビット演算は直接に各ビットビットを処理し、非常に低いレベルの演算であり、利点は速度が非常に速く、欠点は直感的ではなく、多くの場合に使用できない.
  • ビット演算は整数のみに作用します.一つの演算数が整数でない場合、自動的に整数に変換して実行します.
  • JavaScript内部で、数値は64ビットの浮動小数点として保存されているが、ビット演算を行う場合は32ビットの符号付き整数で演算され、戻り値は32ビットの符号付き整数である.
  • JSでよく使われている7桁の演算子
    1.ビット順(AND)&&は、バイナリ数に対応するビットを特定の方法で組み合わせて操作し、対応するビットが全部1であれば、結果は1であり、いずれかのビットが0であれば、結果は0である.
    // 1       : 00000000 00000000 00000000 00000001
    // 3       : 00000000 00000000 00000000 00000011
    // -----------------------------
    // 1       : 00000000 00000000 00000000 00000001
    console.log(1 & 3)     // 1
    
    2.ビットまたは(OR)による||演算子と&との違いは、対応するビットのいずれかの動作数が1であれば結果は1であるということである.
    // 1       : 00000000 00000000 00000000 00000001
    // 3       : 00000000 00000000 00000000 00000011
    // -----------------------------
    // 3       : 00000000 00000000 00000000 00000011
    console.log(1 | 3)     // 3
    
    3.ビット別または(XOR)^^は、対応する2つの操作ビットがあり、1つの1だけの場合、結果は1であり、他はすべて0である.
    // 1       : 00000000 00000000 00000000 00000001
    // 3       : 00000000 00000000 00000000 00000011
    // -----------------------------
    // 2       : 00000000 00000000 00000000 00000010
    console.log(1 ^ 3)     // 2
    
    4.ビット別非(NOT)~~演算子は対位逆、1は0、0は1、つまりバイナリの逆符号を求めます.
    // 1       : 00000000 00000000 00000000 00000001
    // 3       : 00000000 00000000 00000000 00000011
    // -----------------------------
    // 1       : 11111111 11111111 11111111 11111110
    //      (   ) 1,          。JavaScript             ,         1,     ,      ,           10   。
    // -----------------------------
    // 1    1:     11111111 11111111 11111111 11111101
    //     :       00000000 00000000 00000000 00000010
    //    10     :-2
    console.log(~ 1)     // -2
    
  • 簡単な記憶:一つの数と自身のマイナス値の加算は-1に等しいです.
  • 5.左シフト<<<<演算子は、指定された値のバイナリ数をすべてのビットに左に移動させる回数を指定します.その移動規則:上位の位置を捨て、下位のビットは0を補う、つまりすべての数字を2進数で左に移動し、対応するビット数を上位の位置に移動(廃棄)し、下位のスペースはゼロを補足します.
    // 1       : 00000000 00000000 00000000 00000001
    // -----------------------------
    // 2       : 00000000 00000000 00000000 00000010
    console.log(1 << 1)     // 2
    
    6.符号付き右シフト>>>>このオペレータは、指定されたオペランドのバイナリビットを右に移動します.右に移動されたビットは破棄され、一番左のビットをコピーして左側を塗りつぶします.新しい一番左のビットはいつも以前と同じですので、シンボルビットは変更されませんでした.だから「符号伝播」と呼ばれています.
    // 1       : 00000000 00000000 00000000 00000001
    // -----------------------------
    // 0       : 00000000 00000000 00000000 00000000
    console.log(1 >> 1)     // 0
    
    7.符号なし右シフト>>>>>>このオペレータは、最初の操作数を指定されたビット数だけ右に移動する.右に移動されたビットは破棄され、左側は0で充填されます.シンボルビットが0になったので、結果はいつも負ではない.(注:0ビット右に移動しても、結果は負ではない.)
    非負の数に対しては、符号付きの右シフトと符号なしの右シフトは、常に同じ結果を返します.例えば、9 >>> 22 9 >> 2と同じである.
    ビット演算子のjsの中の妙な使い方
  • &演算子を使って一つの数のパリティを判断する
  • .
    //    & 1 = 0
    //    & 1 = 1
    console.log(2 & 1)    // 0
    console.log(3 & 1)    // 1
    
  • ~, >>, <>>, |を使用して
  • を整理する.
    console.log(~~ 6.83)    // 6
    console.log(6.83 >> 0)  // 6
    console.log(6.83 << 0)  // 6
    console.log(6.83 | 0)   // 6
    // >>>       
    console.log(6.83 >>> 0)   // 6
    
    
  • は、^を使用して値交換
  • を完了する.
    var a = 5
    var b = 8
    a ^= b
    b ^= a
    a ^= b
    console.log(a)   // 8
    console.log(b)   // 5
    
  • は、&, >>, |を使用して、rgb値と16進数色値の間の変換を完了する
  • .
    /**
     * 16      RGB
     * @param  {String} hex 16       
     * @return {String}     RGB     
     */
      function hexToRGB(hex) {
        var hexx = hex.replace('#', '0x')
        var r = hexx >> 16
        var g = hexx >> 8 & 0xff
        var b = hexx & 0xff
        return `rgb(${r}, ${g}, ${b})`
    }
    
    /**
     * RGB   16    
     * @param  {String} rgb RGB       
     * @return {String}     16       
     */
    function RGBToHex(rgb) {
        var rgbArr = rgb.split(/[^\d]+/)
        var color = rgbArr[1]<<16 | rgbArr[2]<<8 | rgbArr[3]
        return '#'+ color.toString(16)
    }
    // -------------------------------------------------
    hexToRGB('#ffffff')               // 'rgb(255,255,255)'
    RGBToHex('rgb(255,255,255)')      // '#ffffff'
    
    テストしましたが、確かにビット演算子の性能は従来のものより優れています.1 w回のテストでは、2.1 msかかりました.%3.5 msです.
    高性能クラスのライブラリやフレームワークに対しては、使用をサポートしています.しかし、高速反復のビジネスプロジェクトに対しては、1 wの性能は1.4 msの差があります.ほとんどのビジネスシーンでは、性能損失は無視できますが、可読性損失プログラマの時間コストは比較的大きいです.