摘要:使用兩個(gè)空格進(jìn)行縮進(jìn)。例外可以用來(lái)檢查。子類的構(gòu)造器中一定要調(diào)用使用數(shù)組字面量而不是構(gòu)造器。不要向構(gòu)造器傳入非法的正則表達(dá)式。禁止使用構(gòu)造器。在沒(méi)有分號(hào)的情況下代碼壓縮后會(huì)導(dǎo)致報(bào)錯(cuò),而堅(jiān)持這一規(guī)范則可避免出錯(cuò)。
使用兩個(gè)空格進(jìn)行縮進(jìn)。
eslint: indent
function hello (name) { console.log("hi", name) }
除需要轉(zhuǎn)義的情況外,字符串統(tǒng)一使用單引號(hào)。
eslint: quotes
console.log("hello there") $("")不要定義未使用的變量。
eslint: no-unused-vars
function myFunction () { var result = something() // ? avoid }關(guān)鍵字后面加空格。
eslint: keyword-spacing
if (condition) { ... } // ? ok if(condition) { ... } // ? avoid函數(shù)聲明時(shí)括號(hào)與函數(shù)名間加空格。
eslint: space-before-function-paren
function name (arg) { ... } // ? ok function name(arg) { ... } // ? avoid run(function () { ... }) // ? ok run(function() { ... }) // ? avoid始終使用 === 替代 ==。
例外: obj == null 可以用來(lái)檢查 null || undefined。
eslint: eqeqeq
if (name === "John") // ? ok if (name == "John") // ? avoid if (name !== "John") // ? ok if (name != "John") // ? avoid字符串拼接操作符 (Infix operators) 之間要留空格。
eslint: space-infix-ops
// ? ok var x = 2 var message = "hello, " + name + "!" // ? avoid var x=2 var message = "hello, "+name+"!"逗號(hào)后面加空格。
eslint: comma-spacing
// ? ok var list = [1, 2, 3, 4] function greet (name, options) { ... } // ? avoid var list = [1,2,3,4] function greet (name,options) { ... }else 關(guān)鍵字要與花括號(hào)保持在同一行。
eslint: brace-style
// ? ok if (condition) { // ... } else { // ... } // ? avoid if (condition) { // ... } else { // ... }多行 if 語(yǔ)句的的括號(hào)不能省
。
eslint: curly
// ? ok if (options.quiet !== true) console.log("done") // ? ok if (options.quiet !== true) { console.log("done") } // ? avoid if (options.quiet !== true) console.log("done")不要丟掉異常處理中err參數(shù)。
eslint: handle-callback-err
// ? ok run(function (err) { if (err) throw err window.alert("done") }) // ? avoid run(function (err) { window.alert("done") })使用瀏覽器全局變量時(shí)加上 window. 前綴。
Exceptions are: document, console and navigator.
eslint: no-undef
window.alert("hi") // ? ok不允許有連續(xù)多行空行。
eslint: no-multiple-empty-lines
// ? ok var value = "hello world" console.log(value) // ? avoid var value = "hello world" console.log(value)對(duì)于三元運(yùn)算符 ? 和 : 與他們所負(fù)責(zé)的代碼處于同一行
eslint: operator-linebreak
// ? ok var location = env.development ? "localhost" : "www.api.com" // ? ok var location = env.development ? "localhost" : "www.api.com" // ? avoid var location = env.development ? "localhost" : "www.api.com"每個(gè) var 關(guān)鍵字多帶帶聲明一個(gè)變量。
eslint: one-var
// ? ok var silent = true var verbose = true // ? avoid var silent = true, verbose = true // ? avoid var silent = true, verbose = true條件語(yǔ)句中賦值語(yǔ)句使用括號(hào)包起來(lái)。
這樣使得代碼更加清晰可讀,而不會(huì)認(rèn)為是將條件判斷語(yǔ)句的全等號(hào)(===)錯(cuò)寫成了等號(hào)(=)。
eslint: no-cond-assign
// ? ok while ((m = text.match(expr))) { // ... } // ? avoid while (m = text.match(expr)) { // ... }單行代碼塊兩邊加空格。
eslint: block-spacing
function foo () {return true} // ? avoid function foo () { return true } // ? ok對(duì)于變量和函數(shù)名統(tǒng)一使用駝峰命名法。
eslint: camelcase
function my_function () { } // ? avoid function myFunction () { } // ? ok var my_var = "hello" // ? avoid var myVar = "hello" // ? ok不允許有多余的行末逗號(hào)。
eslint: comma-dangle
var obj = { message: "hello", // ? avoid }始終將逗號(hào)置于行末。
eslint: comma-style
var obj = { foo: "foo" ,bar: "bar" // ? avoid } var obj = { foo: "foo", bar: "bar" // ? ok }點(diǎn)號(hào)操作符須與屬性需在同一行。
eslint: dot-location
console. log("hello") // ? avoid console .log("hello") // ? ok文件末尾留一空行。
eslint: eol-last
函數(shù)調(diào)用時(shí)標(biāo)識(shí)符與括號(hào)間不留間隔。
eslint: func-call-spacing
console.log ("hello") // ? avoid console.log("hello") // ? ok鍵值對(duì)當(dāng)中冒號(hào)與值之間要留空白。
eslint: key-spacing
var obj = { "key" : "value" } // ? avoid var obj = { "key" :"value" } // ? avoid var obj = { "key":"value" } // ? avoid var obj = { "key": "value" } // ? ok構(gòu)造函數(shù)要以大寫字母開(kāi)頭。
eslint: new-cap
function animal () {} var dog = new animal() // ? avoid function Animal () {} var dog = new Animal() // ? ok無(wú)參的構(gòu)造函數(shù)調(diào)用時(shí)要帶上括號(hào)。
eslint: new-parens
function Animal () {} var dog = new Animal // ? avoid var dog = new Animal() // ? ok對(duì)象中定義了存值器,一定要對(duì)應(yīng)的定義取值器。
eslint: accessor-pairs
var person = { set name (value) { // ? avoid this._name = value } } var person = { set name (value) { this._name = value }, get name () { // ? ok return this._name } }子類的構(gòu)造器中一定要調(diào)用 super
eslint: constructor-super
class Dog { constructor () { super() // ? avoid } } class Dog extends Mammal { constructor () { super() // ? ok } }使用數(shù)組字面量而不是構(gòu)造器。
eslint: no-array-constructor
var nums = new Array(1, 2, 3) // ? avoid var nums = [1, 2, 3] // ? ok避免使用 arguments.callee 和 arguments.caller。
eslint: no-caller
function foo (n) { if (n <= 0) return arguments.callee(n - 1) // ? avoid } function foo (n) { if (n <= 0) return foo(n - 1) }避免對(duì)類名重新賦值。
eslint: no-class-assign
class Dog {} Dog = "Fido" // ? avoid避免修改使用 const 聲明的變量。
eslint: no-const-assign
const score = 100 score = 125 // ? avoid避免使用常量作為條件表達(dá)式的條件(循環(huán)語(yǔ)句除外)。
eslint: no-constant-condition
if (false) { // ? avoid // ... } if (x === 0) { // ? ok // ... } while (true) { // ? ok // ... }正則中不要使用控制符。
eslint: no-control-regex
var pattern = /x1f/ // ? avoid var pattern = /x20/ // ? ok不要使用 debugger。
eslint: no-debugger
function sum (a, b) { debugger // ? avoid return a + b }不要對(duì)變量使用 delete 操作
。
eslint: no-delete-var
var name delete name // ? avoid不要定義冗余的函數(shù)參數(shù)。
eslint: no-dupe-args
function sum (a, b, a) { // ? avoid // ... } function sum (a, b, c) { // ? ok // ... }類中不要定義冗余的屬性。
eslint: no-dupe-class-members
class Dog { bark () {} bark () {} // ? avoid }對(duì)象字面量中不要定義重復(fù)的屬性。
eslint: no-dupe-keys
var user = { name: "Jane Doe", name: "John Doe" // ? avoid }switch 語(yǔ)句中不要定義重復(fù)的 case 分支。
eslint: no-duplicate-case
switch (id) { case 1: // ... case 1: // ? avoid }同一模塊有多個(gè)導(dǎo)入時(shí)一次性寫完。
eslint: no-duplicate-imports
import { myFunc1 } from "module" import { myFunc2 } from "module" // ? avoid import { myFunc1, myFunc2 } from "module" // ? ok正則中不要使用空字符。
eslint: no-empty-character-class
const myRegex = /^abc[]/ // ? avoid const myRegex = /^abc[a-z]/ // ? ok不要解構(gòu)空值。
eslint: no-empty-pattern
const { a: {} } = foo // ? avoid const { a: { b } } = foo // ? ok不要使用 eval()。
eslint: no-eval
eval( "var result = user." + propName ) // ? avoid var result = user[propName] // ? okcatch 中不要對(duì)錯(cuò)誤重新賦值。
eslint: no-ex-assign
try { // ... } catch (e) { e = "new value" // ? avoid } try { // ... } catch (e) { const newVal = "new value" // ? ok }不要擴(kuò)展原生對(duì)象。
eslint: no-extend-native
Object.prototype.age = 21 // ? avoid避免多余的函數(shù)上下文綁定。
eslint: no-extra-bind
const name = function () { getName() }.bind(user) // ? avoid const name = function () { this.getName() }.bind(user) // ? ok避免不必要的布爾轉(zhuǎn)換。
eslint: no-extra-boolean-cast
const result = true if (!!result) { // ? avoid // ... } const result = true if (result) { // ? ok // ... }不要使用多余的括號(hào)包裹函數(shù)。
eslint: no-extra-parens
const myFunc = (function () { }) // ? avoid const myFunc = function () { } // ? okswitch 一定要使用 break 來(lái)將條件分支正常中斷。
eslint: no-fallthrough
switch (filter) { case 1: doSomething() // ? avoid case 2: doSomethingElse() } switch (filter) { case 1: doSomething() break // ? ok case 2: doSomethingElse() } switch (filter) { case 1: doSomething() // fallthrough // ? ok case 2: doSomethingElse() }不要省去小數(shù)點(diǎn)前面的0。
eslint: no-floating-decimal
const discount = .5 // ? avoid const discount = 0.5 // ? ok避免對(duì)聲明過(guò)的函數(shù)重新賦值。
eslint: no-func-assign
function myFunc () { } myFunc = myOtherFunc // ? avoid不要對(duì)全局只讀對(duì)象重新賦值。
eslint: no-global-assign
window = {} // ? avoid注意隱式的 eval()。
eslint: no-implied-eval
setTimeout("alert("Hello world")") // ? avoid setTimeout(function () { alert("Hello world") }) // ? ok嵌套的代碼塊中禁止再定義函數(shù)。
eslint: no-inner-declarations
if (authenticated) { function setAuthUser () {} // ? avoid }不要向 RegExp 構(gòu)造器傳入非法的正則表達(dá)式。
eslint: no-invalid-regexp
RegExp("[a-z") // ? avoid RegExp("[a-z]") // ? ok不要使用非法的空白符。
eslint: no-irregular-whitespace
function myFunc () /**/{} // ? avoid 禁止使用 __iterator__。
eslint: no-iterator
Foo.prototype.__iterator__ = function () {} // ? avoid外部變量不要與對(duì)象屬性重名。
eslint: no-label-var
var score = 100 function game () { score: while (true) { // ? avoid score -= 10 if (score > 0) continue score break } }不要使用標(biāo)簽語(yǔ)句。
eslint: no-labels
label: while (true) { break label // ? avoid }不要書寫不必要的嵌套代碼塊。
eslint: no-lone-blocks
function myFunc () { { // ? avoid myOtherFunc() } } function myFunc () { myOtherFunc() // ? ok }不要混合使用空格與制表符作為縮進(jìn)。
eslint: no-mixed-spaces-and-tabs
除了縮進(jìn),不要使用多個(gè)空格。
eslint: no-multi-spaces
const id = 1234 // ? avoid const id = 1234 // ? ok不要使用多行字符串。
eslint: no-multi-str
const message = "Hello world" // ? avoidnew 創(chuàng)建對(duì)象實(shí)例后需要賦值給變量。
eslint: no-new
new Character() // ? avoid const character = new Character() // ? ok禁止使用 Function 構(gòu)造器。
eslint: no-new-func
var sum = new Function("a", "b", "return a + b") // ? avoid禁止使用 Object 構(gòu)造器。
eslint: no-new-object
let config = new Object() // ? avoid禁止使用 new require。
eslint: no-new-require
const myModule = new require("my-module") // ? avoid禁止使用 Symbol 構(gòu)造器。
eslint: no-new-symbol
const foo = new Symbol("foo") // ? avoid禁止使用原始包裝器。
eslint: no-new-wrappers
const message = new String("hello") // ? avoid不要將全局對(duì)象的屬性作為函數(shù)調(diào)用。
eslint: no-obj-calls
const math = Math() // ? avoid不要使用八進(jìn)制字面量。
eslint: no-octal
const num = 042 // ? avoid const num = "042" // ? ok字符串字面量中也不要使用八進(jìn)制轉(zhuǎn)義字符。
eslint: no-octal-escape
const copyright = "Copyright 251" // ? avoid使用 __dirname 和 __filename 時(shí)盡量避免使用字符串拼接。
eslint: no-path-concat
const pathToFile = __dirname + "/app.js" // ? avoid const pathToFile = path.join(__dirname, "app.js") // ? ok使用 getPrototypeOf 來(lái)替代 __proto__。
eslint: no-proto
const foo = obj.__proto__ // ? avoid const foo = Object.getPrototypeOf(obj) // ? ok不要重復(fù)聲明變量。
eslint: no-redeclare
let name = "John" let name = "Jane" // ? avoid let name = "John" name = "Jane" // ? ok正則中避免使用多個(gè)空格。
eslint: no-regex-spaces
const regexp = /test value/ // ? avoid const regexp = /test {3}value/ // ? ok const regexp = /test value/ // ? okreturn 語(yǔ)句中的賦值必需有括號(hào)包裹。
eslint: no-return-assign
function sum (a, b) { return result = a + b // ? avoid } function sum (a, b) { return (result = a + b) // ? ok }避免將變量賦值給自己。
eslint: no-self-assign
name = name // ? avoid避免將變量與自己進(jìn)行比較操作。
esint: no-self-compare
if (score === score) {} // ? avoid避免使用逗號(hào)操作符。
eslint: no-sequences
if (doSomething(), !!test) {} // ? avoid不要隨意更改關(guān)鍵字的值。
eslint: no-shadow-restricted-names
let undefined = "value" // ? avoid禁止使用稀疏數(shù)組(Sparse arrays)。
eslint: no-sparse-arrays
let fruits = ["apple",, "orange"] // ? avoid不要使用制表符。
eslint: no-tabs
正確使用 ES6 中的字符串模板。
eslint: no-template-curly-in-string
const message = "Hello ${name}" // ? avoid const message = `Hello ${name}` // ? ok使用 this 前請(qǐng)確保 super() 已調(diào)用。
eslint: no-this-before-super
class Dog extends Animal { constructor () { this.legs = 4 // ? avoid super() } }用 throw 拋錯(cuò)時(shí),拋出 Error 對(duì)象而不是字符串。
eslint: no-throw-literal
throw "error" // ? avoid throw new Error("error") // ? ok行末不留空格。
eslint: no-trailing-spaces
不要使用 undefined 來(lái)初始化變量。
eslint: no-undef-init
let name = undefined // ? avoid let name name = "value" // ? ok循環(huán)語(yǔ)句中注意更新循環(huán)變量。
eslint: no-unmodified-loop-condition
for (let i = 0; i < items.length; j++) {...} // ? avoid for (let i = 0; i < items.length; i++) {...} // ? ok如果有更好的實(shí)現(xiàn),盡量不要使用三元表達(dá)式。
eslint: no-unneeded-ternary
let score = val ? val : 0 // ? avoid let score = val || 0 // ? okreturn,throw,continue 和 break 后不要再跟代碼。
eslint: no-unreachable
function doSomething () { return true console.log("never called") // ? avoid }finally 代碼塊中不要再改變程序執(zhí)行流程。
eslint: no-unsafe-finally
try { // ... } catch (e) { // ... } finally { return 42 // ? avoid }關(guān)系運(yùn)算符的左值不要做取反操作。
eslint: no-unsafe-negation
if (!key in obj) {} // ? avoid避免不必要的 .call() 和 .apply()。
eslint: no-useless-call
sum.call(null, 1, 2, 3) // ? avoid避免使用不必要的計(jì)算值作對(duì)象屬性。
eslint: no-useless-computed-key
const user = { ["name"]: "John Doe" } // ? avoid const user = { name: "John Doe" } // ? ok禁止多余的構(gòu)造器。
eslint: no-useless-constructor
class Car { constructor () { // ? avoid } }禁止不必要的轉(zhuǎn)義。
eslint: no-useless-escape
let message = "Hello" // ? avoidimport, export 和解構(gòu)操作中,禁止賦值到同名變量。
eslint: no-useless-rename
import { config as config } from "./config" // ? avoid import { config } from "./config" // ? ok屬性前面不要加空格。
eslint: no-whitespace-before-property
user .name // ? avoid user.name // ? ok禁止使用 with。
eslint: no-with
with (val) {...} // ? avoid對(duì)象屬性換行時(shí)注意統(tǒng)一代碼風(fēng)格。
eslint: object-property-newline
const user = { name: "Jane Doe", age: 30, username: "jdoe86" // ? avoid } const user = { name: "Jane Doe", age: 30, username: "jdoe86" } // ? ok const user = { name: "Jane Doe", age: 30, username: "jdoe86" } // ? ok代碼塊中避免多余留白。
eslint: padded-blocks
if (user) { // ? avoid const name = getName() } if (user) { const name = getName() // ? ok }展開(kāi)運(yùn)算符與它的表達(dá)式間不要留空白。
eslint: rest-spread-spacing
fn(... args) // ? avoid fn(...args) // ? ok遇到分號(hào)時(shí)空格要后留前不留。
eslint: semi-spacing
for (let i = 0 ;i < items.length ;i++) {...} // ? avoid for (let i = 0; i < items.length; i++) {...} // ? ok代碼塊首尾留空格。
eslint: space-before-blocks
if (admin){...} // ? avoid if (admin) {...} // ? ok圓括號(hào)間不留空格。
eslint: space-in-parens
getName( name ) // ? avoid getName(name) // ? ok一元運(yùn)算符后面跟一個(gè)空格。
eslint: space-unary-ops
typeof!admin // ? avoid typeof !admin // ? ok注釋首尾留空格。
eslint: spaced-comment
//comment // ? avoid // comment // ? ok /*comment*/ // ? avoid /* comment */ // ? ok模板字符串中變量前后不加空格。
eslint: template-curly-spacing
const message = `Hello, ${ name }` // ? avoid const message = `Hello, ${name}` // ? ok檢查 NaN 的正確姿勢(shì)是使用 isNaN()。
eslint: use-isnan
if (price === NaN) { } // ? avoid if (isNaN(price)) { } // ? ok用合法的字符串跟 typeof 進(jìn)行比較操作。
eslint: valid-typeof
typeof name === "undefimed" // ? avoid typeof name === "undefined" // ? ok自調(diào)用匿名函數(shù) (IIFEs) 使用括號(hào)包裹。
eslint: wrap-iife
const getName = function () { }() // ? avoid const getName = (function () { }()) // ? ok const getName = (function () { })() // ? okyield 中的 前后都要有空格。
eslint: yield-star-spacing
yield* increment() // ? avoid yield * increment() // ? ok請(qǐng)書寫優(yōu)雅的條件語(yǔ)句(avoid Yoda conditions)。
eslint: yoda
if (42 === age) { } // ? avoid if (age === 42) { } // ? ok關(guān)于分號(hào)
不要使用分號(hào)
。 (參見(jiàn):1,2,3)
eslint: semi
window.alert("hi") // ? ok window.alert("hi"); // ? avoid不要使用 (, [, or ` 等作為一行的開(kāi)始。在沒(méi)有分號(hào)的情況下代碼壓縮后會(huì)導(dǎo)致報(bào)錯(cuò),而堅(jiān)持這一規(guī)范則可避免出錯(cuò)。
eslint: no-unexpected-multiline
// ? ok ;(function () { window.alert("ok") }()) // ? avoid (function () { window.alert("ok") }()) // ? ok ;[1, 2, 3].forEach(bar) // ? avoid [1, 2, 3].forEach(bar) // ? ok ;`hello`.indexOf("o") // ? avoid `hello`.indexOf("o") 備注:上面的寫法只能說(shuō)聰明過(guò)頭了。相比更加可讀易懂的代碼,那些看似投巧的寫法是不可取的。
譬如:
;[1, 2, 3].forEach(bar) 建議的寫法是: var nums = [1, 2, 3] nums.forEach(bar)文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/99900.html
摘要:初始命令初始命令如下生成文件自動(dòng)修復(fù)錯(cuò)誤。第一個(gè)是錯(cuò)誤級(jí)別關(guān)閉規(guī)則將規(guī)則視為一個(gè)警告不會(huì)影響退出碼將規(guī)則視為一個(gè)錯(cuò)誤退出碼為可以從基礎(chǔ)配置中繼承已啟用的規(guī)則。一旦發(fā)現(xiàn)配置文件中有,它就會(huì)停止在父級(jí)目錄中尋找。 1、初始命令 eslint初始命令如下: (1) eslint --init: 生成.eslintrc.js文件(2) eslint src --fix: 自動(dòng)修復(fù)錯(cuò)誤。但是只能...
摘要:使用配置完成,如何使用呢在文件中添加一條代表需要解析的文件格式,最后接上文件路徑,由于我們的主要代碼都在目錄下,這里就配置文件夾。 前言: 本章內(nèi)容,我們?cè)陧?xiàng)目中加入eslint配置,來(lái)審查校驗(yàn)代碼,這樣能夠避免一些比較低級(jí)的錯(cuò)誤。并且在團(tuán)隊(duì)協(xié)作的時(shí)候,保持同一種風(fēng)格和規(guī)范能提高代碼的可讀性,進(jìn)而提高我們的工作效率。 安裝: eslint-config-standard 是一種較為成熟...
摘要:基礎(chǔ)開(kāi)發(fā)插件圖標(biāo)美化調(diào)試代碼格式化代碼格式化代碼規(guī)范語(yǔ)法提示必備及相關(guān)技術(shù)棧語(yǔ)法提示文件高亮格式化編碼支持自動(dòng)閉合標(biāo)簽自動(dòng)更改對(duì)應(yīng)標(biāo)簽名自動(dòng)補(bǔ)全路徑本地項(xiàng)目管理右擊在瀏覽器打開(kāi)文件支持支持友好化配置基礎(chǔ)設(shè)置設(shè)置設(shè)置設(shè)置設(shè)置設(shè)置配 1. vscode基礎(chǔ)開(kāi)發(fā)插件 vscode-icons 圖標(biāo)美化 Debugger for Chrome 調(diào)試 Beautify 代碼格式化 Pretti...
摘要:前言這一篇,我們將接著上篇來(lái)完成配置。開(kāi)發(fā)一配置我們采用的方式來(lái)創(chuàng)建。對(duì)了,前提我們需要全局安裝。三配置創(chuàng)建文件,上配置配置總結(jié)這篇不多,就做了三件事,。下一篇我們將創(chuàng)建項(xiàng)目文件目錄架構(gòu)從零開(kāi)始做前端架構(gòu)項(xiàng)目完整代碼前端架構(gòu)子咻 前言 這一篇,我們將接著上篇來(lái)完成配置eslint、babel、postcss。 開(kāi)發(fā) 一、配置eslint 我們采用eslint --init的方式來(lái)創(chuàng)建e...
摘要:前言這一篇,我們將接著上篇來(lái)完成配置。開(kāi)發(fā)一配置我們采用的方式來(lái)創(chuàng)建。對(duì)了,前提我們需要全局安裝。三配置創(chuàng)建文件,上配置配置總結(jié)這篇不多,就做了三件事,。下一篇我們將創(chuàng)建項(xiàng)目文件目錄架構(gòu)從零開(kāi)始做前端架構(gòu)項(xiàng)目完整代碼前端架構(gòu)子咻 前言 這一篇,我們將接著上篇來(lái)完成配置eslint、babel、postcss。 開(kāi)發(fā) 一、配置eslint 我們采用eslint --init的方式來(lái)創(chuàng)建e...
閱讀 1686·2021-11-15 11:38
閱讀 4543·2021-09-22 15:33
閱讀 2347·2021-08-30 09:46
閱讀 2193·2019-08-30 15:43
閱讀 838·2019-08-30 14:16
閱讀 2086·2019-08-30 13:09
閱讀 1264·2019-08-30 11:25
閱讀 714·2019-08-29 16:42