# Swift 运算符的优先级和关联性

> 原文： [https://www.programiz.com/swift-programming/operator-precedence-associativity](https://www.programiz.com/swift-programming/operator-precedence-associativity)

#### 在本文中，您将了解用于计算带有运算符和操作数的表达式的规则。

## Swift 运算符优先级

运算符优先级是用于求值给定数学表达式的规则的集合。 当在单个表达式中使用多个运算符时，将按称为运算符优先级的特定顺序求值每个部分。 某些运算符的优先级高于其他运算符，这会影响表达式的求值方式。

* * *

### 运算符优先级表

下表列出了中[运算符的优先级。 它在表格中显示的越高，其优先级越高。](/swift-programming/operators "Swift operators")

Swift Standard Library Precedence Groups (Highest to Lowest)

| 运营商集团 | 例子 |
| --- | --- |
| 按位移位优先 | > > & < < & > > > > |
| 乘法优先级 | & *％& * / |
| 加法优先级 | &#124; & + &-+-^ |
| 范围形成优先 | .. < ... |
| 投放优先 | 就像 |
| 无推论优先 | ?? |
| 比较优先级 | ！= > < > = < = === == |
| 逻辑合取优先 | & & |
| 逻辑析取优先级 | &#124;&#124; |
| 默认优先级 | 〜> |
| 三元优先 | ?: |
| 功能箭头优先 | ( ) |
| 分配优先级 | &#124; =％= / = & < < = & > > = & = * = > > = < < = ^ = + = -= |

* * *

### 示例 1：Swift 运算符优先级

```swift
let x = 4 + 5 * 5
print(x) 
```

当您运行上述程序时，输出将是：

```swift
29
```

在上面的示例中，如果从左到右读取表达式，则可能期望输出为 45。但是，乘法运算符的优先级高于加法运算符，因此表达式`4 + 5 * 5`的求值为`4 + (5 * 5)`。 因此，`print(x)`在屏幕上输出 29。

Execution Steps

| 步骤 | 运算符 | 表达 | 表达式返回的值 |
| --- | --- | --- | --- |
| 1 | `*` | `5 * 5` | **25** |
| 2 | `+` | `4 + 25` | **29** |
| 3 | `=` | `print(x)` | **29** |

* * *

### 示例 2：具有复杂赋值运算符的 Swift 运算符优先级

```swift
var y = 15
y += 10 - 2 * 3
print(y) 
```

运行该程序时，输出为：

```swift
19
```

在上面的示例中，表达式`var y = 15`在变量`y`中分配值 15。

在下一个表达式`y += 10 - 2 * 3`中，乘法运算符的优先级高于减法&复合赋值运算符（`+=`）。

因此，表达式`y += 10 - 2 * 3`被求值为`y = y + (10 - (2 * 3))`。

Execution Steps

| 脚步 | 运算符 | 表达 | 表达式返回的值 |
| 1 | = | var y = 15 | **15** |
| 2 | * | 2 * 3 | **6** |
| 3 | - | 10 - 6 | **4** |
| 4 | += | 15 + 4 | **19** |

* * *

## Swift 运算符关联

尽管存在由运算符优先级定义的预定义规则来求值表达式，但是您可能想知道如果存在多个相同优先级的运算符会发生什么。 运算符关联性定义了如何将具有相同优先级的运算符组合在一起。

在 Swift 中，运算符可以是左侧关联，右侧关联或没有关联性。 在表达式中按顺序使用时，左关联的运算符将从语句的左侧开始对其操作数进行分组，右起的右关联运算符以及没有关联性的运算符没有定义的行为。

* * *

### 运算符关联表

下表显示了 Swift 运算符的关联性及其优先级。

Swift Standard Library Associativity (Precedence Highest to Lowest)

| Operator Groups | Examples | 关联性 |
| --- | --- | --- |
| Bitwise shift precedence | >> &<< &>> >> | 没有 |
| Multiplication precedence | &* % & * / | 剩下 |
| Addition precedence | &#124; &+ &- + -  ^ | left |
| Range Formation Precedence | ..< ... | none |
| Casting Precedence | is as | none |
| Nil-Coalescing Precedence | ?? | 对 |
| Comparison Precedence | != > < >= <= === == | none |
| Logical Conjunction Precedence | && | left |
| Logical Disjunction Precedence | &#124;&#124; | left |
| Default Precedence | ~> | none |
| Ternary Precedence | ?: | right |
| Function Arrow precedence | ( ) | right |
| Assignment Precedence | &#124; =％= / = & < < = & > > = & = * = > > = < < = ^ = | right |

* * *

### 示例 3：Swift 运算符关联

```swift
let x =  40  / 2 * 10
print(x) 
```

运行该程序时，输出为：

```swift
200
```

在上面的程序中，表达式是从左到右计算的，因为运算符属于乘法优先级组，并且具有左关联性。 因此，除法运算较早进行，您会得到结果 **200** 。 如果要先执行乘法怎么办？ 您需要将`2 * 10`表达式包装为（）大括号，如下所示：

```swift
let x =  40  / (2 * 10)
print(x) 
```

运行该程序时，输出为：

```swift
2
```

您无需记住优先级和关联表。 在大多数情况下，运算符的优先级和关联性本身就是有意义的。 如有疑问，您可以随时使用该表作为参考。 另外，最好使用括号使代码更易于理解。