亚洲激情专区-91九色丨porny丨老师-久久久久久久女国产乱让韩-国产精品午夜小视频观看

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

Javascript分號規則是什么

發布時間:2020-12-02 13:34:48 來源:億速云 閱讀:137 作者:小新 欄目:web開發

小編給大家分享一下Javascript分號規則是什么,相信大部分人都還不怎么了解,因此分享這篇文章給大家參考一下,希望大家閱讀完這篇文章后大有收獲,下面讓我們一起去了解一下吧!

分號允許的場景

分號一般允許出現在大部分語句(statement)的末尾,比如 do-while statement , var statements, expression statements , continue , return , break statement, throw, debugger 等

栗子:

do Statement while ( Expression ) ;

4+4;

f();

debugger;

僅有一個分號 ; 可以表示空語句——在JS中合法,比如 ;;; 可解析為三個空語句(empty statement)

空語句可用于輔助產生語法合法的解析結果,如:

while(1);

如果沒有末尾的分號,將會產生解析錯誤 —— 條件循環后必須跟隨一個語句

分號還會出現在 for 循環 for ( Expression ; Expression ; Expression ) Statement 中

最后,分號還會出現在 字符串 或 正則表達式中 —— 表示分號本身

分號可以省略的場景

有些場景下分號可以省略,解析器在解析語句時會根據需要自動插入分號,大概流程可以這樣理解:

書寫省略 => 解析器解析時發現缺少時會無法正確解析 => 自動添加分號

so 需要明確能自動插入分號的場景,并明確不會自動插入分號且會引起解析錯誤的情況

規則1:當下一個 token (offending token) 和當前解析的 token (previous token) 無法組成合法語句,且滿足以下一個或多個條件時,將會在 offending token 前插入一個分號:

  • offending token 和 previous token 被至少一個換行符分割(LineTerminator),且分號插入的作用不是被解析為 空語句 (empty statement)
  • offending token 是 }
  • previous token 是 ), 并且插入的分號將被解析為do-while語句的終止分號

還要考慮一種優先級更高的條件:如果插入的分號會被解析為一個空語句,或是 for 語句的頭部兩個分號之一,這時不會插入分號(除了 do-while 語句的終止分號外)

規則2:當解析到達源代碼文件 (input stream) 的末尾時,將自動添加一個分號標識解析結束

規則3:符合 restricted production 語法的語句 —— 比較難翻譯,看不懂的可以直接看栗子,這種情況主要描述的是:不應該出現換行符的地方出現換行符導致插入分號引起原語句含義變化

同時滿足以下條件,將在 offending token 前自動插入一個分號:

  • offending token 和 previous token 組成合語法的 restricted production 語句
  • offending token 出現于 restricted production 語句描述中的 [no LineTerminaator here] 部分 ( the token would be the first token for a terminal or nonterminal immediately following the annotation “[no LineTerminator here]” within the restricted production )
  • offending token 和 previous token 之間至少存在一個換行符 (LineTerminator)

其中 restricted production 包括且只有以下:

UpdateExpression[Yield, Await]:
  LeftHandSideExpression[?Yield, ?Await] [no LineTerminator here] ++
  LeftHandSideExpression[?Yield, ?Await] [no LineTerminator here] --

ContinueStatement[Yield, Await]:
  continue;
  continue [no LineTerminator here] LabelIdentifier[?Yield, ?Await];

BreakStatement[Yield, Await]:
  break;
  break  [no LineTerminator here]  LabelIdentifier[?Yield, ?Await];

ReturnStatement[Yield, Await]:
  return;
  return  [no LineTerminator here]  Expression  [+In, ?Yield, ?Await];

ThrowStatement[Yield, Await]:
  throw [no LineTerminator here] Expression [+In, ?Yield, ?Await];

ArrowFunction[In, Yield, Await]:
  ArrowParameters[?Yield, ?Await] [no LineTerminator here] => ConciseBody[?In]

YieldExpression[In, Await]:
  yield [no LineTerminator here] * AssignmentExpression[?In, +Yield, ?Await]
  yield [no LineTerminator here] AssignmentExpression[?In, +Yield, ?Await]

簡單總結:

使用 a++ 語句時,變量和 ++ 必須在同一行,否則會在 ++ 前插入分號導致語義不同

return throw yield continue break 后如果緊跟著換行,將會自動添加分號

箭頭函數的 => 之前不應該有換行符

栗子 & 可能不符合預期的情況

符合預期情況

// 相當于 42;"hello"
42
"hello"

// offending token 是 }
if(x){y()}

// previous token 是 ) 且插入分號是 do while 語句的結束
var a = 1
do {a++} while(a<100)
console.log(a)

//  不會解析成 b++ 因為 b和++之間存在換行符,會在 b 之后自動插入分號
a = b
++c

可能不符合預期的情況

const hey = 'hey'
const you = 'hey'
const heyYou = hey + ' ' + you

['h', 'e', 'y'].forEach((letter) => console.log(letter))

會收到錯誤 Uncaught TypeError: Cannot read property 'forEach' of undefined , 因為 you 和 ['h', 'e', 'y'] 的連接能命中合法語法,故它們之間不會自動插入分號 —— 與預期不一致,JS嘗試將代碼解析為:

const hey = 'hey';
const you = 'hey';
const heyYou = hey + ' ' + you['h', 'e', 'y'].forEach((letter) => console.log(letter))

再看一種情況:

const a = 1
const b = 2
const c = a + b
(a + b).toString()

會引發 TypeError: b is not a function 報錯,因為會被解釋為:

const a = 1
const b = 2
const c = a + b(a + b).toString()

除了 do while 語句外,不會有插入分號作為空語句的其他情況,或作為 for 語句頭部的兩個必要分號 :

if (a > b)
else c = d

for (a; b
)

以上均不是合法的 JS 語句,并且會引起報錯

故以下栗子中的每一個分號都不能省略!!

// for循環沒有循環體的情況,每一個分號都不能省略
for (node=getNode();
     node.parent;
     node=node.parent) ;

再看一個帶詳細注釋的例子:

var         // 這一行不會插入分號 ,因為 下一行的代碼不會破壞當前行的代碼  
    a = 1   // 這一行會插入分號   
let b = 2   

// 再比如這種情況,你的原意可能是定義 `a` 變量,再執行 `(a + 3).toString()`,
// 但是其實 JavaScript 解析器解析成了,`var a = 2(a + 3).toString()`,
// 這時會拋出錯誤 Uncaught TypeError: 2 is not a function
var a = 2
(a + 3).toString()

// 同理,下面的代碼會被解釋為 `a = b(function(){...})()`
a = b
(function(){
...
})()

以上都是未能命中規則1而未插入分號導致解析與預期不符合的情況

看一個基于規則3的例子:

(() => {
  return
  {
    color: 'white'
  }
})()

預期是返回一個包含 color 屬性的對象,但事實上 return 后會被插入一個分號,而導致最終返回 undefined,可以通過在 return 后立刻放置花括號 { :

(() => {
  return {
    color: 'white'
  }
})()

省略分號的最佳實踐

不要使用以下單個字符 ( [ / + - 開始一行 , 會極有可能和上一行語句合在一起被解析( ++ 和 -- 不符合單個 +、- 字符)

注意 return break throw continue 語句,如果需要跟隨參數或表達式,把它添加到和這些語句同一行,針對 return 返回內容較多的情況 (大對象,柯里化調用,多行字符串等),可以參考規則1,避免命中該規則而引起非預期的分號插入,比如:

return obj.method('abc')
          .method('xyz')
          .method('pqr')
 
return "a long string\n"
     + "continued across\n"
     + "several lines"
 
totalArea = rect_a.height * rect_a.width
          + rect_b.height * rect_b.width
          + circ.radius * circ.radius * Math.PI

后綴運算符 ++ -- 需要和操作變量在同一行使用

當然大部分工程化情況下,我們最終會配合Eslint使用帶分號或省略分號規范

以上是“Javascript分號規則是什么”這篇文章的所有內容,感謝各位的閱讀!相信大家都有了一定的了解,希望分享的內容對大家有所幫助,如果還想學習更多知識,歡迎關注億速云行業資訊頻道!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

永州市| 离岛区| 赣榆县| 宜昌市| 九龙坡区| 射阳县| 锡林郭勒盟| 轮台县| 纳雍县| 阿城市| 措美县| 通辽市| 瓮安县| 黄骅市| 丰顺县| 临泽县| 嘉善县| 新郑市| 玉林市| 竹溪县| 蚌埠市| 班戈县| 洛扎县| 武宣县| 卢氏县| 闽清县| 车致| 固原市| 渭南市| 广东省| 凌云县| 扬州市| 香格里拉县| 老河口市| 清流县| 河津市| 怀化市| 工布江达县| 修武县| 环江| 通河县|