JS之運算符與表達式


運算符:也叫操作符,是一種符號。通過運算符可以對一個或多個值進行運算,並獲取運算結果。

表達式:由數字、運算符、變量的組合(組成的式子)。

表達式最終都會有一個運算結果,我們將這個結果稱為表達式的返回值。

比如:`+`、`*`、`/`、`(` 都是運算符,而`(3+5)/2`則是表達式。

比如:typeof 就是運算符,可以來獲得一個值的類型。它會將該值的類型以字符串的形式返回,返回值可以是 number string boolean undefined object。

一、運算符

 分類

- 算數運算符

- 自增/自減運算符

- 一元運算符

- 邏輯運算符

- 賦值運算符

- 比較運算符

- 三元運算符(條件運算符)

1、算數運算符

**算術運算符**:用於執行兩個變量或值的算術運算。

常見的算數運算符有以下幾種:

| 運算符 | 描述 |
| :---------------- | :-------: |
| + | 加、字符串連接 |
| - | 減 |
| * | 乘 |
| / | 除 |
| % | 獲取余數(取余、取模) |

**求余的舉例**:

假設用戶輸入345,怎么分別得到3、4、5這三個數呢?

 

得到3的方法:345 除以100,得到3.45然后取整,得到3。即:parseInt(345/100)

得到4的方法:345 除以100,余數是45,除以10,得到4.5,取整。即:parseInt(345 % 100 / 10)

得到5的方法:345 除以10,余數就是5。即:345 % 10

算數運算符的運算規則

(1)先算乘除、后算加減。

(2)小括號`( )`:能夠影響計算順序,且可以嵌套。沒有中括號、沒有大括號,只有小括號。

(3)百分號:取余。只關心余數。

舉例1:(取余)

console.log(3 % 5);

輸出結果為3。

舉例2:(注意運算符的優先級)

var a = 1 + 2 * 3 % 4 / 3;

結果分析:

原式 = 1 + 6 % 4 / 3 = 1 + 2 / 3 = 1.66666666666666

 

浮點數運算的精度問題

浮點數值的最高精度是 17 位小數,但在進行算術計算時,會丟失精度,導致計算不夠准確。比如:

console.log(0.1 + 0.2); // 運算結果不是 0.3,而是 0.30000000000000004

console.log(0.07 * 100); // 運算結果不是 7,而是 7.000000000000001

因此,不要直接判斷兩個浮點數是否相等。

 

2、自增和自減

自增 `++`

自增分成兩種:`a++`和`++a`。

(1)一個變量自增以后,原變量的值會**立即**自增1。也就是說,無論是 `a++` 還是`++a`,都會立即使原變量的值自增1。

(2)**我們要注意的是**:`a`是變量,而`a++`和`++a`是**表達式**。

那這兩種自增,有啥區別呢?區別是:`a++` 和 `++a`的值不同:(也就是說,表達式的值不同)

- `a++`這個表達式的值等於原變量的值(a自增前的值)。你可以這樣理解:先把 a 的值賦值給表達式,然后 a 再自增。

- `++a`這個表達式的值等於新值 (a自增后的值)。 你可以這樣理解:a 先自增,然后再把自增后的值賦值給表達式。

自減 `-- `

原理同上。

開發時,大多使用后置的自增/自減,並且代碼獨占一行,例如:`num++`,或者 `num--`。

### 代碼舉例

```javascript
var n1 = 10;
var n2 = 20;

var result1 = n1++;

console.log(n1); // 11
console.log(result1); // 10

result = ++n1;
console.log(n1); //12
console.log(result); //12

var result2 = n2--;
console.log(n2); // 19
console.log(result2); // 20

result2 = --n2;
console.log(n2); // 18
console.log(result2); // 18
```

3、一元運算符

一元運算符,只需要一個操作數。

常見的一元運算符如下。

typeof

typeof就是典型的一元運算符,因為后面只跟一個操作數。

舉例如下:

```javascript
var a = '123';
console.log(typeof a); // 打印結果:string
```


正號 `+`

(1)正號不會對數字產生任何影響。比如說,`2`和`+2`是一樣的。

(2)我們可以對一個其他的數據類型使用`+`,來將其轉換為number【重要的小技巧】。比如:

```javascript
var a = true;
a = +a; // 注意這行代碼的一元運算符操作
console.log('a:' + a);
console.log(typeof a);

console.log('-----------------');

var b = '18';
b = +b; // 注意這行代碼的一元運算符操作
console.log('b:' + b);
console.log(typeof b);
```

打印結果:

```
a:1
number

-----------------

b:18
number
```

負號 `-`

負號可以對數字進行取反。

 

4、邏輯運算符

邏輯運算符有三個:

- `&&` 與(且):兩個都為真,結果才為真。

- `||` 或:只要有一個是真,結果就是真。

- `!` 非:對一個布爾值進行取反。

連比的寫法:

來看看邏輯運算符連比的寫法。

舉例1:

```javascript
console.log(3 < 2 && 2 < 4);
```

輸出結果為false。

舉例2:(判斷一個人的年齡是否在18~60歲之間)

```javascript
var a = prompt("請輸入您的年齡");
alert(a>=18 && a<= 65);
```


PS:上面的這個`a>=18 && a<= 65`千萬別想當然的寫成` 18<= a <= 65`,沒有這種語法。

注意事項

(1)能參與邏輯運算的,都是布爾值。

(2)JS中的`&&`屬於**短路**的與,如果第一個值為false,則不會看第二個值。舉例:

```javascript
//第一個值為true,會檢查第二個值
true && alert("看我出不出來!!"); // 可以彈出 alert 框

//第一個值為false,不會檢查第二個值
false && alert("看我出不出來!!"); // 不會彈出 alert 框
```

(3)JS中的`||`屬於**短路**的或,如果第一個值為true,則不會看第二個值。舉例:

(4)如果對**非布爾值**進行邏輯運算,則會**先將其轉換為布爾值**,然后再操作。舉例:

```javascript
var a = 10;
a = !a;

console.log(a); // false
console.log(typeof a); // boolean
```

上面的例子,我們可以看到,對非布爾值進行`!`操作之后,返回結果為布爾值。

非布爾值的與或運算【重要】

> 之所以重要,是因為在實際開發中,我們經常用這種代碼做容錯處理或者兜底處理。

非布爾值進行**與或運算**時,會先將其轉換為布爾值,然后再運算,但返回結果是**原值**。比如說:

```javascript
var result = 5 && 6; // 運算過程:true && true;
console.log('result:' + result); // 打印結果:6(也就是說最后面的那個值。)
```

上方代碼可以看到,雖然運算過程為布爾值的運算,但返回結果是原值。

那么,返回結果是哪個原值呢?我們來看一下。

**與運算**的返回結果:(以兩個非布爾值的運算為例)

- 如果第一個值為false,則直接返回第一個值;不會再往后執行。

- 如果第一個值為true,則返回第二個值(如果所有的值都為true,則返回的是最后一個值)。


**或運算**的返回結果:(以兩個非布爾值的運算為例)

- 如果第一個值為true,則直接返回第一個值;不會再往后執行。

- 如果第一個值為false,則返回第二個值((如果所有的值都為false,則返回的是最后一個值)。


實際開發中,我們經常是這樣來做「容錯處理」的:

當成功調用一個接口后,返回的數據為 result 對象。這個時候,我們用變量 a 來接收 result 里的圖片資源。通常的寫法是這樣的:


```javascript
if (result.resultCode == 0) {
var a = result && result.data && result.data.imgUrl || 'http://img.smyhvae.com/20160401_01.jpg';
}
```

上方代碼的意思是,獲取返回結果中的`result.data.imgUrl`這個圖片資源;如果返回結果中沒有 `result.data.imgUrl` 這個字段,就用 `http://img.smyhvae.com/20160401_01.jpg` 作為**兜底**圖片。這種寫法,在實際開發中經常用到。

 

5、賦值運算符

可以將符號右側的值賦值給符號左側的變量。

舉例:

- `=` 直接賦值。比如 `var a = 5`

- `+=`。a += 5 等價於 a = a + 5

- `-=`。a -= 5 等價於 a = a - 5

- `*=`。a *= 5 等價於 a = a * 5

- `/=`。a /= 5 等價於 a = a / 5

- `%=`。a %= 5 等價於 a = a % 5

 

6、比較運算符

比較運算符可以比較兩個值之間的大小關系,如果關系成立它會返回true,如果關系不成立則返回false。

比較運算符有很多種,比如:

```
> 大於號
< 小於號
>= 大於或等於
<= 小於或等於
== 等於
=== 全等於
!= 不等於
!== 不全等於
```

**比較運算符,得到的結果都是布爾值:要么是true,要么是false**。

舉例如下:

```javascript
var result = 5 > 10; // false
```

非數值的比較

(1)對於非數值進行比較時,會將其轉換為數字然后再比較。

舉例如下:

```javascript
console.log(1 > true); //false
console.log(1 >= true); //true
console.log(1 > "0"); //true

//console.log(10 > null); //true

//任何值和NaN做任何比較都是false

console.log(10 <= "hello"); //false
console.log(true > false); //true

```

(2)特殊情況:如果符號兩側的值都是字符串時,**不會**將其轉換為數字進行比較。比較兩個字符串時,比較的是字符串的**Unicode編碼**。【非常重要,這里是個大坑,很容易踩到】

比較字符編碼時,是一位一位進行比較。如果兩位一樣,則比較下一位。

比如說,當你嘗試去比較`"123"`和`"56"`這兩個字符串時,你會發現,字符串"56"竟然比字符串"123"要大。也就是說,下面這樣代碼的打印結果,其實是true:(這個我們一定要注意,在日常開發中,很容易忽視)

```javascript
// 比較兩個字符串時,比較的是字符串的字符編碼,所以可能會得到不可預期的結果
console.log("56" > "123"); // true
```

**因此**:當我們在比較兩個字符串型的數字時,**一定一定要先轉型**再比較大小,比如 `parseInt()`。

(3)任何值和NaN做任何比較都是false。

`==`符號的強調

注意`==`這個符號,它是**判斷是否等於**,而不是賦值。

(1)`== `這個符號,還可以驗證字符串是否相同。例如:

```javascript
console.log("我愛你中國" == "我愛你中國"); // 輸出結果為true
```

(2)`== `這個符號並不嚴謹,會做隱式轉換,將不同的數據類型,**轉為相同類型**進行比較(大部分情況下,都是轉換為數字)。例如:

```javascript
console.log("6" == 6); // 打印結果:true。這里的字符串"6"會先轉換為數字6,然后再進行比較
console.log(true == "1"); // 打印結果:true
console.log(0 == -0); // 打印結果:true

console.log(null == 0); // 打印結果:false
```

(3)undefined 衍生自 null,所以這兩個值做相等判斷時,會返回true。

```javascript
console.log(undefined == null); //打印結果:true。
```

(4)NaN不和任何值相等,包括他本身。

```javascript
console.log(NaN == NaN); //false
console.log(NaN === NaN); //false
```

問題:那如果我想判斷 b的值是否為NaN,該怎么辦呢?

答案:可以通過isNaN()函數來判斷一個值是否是NaN。舉例:

```javascript
console.log(isNaN(b));
```

如上方代碼所示,如果 b 為 NaN,則返回true;否則返回false。

`===`全等符號的強調

**全等在比較時,不會做類型轉換**。如果要保證**絕對等於(完全等於)**,我們就要用三個等號`===`。例如:

```javascript
console.log("6" === 6); //false
console.log(6 === 6); //true
```

上述內容分析出:

- `==`兩個等號,不嚴謹,"6"和6是true。

- `===`三個等號,嚴謹,"6"和6是false。

另外還有:**`==`的反面是`!=`,`===`的反面是`!==`**。例如:

```javascript
console.log(3 != 8); //true
console.log(3 != "3"); //false,因為3=="3"是true,所以反過來就是false。
console.log(3 !== "3"); //true,應為3==="3"是false,所以反過來是true。
```

7、三元運算符

三元運算符也叫條件運算符。

語法:

```
條件表達式 ? 語句1 : 語句2;
```

**執行的流程**:

條件運算符在執行時,首先對條件表達式進行求值:

- 如果該值為true,則執行語句1,並返回執行結果

- 如果該值為false,則執行語句2,並返回執行結果

如果條件的表達式的求值結果是一個非布爾值,會將其轉換為布爾值然后再運算。

 

二、運算符的優先級

運算符的優先級如下:(優先級從高到低)

- `.`、`[]`、`new`

- `()`

- `++`、`--`

- `!`、`~`、`+`(單目)、`-`(單目)、`typeof`、`void`、`delete`

- `%`、`*`、`/`

- `+`(雙目)、`-`(雙目)

- `<<`、`>>`、`>>>`

- 關系運算符:`<`、`<=`、`>`、`>=`

- `==`、`!==`、`===`、`!==`

- `&`

- `^`

- `|`

- `&&`

- `||`

- `?:`

- `=`、`+=`、`-=`、`*=`、`/=`、`%=`、`<<=`、`>>=`、`>>>=`、`&=`、`^=`、`|=`

- `,`

注意:邏輯與 `&&` 比邏輯或 `||` 的優先級更高。

備注:你在實際寫代碼的時候,如果不清楚哪個優先級更高,可以把括號運用上。

三、Unicode 編碼

引申Unicode編碼的使用。

1、在字符串中可以使用轉義字符輸入Unicode編碼。格式如下:

```
\u四位編碼
```

舉例如下:

```javascript
console.log("\u2600"); // 這里的 2600 采用的是16進制
console.log("\u2602"); // 這里的 2602 采用的是16進制。
```

打印結果:

 

 

2、我們還可以在 HTML 網頁中使用Unicode編碼。格式如下:

```
&#四位編碼;
```

PS:我們知道,Unicode編碼采用的是16進制,但是,這里的編碼需要使用10進制。

舉例如下:

```html
<h1 style="font-size: 100px;">&#9860;</h1>

```

效果:

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM