> For the complete documentation index, see [llms.txt](https://swift.unicorndonkeys.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://swift.unicorndonkeys.com/guida-al-linguaggio/operatori-di-base.md).

# Operatori di base (Basic Operators)

Esegui operazioni come assegnamento, aritmetica e confronto.

Un *operatore* è un simbolo o un'espressione speciale che usi per verificare, modificare o combinare valori. Per esempio, l'operatore di addizione (`+`) somma due numeri, come in `let i = 1 + 2`, e l'operatore logico AND (`&&`) combina due valori booleani, come in `if enteredDoorCode && passedRetinaScan`.

Swift supporta gli operatori che potresti già conoscere da linguaggi come il C, e ne migliora diverse capacità per eliminare errori di programmazione comuni. L'operatore di assegnamento (`=`) non restituisce un valore, per evitare che venga usato per errore quando si intende usare l'operatore di uguaglianza (`==`). Gli operatori aritmetici (`+`, `-`, `*`, `/`, `%` e così via) rilevano e non consentono l'overflow dei valori, per evitare risultati inattesi quando si lavora con numeri che diventano più grandi o più piccoli dell'intervallo di valori consentito dal tipo che li memorizza. Puoi scegliere di abilitare il comportamento di overflow dei valori usando gli operatori di overflow di Swift, come descritto in [Operatori di overflow](/guida-al-linguaggio/operatori-avanzati.md#operatori-di-overflow).

Swift fornisce anche operatori di intervallo che non si trovano in C, come `a..<b` e `a...b`, come scorciatoia per esprimere un intervallo di valori.

Questo capitolo descrive gli operatori comuni in Swift. [Operatori avanzati](/guida-al-linguaggio/operatori-avanzati.md) tratta gli operatori avanzati di Swift, e descrive come definire i tuoi operatori personalizzati e implementare gli operatori standard per i tuoi tipi personalizzati.

## Terminologia <a href="#terminologia" id="terminologia"></a>

Gli operatori sono unari, binari o ternari:

* Gli operatori *unari* operano su un singolo operando (come `-a`). Gli operatori unari *prefissi* compaiono immediatamente prima del loro operando (come `!b`), e gli operatori unari *postfissi* compaiono immediatamente dopo il loro operando (come `c!`).
* Gli operatori *binari* operano su due operandi (come `2 + 3`) e sono *infissi* perché compaiono tra i loro due operandi.
* Gli operatori *ternari* operano su tre operandi. Come il C, Swift ha un solo operatore ternario, l'operatore condizionale ternario (`a ? b : c`).

I valori su cui agiscono gli operatori sono gli *operandi*. Nell'espressione `1 + 2`, il simbolo `+` è un operatore infisso e i suoi due operandi sono i valori `1` e `2`.

## Operatore di assegnamento <a href="#operatore-di-assegnamento" id="operatore-di-assegnamento"></a>

L'*operatore di assegnamento* (`a = b`) inizializza o aggiorna il valore di `a` con il valore di `b`:

```swift
let b = 10
var a = 5
a = b
// a ora è uguale a 10
```

Se il lato destro dell'assegnamento è una tupla con più valori, i suoi elementi possono essere scomposti in più costanti o variabili contemporaneamente:

```swift
let (x, y) = (1, 2)
// x è uguale a 1, e y è uguale a 2
```

A differenza dell'operatore di assegnamento in C e Objective-C, l'operatore di assegnamento in Swift non restituisce di per sé un valore. L'istruzione seguente non è valida:

```swift
if x = y {
    // Questo non è valido, perché x = y non restituisce un valore.
}
```

Questa caratteristica impedisce che l'operatore di assegnamento (`=`) venga usato per sbaglio quando in realtà si intende usare l'operatore di uguaglianza (`==`). Rendendo non valido `if x = y`, Swift ti aiuta a evitare questo tipo di errori nel tuo codice.

## Operatori aritmetici <a href="#operatori-aritmetici" id="operatori-aritmetici"></a>

Swift supporta i quattro *operatori aritmetici* standard per tutti i tipi numerici:

* Addizione (`+`)
* Sottrazione (`-`)
* Moltiplicazione (`*`)
* Divisione (`/`)

```swift
1 + 2       // è uguale a 3
5 - 3       // è uguale a 2
2 * 3       // è uguale a 6
10.0 / 2.5  // è uguale a 4.0
```

A differenza degli operatori aritmetici in C e Objective-C, gli operatori aritmetici di Swift per impostazione predefinita non consentono l'overflow dei valori. Puoi scegliere di abilitare il comportamento di overflow dei valori usando gli operatori di overflow di Swift (come `a &+ b`). Vedi [Operatori di overflow](/guida-al-linguaggio/operatori-avanzati.md#operatori-di-overflow).

L'operatore di addizione è supportato anche per la concatenazione di `String`:

```swift
"hello, " + "world"  // è uguale a "hello, world"
```

### Operatore di resto <a href="#operatore-di-resto" id="operatore-di-resto"></a>

L'*operatore di resto* (`a % b`) calcola quanti multipli di `b` stanno dentro `a` e restituisce il valore che avanza (noto come *resto*).

{% hint style="info" %}
**Nota:** L'operatore di resto (`%`) è noto anche come *operatore modulo* in altri linguaggi. Tuttavia, il suo comportamento in Swift con i numeri negativi fa sì che, a rigor di termini, si tratti di un'operazione di resto piuttosto che di modulo.
{% endhint %}

Ecco come funziona l'operatore di resto. Per calcolare `9 % 4`, per prima cosa calcoli quanti `4` stanno dentro `9`:

![](https://3581893755-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FNzatREGwodw9Z93LQYJb%2Fuploads%2F4fLSV1PlgOFirA6qoOTd%2FremainderInteger%402x.png?alt=media)

Dentro `9` stanno due `4`, e il resto è `1` (mostrato in arancione).

In Swift, questo si scriverebbe così:

```swift
9 % 4    // è uguale a 1
```

Per determinare il risultato di `a % b`, l'operatore `%` calcola l'equazione seguente e restituisce `remainder` come output:

`a` = (`b` x `some multiplier`) + `remainder`

dove `some multiplier` è il numero più grande di multipli di `b` che stanno dentro `a`.

Inserendo `9` e `4` in questa equazione si ottiene:

`9` = (`4` x `2`) + `1`

Lo stesso metodo si applica quando si calcola il resto per un valore negativo di `a`:

```swift
-9 % 4   // è uguale a -1
```

Inserendo `-9` e `4` nell'equazione si ottiene:

`-9` = (`4` x `-2`) + `-1`

che dà un valore del resto pari a `-1`.

Il segno di `b` viene ignorato per i valori negativi di `b`. Ciò significa che `a % b` e `a % -b` danno sempre lo stesso risultato.

### Operatore meno unario <a href="#operatore-meno-unario" id="operatore-meno-unario"></a>

Il segno di un valore numerico può essere invertito usando un `-` prefisso, noto come *operatore meno unario*:

```swift
let three = 3
let minusThree = -three       // minusThree è uguale a -3
let plusThree = -minusThree   // plusThree è uguale a 3, ovvero "meno meno tre"
```

L'operatore meno unario (`-`) va anteposto direttamente al valore su cui opera, senza alcuno spazio.

### Operatore più unario <a href="#operatore-piu-unario" id="operatore-piu-unario"></a>

L'*operatore più unario* (`+`) restituisce semplicemente il valore su cui opera, senza alcuna modifica:

```swift
let minusSix = -6
let alsoMinusSix = +minusSix  // alsoMinusSix è uguale a -6
```

Sebbene l'operatore più unario non faccia effettivamente nulla, puoi usarlo per dare simmetria al tuo codice per i numeri positivi quando usi anche l'operatore meno unario per i numeri negativi.

## Operatori di assegnamento composti <a href="#operatori-di-assegnamento-composti" id="operatori-di-assegnamento-composti"></a>

Come il C, Swift fornisce *operatori di assegnamento composti* che combinano l'assegnamento (`=`) con un'altra operazione. Un esempio è l'*operatore di assegnamento con addizione* (`+=`):

```swift
var a = 1
a += 2
// a ora è uguale a 3
```

L'espressione `a += 2` è una forma abbreviata di `a = a + 2`. Di fatto, l'addizione e l'assegnamento sono combinati in un unico operatore che esegue entrambe le operazioni contemporaneamente.

{% hint style="info" %}
**Nota:** Gli operatori di assegnamento composti non restituiscono un valore. Per esempio, non puoi scrivere `let b = a += 2`.
{% endhint %}

Per informazioni sugli operatori forniti dalla libreria standard di Swift, vedi [Operator Declarations](https://developer.apple.com/documentation/swift/operator_declarations).

## Operatori di confronto <a href="#operatori-di-confronto" id="operatori-di-confronto"></a>

Swift supporta i seguenti operatori di confronto:

* Uguale a (`a == b`)
* Diverso da (`a != b`)
* Maggiore di (`a > b`)
* Minore di (`a < b`)
* Maggiore o uguale a (`a >= b`)
* Minore o uguale a (`a <= b`)

{% hint style="info" %}
**Nota:** Swift fornisce anche due *operatori di identità* (`===` e `!==`), che usi per verificare se due riferimenti a oggetti si riferiscono entrambi alla stessa istanza di oggetto. Per maggiori informazioni, vedi [Operatori di identità](/guida-al-linguaggio/strutture-e-classi.md#operatori-di-identita).
{% endhint %}

Ciascuno degli operatori di confronto restituisce un valore `Bool` per indicare se l'affermazione è vera o meno:

```swift
1 == 1   // true perché 1 è uguale a 1
2 != 1   // true perché 2 non è uguale a 1
2 > 1    // true perché 2 è maggiore di 1
1 < 2    // true perché 1 è minore di 2
1 >= 1   // true perché 1 è maggiore o uguale a 1
2 <= 1   // false perché 2 non è minore o uguale a 1
```

Gli operatori di confronto sono spesso usati nelle istruzioni condizionali, come l'istruzione `if`:

```swift
let name = "world"
if name == "world" {
    print("hello, world")
} else {
    print("I'm sorry \(name), but I don't recognize you")
}
// Stampa "hello, world", perché name è effettivamente uguale a "world".
```

Per saperne di più sull'istruzione `if`, vedi [Flusso di controllo](/guida-al-linguaggio/flusso-di-controllo.md).

Puoi confrontare due tuple se hanno lo stesso tipo e lo stesso numero di valori. Le tuple vengono confrontate da sinistra a destra, un valore alla volta, finché il confronto non trova due valori che non sono uguali. Quei due valori vengono confrontati, e il risultato di quel confronto determina il risultato complessivo del confronto tra tuple. Se tutti gli elementi sono uguali, allora le tuple stesse sono uguali. Per esempio:

```swift
(1, "zebra") < (2, "apple")   // true perché 1 è minore di 2; "zebra" e "apple" non vengono confrontati
(3, "apple") < (3, "bird")    // true perché 3 è uguale a 3, e "apple" è minore di "bird"
(4, "dog") == (4, "dog")      // true perché 4 è uguale a 4, e "dog" è uguale a "dog"
```

Nell'esempio qui sopra, puoi vedere il comportamento di confronto da sinistra a destra nella prima riga. Poiché `1` è minore di `2`, `(1, "zebra")` è considerata minore di `(2, "apple")`, indipendentemente da qualsiasi altro valore nelle tuple. Non importa che `"zebra"` non sia minore di `"apple"`, perché il confronto è già determinato dai primi elementi delle tuple. Tuttavia, quando i primi elementi delle tuple sono uguali, i loro secondi elementi *vengono* confrontati — questo è ciò che accade nella seconda e nella terza riga.

Le tuple possono essere confrontate con un dato operatore solo se l'operatore può essere applicato a ciascun valore delle rispettive tuple. Per esempio, come dimostrato nel codice seguente, puoi confrontare due tuple di tipo `(String, Int)` perché sia i valori `String` sia i valori `Int` possono essere confrontati usando l'operatore `<`. Al contrario, due tuple di tipo `(String, Bool)` non possono essere confrontate con l'operatore `<` perché l'operatore `<` non può essere applicato ai valori `Bool`.

```swift
("blue", -1) < ("purple", 1)        // OK: restituisce true.
("blue", false) < ("purple", true)  // Errore: non si può usare < per confrontare valori booleani.
```

{% hint style="info" %}
**Nota:** La libreria standard di Swift include operatori di confronto tra tuple per le tuple con meno di sette elementi. Per confrontare tuple con sette o più elementi, devi implementare personalmente gli operatori di confronto.
{% endhint %}

## Operatore condizionale ternario <a href="#operatore-condizionale-ternario" id="operatore-condizionale-ternario"></a>

L'*operatore condizionale ternario* è un operatore speciale composto da tre parti, che ha la forma `question ? answer1 : answer2`. È una scorciatoia per valutare una tra due espressioni a seconda che `question` sia vera o falsa. Se `question` è vera, valuta `answer1` e ne restituisce il valore; altrimenti, valuta `answer2` e ne restituisce il valore.

L'operatore condizionale ternario è una forma abbreviata del codice seguente:

```swift
if question {
    answer1
} else {
    answer2
}
```

Ecco un esempio, che calcola l'altezza della riga di una tabella. L'altezza della riga deve essere di 50 punti superiore all'altezza del contenuto se la riga ha un'intestazione, e di 20 punti superiore se la riga non ha un'intestazione:

```swift
let contentHeight = 40
let hasHeader = true
let rowHeight = contentHeight + (hasHeader ? 50 : 20)
// rowHeight è uguale a 90
```

L'esempio qui sopra è una forma abbreviata del codice seguente:

```swift
let contentHeight = 40
let hasHeader = true
let rowHeight: Int
if hasHeader {
    rowHeight = contentHeight + 50
} else {
    rowHeight = contentHeight + 20
}
// rowHeight è uguale a 90
```

L'uso dell'operatore condizionale ternario nel primo esempio fa sì che `rowHeight` possa essere impostata al valore corretto con una sola riga di codice, il che è più conciso del codice usato nel secondo esempio.

L'operatore condizionale ternario fornisce una forma abbreviata efficiente per decidere quale tra due espressioni considerare. Usa tuttavia l'operatore condizionale ternario con cautela. La sua concisione può portare a codice difficile da leggere se se ne abusa. Evita di combinare più istanze dell'operatore condizionale ternario in un'unica istruzione composta.

## Operatore di nil-coalescing <a href="#operatore-di-nil-coalescing" id="operatore-di-nil-coalescing"></a>

L'*operatore di nil-coalescing* (`a ?? b`) fa l'unwrapping di un opzionale `a` se contiene un valore, oppure restituisce un valore predefinito `b` se `a` è `nil`. L'espressione `a` è sempre di un tipo opzionale. L'espressione `b` deve corrispondere al tipo memorizzato all'interno di `a`.

L'operatore di nil-coalescing è una forma abbreviata del codice seguente:

```swift
a != nil ? a! : b
```

Il codice qui sopra usa l'operatore condizionale ternario e l'unwrapping forzato (`a!`) per accedere al valore racchiuso in `a` quando `a` non è `nil`, e per restituire `b` in caso contrario. L'operatore di nil-coalescing fornisce un modo più elegante di incapsulare questo controllo condizionale e questo unwrapping in una forma concisa e leggibile.

{% hint style="info" %}
**Nota:** Se il valore di `a` è diverso da `nil`, il valore di `b` non viene valutato. Questo è noto come *valutazione a corto circuito*.
{% endhint %}

L'esempio seguente usa l'operatore di nil-coalescing per scegliere tra un nome di colore predefinito e un nome di colore opzionale definito dall'utente:

```swift
let defaultColorName = "red"
var userDefinedColorName: String?   // il valore predefinito è nil

var colorNameToUse = userDefinedColorName ?? defaultColorName
// userDefinedColorName è nil, quindi colorNameToUse viene impostata al valore predefinito "red"
```

La variabile `userDefinedColorName` è definita come `String` opzionale, con un valore predefinito di `nil`. Poiché `userDefinedColorName` è di un tipo opzionale, puoi usare l'operatore di nil-coalescing per considerarne il valore. Nell'esempio qui sopra, l'operatore viene usato per determinare un valore iniziale per una variabile `String` chiamata `colorNameToUse`. Poiché `userDefinedColorName` è `nil`, l'espressione `userDefinedColorName ?? defaultColorName` restituisce il valore di `defaultColorName`, ovvero `"red"`.

Se assegni un valore diverso da `nil` a `userDefinedColorName` ed esegui di nuovo il controllo con l'operatore di nil-coalescing, viene usato il valore racchiuso in `userDefinedColorName` invece di quello predefinito:

```swift
userDefinedColorName = "green"
colorNameToUse = userDefinedColorName ?? defaultColorName
// userDefinedColorName non è nil, quindi colorNameToUse viene impostata a "green"
```

## Operatori di intervallo <a href="#operatori-di-intervallo" id="operatori-di-intervallo"></a>

Swift include diversi *operatori di intervallo*, che sono scorciatoie per esprimere un intervallo di valori.

### Operatore di intervallo chiuso <a href="#operatore-di-intervallo-chiuso" id="operatore-di-intervallo-chiuso"></a>

L'*operatore di intervallo chiuso* (`a...b`) definisce un intervallo che va da `a` a `b`, e include i valori `a` e `b`. Il valore di `a` non deve essere maggiore di `b`.

L'operatore di intervallo chiuso è utile quando iteri su un intervallo in cui vuoi usare tutti i valori, come con un ciclo `for`-`in`:

```swift
for index in 1...5 {
    print("\(index) times 5 is \(index * 5)")
}
// 1 times 5 is 5
// 2 times 5 is 10
// 3 times 5 is 15
// 4 times 5 is 20
// 5 times 5 is 25
```

Per saperne di più sui cicli `for`-`in`, vedi [Flusso di controllo](/guida-al-linguaggio/flusso-di-controllo.md).

### Operatore di intervallo semiaperto <a href="#operatore-di-intervallo-semiaperto" id="operatore-di-intervallo-semiaperto"></a>

L'*operatore di intervallo semiaperto* (`a..<b`) definisce un intervallo che va da `a` a `b`, ma non include `b`. Si dice *semiaperto* perché contiene il suo primo valore, ma non il suo valore finale. Come per l'operatore di intervallo chiuso, il valore di `a` non deve essere maggiore di `b`. Se il valore di `a` è uguale a `b`, allora l'intervallo risultante sarà vuoto.

Gli intervalli semiaperti sono particolarmente utili quando lavori con elenchi a base zero come gli array, in cui è utile contare fino alla lunghezza dell'elenco (esclusa):

```swift
let names = ["Anna", "Alex", "Brian", "Jack"]
let count = names.count
for i in 0..<count {
    print("Person \(i + 1) is called \(names[i])")
}
// Person 1 is called Anna
// Person 2 is called Alex
// Person 3 is called Brian
// Person 4 is called Jack
```

Nota che l'array contiene quattro elementi, ma `0..<count` conta solo fino a `3` (l'indice dell'ultimo elemento dell'array), perché è un intervallo semiaperto. Per saperne di più sugli array, vedi [Array](/guida-al-linguaggio/tipi-collezione.md#array).

### Intervalli unilaterali <a href="#intervalli-unilaterali" id="intervalli-unilaterali"></a>

L'operatore di intervallo chiuso ha una forma alternativa per gli intervalli che proseguono il più possibile in una direzione — per esempio, un intervallo che include tutti gli elementi di un array dall'indice 2 alla fine dell'array. In questi casi, puoi omettere il valore da un lato dell'operatore di intervallo. Questo tipo di intervallo è chiamato *intervallo unilaterale* perché l'operatore ha un valore su un solo lato. Per esempio:

```swift
for name in names[2...] {
    print(name)
}
// Brian
// Jack

for name in names[...2] {
    print(name)
}
// Anna
// Alex
// Brian
```

Anche l'operatore di intervallo semiaperto ha una forma unilaterale che si scrive con il solo valore finale. Proprio come quando includi un valore su entrambi i lati, il valore finale non fa parte dell'intervallo. Per esempio:

```swift
for name in names[..<2] {
    print(name)
}
// Anna
// Alex
```

Gli intervalli unilaterali possono essere usati in altri contesti, non solo nei subscript. Non puoi iterare su un intervallo unilaterale che omette il primo valore, perché non è chiaro da dove debba iniziare l'iterazione. *Puoi* iterare su un intervallo unilaterale che omette il valore finale; tuttavia, poiché l'intervallo prosegue indefinitamente, assicurati di aggiungere una condizione di terminazione esplicita per il ciclo. Puoi anche verificare se un intervallo unilaterale contiene un particolare valore, come mostrato nel codice seguente.

```swift
let range = ...5
range.contains(7)   // false
range.contains(4)   // true
range.contains(-1)  // true
```

## Operatori logici <a href="#operatori-logici" id="operatori-logici"></a>

Gli *operatori logici* modificano o combinano i valori logici booleani `true` e `false`. Swift supporta i tre operatori logici standard presenti nei linguaggi derivati dal C:

* NOT logico (`!a`)
* AND logico (`a && b`)
* OR logico (`a || b`)

### Operatore NOT logico <a href="#operatore-not-logico" id="operatore-not-logico"></a>

L'*operatore NOT logico* (`!a`) inverte un valore booleano in modo che `true` diventi `false`, e `false` diventi `true`.

L'operatore NOT logico è un operatore prefisso, e compare immediatamente prima del valore su cui opera, senza alcuno spazio. Può essere letto come “non `a`”, come si vede nell'esempio seguente:

```swift
let allowedEntry = false
if !allowedEntry {
    print("ACCESS DENIED")
}
// Stampa "ACCESS DENIED".
```

L'espressione `if !allowedEntry` può essere letta come “se l'ingresso non è consentito”. La riga successiva viene eseguita solo se “ingresso non consentito” è vero; cioè, se `allowedEntry` è `false`.

Come in questo esempio, una scelta accurata dei nomi delle costanti e delle variabili booleane può aiutare a mantenere il codice leggibile e conciso, evitando doppie negazioni o affermazioni logiche confuse.

### Operatore AND logico <a href="#operatore-and-logico" id="operatore-and-logico"></a>

L'*operatore AND logico* (`a && b`) crea espressioni logiche in cui entrambi i valori devono essere `true` affinché anche l'espressione complessiva sia `true`.

Se uno dei due valori è `false`, anche l'espressione complessiva sarà `false`. Infatti, se il *primo* valore è `false`, il secondo valore non verrà nemmeno valutato, perché non può in alcun modo rendere l'espressione complessiva uguale a `true`. Questo è noto come *valutazione a corto circuito*.

Questo esempio considera due valori `Bool` e consente l'accesso solo se entrambi i valori sono `true`:

```swift
let enteredDoorCode = true
let passedRetinaScan = false
if enteredDoorCode && passedRetinaScan {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Stampa "ACCESS DENIED".
```

### Operatore OR logico <a href="#operatore-or-logico" id="operatore-or-logico"></a>

L'*operatore OR logico* (`a || b`) è un operatore infisso composto da due caratteri barra verticale adiacenti. Lo usi per creare espressioni logiche in cui solo *uno* dei due valori deve essere `true` affinché l'espressione complessiva sia `true`.

Come l'operatore AND logico visto sopra, l'operatore OR logico usa la valutazione a corto circuito per considerare le sue espressioni. Se il lato sinistro di un'espressione OR logica è `true`, il lato destro non viene valutato, perché non può cambiare il risultato dell'espressione complessiva.

Nell'esempio seguente, il primo valore `Bool` (`hasDoorKey`) è `false`, ma il secondo valore (`knowsOverridePassword`) è `true`. Poiché un valore è `true`, anche l'espressione complessiva restituisce `true`, e l'accesso è consentito:

```swift
let hasDoorKey = false
let knowsOverridePassword = true
if hasDoorKey || knowsOverridePassword {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Stampa "Welcome!"
```

### Combinare operatori logici <a href="#combinare-operatori-logici" id="combinare-operatori-logici"></a>

Puoi combinare più operatori logici per creare espressioni composte più lunghe:

```swift
if enteredDoorCode && passedRetinaScan || hasDoorKey || knowsOverridePassword {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Stampa "Welcome!"
```

Questo esempio usa più operatori `&&` e `||` per creare un'espressione composta più lunga. Tuttavia, gli operatori `&&` e `||` operano comunque su due soli valori, quindi si tratta in realtà di tre espressioni più piccole concatenate tra loro. L'esempio può essere letto come:

Se abbiamo inserito il codice corretto della porta e superato la scansione della retina, oppure se abbiamo una chiave valida della porta, oppure se conosciamo la password di sblocco di emergenza, allora consenti l'accesso.

In base ai valori di `enteredDoorCode`, `passedRetinaScan` e `hasDoorKey`, le prime due sottoespressioni sono `false`. Tuttavia, la password di sblocco di emergenza è nota, quindi l'espressione composta complessiva restituisce comunque `true`.

{% hint style="info" %}
**Nota:** Gli operatori logici `&&` e `||` di Swift sono associativi a sinistra, il che significa che le espressioni composte con più operatori logici valutano per prima la sottoespressione più a sinistra.
{% endhint %}

### Parentesi esplicite <a href="#parentesi-esplicite" id="parentesi-esplicite"></a>

A volte è utile includere delle parentesi anche quando non sono strettamente necessarie, per rendere più facile da leggere l'intenzione di un'espressione complessa. Nell'esempio dell'accesso alla porta visto sopra, è utile aggiungere delle parentesi attorno alla prima parte dell'espressione composta per renderne esplicita l'intenzione:

```swift
if (enteredDoorCode && passedRetinaScan) || hasDoorKey || knowsOverridePassword {
    print("Welcome!")
} else {
    print("ACCESS DENIED")
}
// Stampa "Welcome!"
```

Le parentesi rendono chiaro che i primi due valori sono considerati come parte di un possibile stato separato nella logica complessiva. L'output dell'espressione composta non cambia, ma l'intenzione complessiva risulta più chiara al lettore. La leggibilità è sempre preferibile alla brevità; usa le parentesi dove aiutano a rendere chiare le tue intenzioni.
