成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

一行神奇的javascript代碼

開發 前端
寫本篇文章的緣由是之前群里@墨塵發了一段js代碼。只是有一些需要重復勞動的,只要你掌握了運算的優先級,能把大串分解成一個個小串,然后運用類型轉化的知識挨個處理就搞定了。

[[187451]]

寫本篇文章的緣由是之前群里@墨塵發了一段js代碼,如下:

  1. (!(~+[])+{})[--[~+""][+[]]*[~+[]] + ~~!+[]]+({}+[])[[~!+[]]*~+[]] 

然后讓大家運行,出來的結果讓人有點出乎意料,請看:

 

 

太風騷了有木有!如果有人詆毀前端瞧不起js的話,那就可以把這段代碼發給他了~

不過話說回來了,這到底是什么原理呢?為什么一堆符號運算結果竟然能是兩個字符,而且恰巧還是個sb!

其實靠的是js的類型轉化的一些基本原理,本篇就來揭密”sb”是如何煉成的。相信你如果能把這個理清楚了,以后遇到類型轉化之類的題目,就可以瞬間秒殺了。

首先要運用到的***個知識就是js運算符的優先級,因為這么長一段運算看的人眼花,我們必須得先根據優先級分成n小段,然后再各個擊破。優先級的排列如下表:

優先級從高到低:

 

 

根據此規則,我們把這一串運算分為以下16個子表達式:

 

 

運算符用紅色標出,有一點可能大家會意識不到,其實中括號[]也是一個運算符,用來通過索引訪問數組項,另外也可以訪問字符串的子字符,有點類似charAt方法,如:’abcd’[1] // 返回’b'。而且中括號的優先級還是***的哦。

預處理結束,接下來需要運用的就是javascript的類型轉化知識了。我們先說說什么情況下需要進行類型轉化。當操作符兩邊的操作數類型不一致或者不是基本類型(也叫原始類型)時,需要進行類型轉化。先按運算符來分一下類:

  • 減號-,乘號*,肯定是進行數學運算,所以操作數需轉化為number類型。
  • 加號+,可能是字符串拼接,也可能是數學運算,所以可能會轉化為number或string
  • 一元運算,如+[],只有一個操作數的,轉化為number類型

下面來看一下轉化規則。

1. 對于非原始類型的,通過ToPrimitive() 將值轉換成原始類型:

ToPrimitive(input, PreferredType?)

可選參數PreferredType是Number或者是String。返回值為任何原始值.如果PreferredType是Number,執行順序如下:(參考:http://es5.github.io/#x9.1)

如果input為primitive,返回

否則,input為Object。調用 obj.valueOf()。如果結果是primitive,返回。

否則,調用obj.toString(). 如果結果是primitive,返回

否則,拋出TypeError

如果 PreferredType是String,步驟2跟3互換,如果PreferredType沒有,Date實例被設置成String,其他都是Number

2. 通過ToNumber()把值轉換成Number,直接看ECMA 9.3的表格http://es5.github.io/#x9.3

規則如下:

 

 

3. 通過ToString()把值轉化成字符串, 直接看ECMA 9.8的表格http://es5.github.io/#x9.8

 

 

規則就這么多,接下來實踐一下,根據我們上面劃分出的子表達式,一步一步將這個神奇的代碼給執行出來。開工~

先看最簡單的子表達式16:+[]

只有一個操作數[],肯定是轉化為number了,根據上面的規則2,[]是個數組,object類型,即對象。所以得先調用toPrimitive轉化為原始類型,并且PreferredType為number,這個參數表示更“傾向于”轉化的類型,這里肯定是number了。然后首先調用數組的valueOf方法,數組調用valueOf會返回自身,如下:

  1. [].value.of() 
  2.  
  3. [] 

 

這個時候,我們得到一個空串“”,還沒有結束,看上面的規則2描述,繼續調用toNumber,轉化為number類型,如下:

  1. Number(""
  2.  

 

大功告成!子表達式16轉化完畢,+[],最終得到0。

來看子表達式15:[~+""]

空串”"前面有兩個一元操作符,但是操作數還是只有一個,所以,最終要轉化為的類型是number。看規則2吧,空串調用toNumber得到0。接下來是~,這是個什么東東呢?它是位運算符,作用可以記為把數字取負然后減一,所以~0就是-1 。

別忘了,這個子表達式外頭還包著中括號,所以最終的值為[-1],即一個數組,里面只有一個元素-1.

接下來看子表達式13就簡單了,把15、16求出來的填進去,就變成了這樣:–[-1][0],取數組的第0個元素,然后自減,結果為-2,是不so easy!

繼續往上走,子表達式14: [~+[]]

其實把15、和16的原理用上就非常明顯了,答案[-1]

繼續來求子表達式9,此刻它已變成:-2*[-1],有稍許不一樣,不過沒關系,我們還是按照規則來,運算符是乘號*,當然是做數學運算,那后面的[-1]就得轉化為number,與16的求法類似,過程如下:

①調用toPrimitive,發現是object類型

②調用valueOf,返回自身[-1]

③因為不是原始類型,繼續調用toString,返回”-1″

④”-1″是原始類型了,然后調用toNumber,返回-1

⑤與-2相乘,返回2

子表達式10:~~!+[],不多說了,答案1. 就是從右往左依次一元計算。

有了9和10,我們來到了子表達式4,此刻它已經長這樣了:2+1, 好,我不多說了。

繼續看表達式7:!(~+[]),~+[]=-1,這個根據上面已經知道了,那!-1是什么呢?這里要說一下這個感嘆號,它是邏輯取非的意思,會把表達式轉化為布爾類型,轉化規則和js的Truthy和Falsy原則是一樣的,后面跟數字的,除0以外都為false,后面跟字符串的,除空串以外都為false。這里的!-1當然就是false了。

接下來這個表達式3:false+{}有點關鍵。一個布爾加一個對象,那這個{}應該先轉化為原始類型,流程如下:

①調用toPrimitive,發現是object類型

②調用valueOf,返回自身{},

③不是原始類型,調用toString,返回”[object Object]“

④false與”[object Object]“相加,false先轉化為字符串”false”

⑤相加得結果”false[object Object]“

知道了表達式3和4,我們就可以來看表達式1了,此時它是這樣的:”false[object Object]“[3],因為這個[]可以取字符串的子字符,像charAt一樣,所以得到了結果”s”

經過上面艱難的流程,我們拿到了字符”s”,也就是那張圖的左半邊,剩下的那個”b”,相同的原理可以搞出來,我這里就不一一演示了,留給你練練吧~

回顧一下這個過程其實也不復雜,只是有一些需要重復勞動的,只要你掌握了運算的優先級,能把大串分解成一個個小串,然后運用類型轉化的知識挨個處理就搞定了。怎么樣,看到這里你還覺得神奇嗎?

如果有人瞧不起js,請把這段代碼發給他,如果他想知道答案,請把本文發給他~

責任編輯:龐桂玉 來源: 前端大全
相關推薦

2021-11-02 16:25:41

Python代碼技巧

2024-11-08 17:22:22

2009-07-23 09:20:25

Javascript代

2016-12-02 08:53:18

Python一行代碼

2021-02-24 14:30:59

JavaScript語言開發

2025-05-09 08:00:00

JavaScript代碼防抖節流

2025-03-05 11:00:00

JavaScript跨域前端

2025-04-17 08:05:00

JavaScript

2014-02-12 13:43:50

代碼并行任務

2022-04-09 09:11:33

Python

2025-03-25 08:15:00

JavaScript開發代碼

2025-03-07 07:20:00

JavaScript異步編程Promise

2020-08-12 14:54:00

Python代碼開發

2021-08-31 09:49:37

CPU執行語言

2017-04-13 19:20:18

Python代碼并行任務

2020-08-19 10:30:25

代碼Python多線程

2020-09-09 16:00:22

Linux進程

2023-09-12 10:10:57

開發者工具開源

2021-11-05 06:57:50

架構工具代碼

2019-12-25 14:08:50

Pandas數據計算
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 夜夜骑首页 | 欧美成人精品一区二区男人看 | 日批免费在线观看 | 亚洲精品乱码久久久久久蜜桃91 | 国产欧美精品在线观看 | 一级看片免费视频囗交动图 | 日韩小视频在线 | 91成人在线 | 久久成人高清视频 | 狠狠久久综合 | 精品久久香蕉国产线看观看亚洲 | 久久久久久久电影 | 久久99精品国产自在现线小黄鸭 | 99精品在线观看 | 久久精品色欧美aⅴ一区二区 | 9久久精品 | 性高朝久久久久久久3小时 av一区二区三区四区 | 狠狠干五月天 | 在线看片国产精品 | 欧美激情五月 | 欧美电影一区 | 一区影视 | av网站在线播放 | 精品国产一区二区三区四区在线 | 久久精品国产一区 | 成人免费一区二区 | 日韩欧美在线免费 | 欧美日韩久久精品 | 亚洲第一在线 | 91xxx在线观看 | 日本一区不卡 | 成人在线免费视频 | 久久蜜桃资源一区二区老牛 | 亚洲传媒在线 | 国产精品欧美一区二区三区不卡 | 日日碰狠狠躁久久躁96avv | 91国产视频在线 | 一级黄a视频 | 国产精品国产三级国产aⅴ中文 | 日韩免费看视频 | 日韩一二区 |