Tutto quello che voleva sapere se la dichiarazione

  • 05/23/2020
  • 18 minuti per leggere
    • j
    • x
    • t
    • D

Come molti altri linguaggi, PowerShell ha istruzioni per condizionalmente l’esecuzione di codice in yourscripts. Una di queste affermazioni è la dichiarazione If., Oggi faremo un tuffo profondo in uno deii comandi più fondamentali in PowerShell.

Nota

La versione originale di questo articolo è apparso sul blog scritto da @KevinMarquette. Il team di PowerShell ringrazia Kevin per aver condiviso questo contenuto con noi. Si prega di controllare il suo blog atPowerShellExplained.com.

Esecuzione condizionale

I tuoi script spesso devono prendere decisioni ed eseguire logiche diverse in base a tali decisioni.Questo è ciò che intendo per esecuzione condizionale., Hai un’istruzione o un valore da valutare, quindi esegui un’altra sezione di codice in base a tale valutazione. Questo è esattamente ciò che fa l’istruzione if.

L’istruzione if

Ecco un esempio di base dell’istruzione if:

$condition = $trueif ( $condition ){ Write-Output "The condition was true"}

La prima cosa che l’istruzione if fa è valutare l’espressione tra parentesi. Se si evaluatesto $true, quindi esegue il scriptblock tra parentesi graffe., Se il valore era $false, allora salterebbe su quel scriptblock.

Nell’esempio precedente, l’istruzioneifstava solo valutando la variabile$condition. Era $truee avrebbe eseguito il comando Write-Output all’interno dello scriptblock.

In alcune lingue, è possibile inserire una singola riga di codice dopo l’istruzione if e viene eseguita. Questo non è il caso di PowerShell. È necessario fornire un scriptblock completo con le parentesi graffe affinché funzioni correttamente.,

Operatori di confronto

L’uso più comune dell’istruzioneif per sta confrontando due elementi tra loro. PowerShell haoperatori speciali per diversi scenari di confronto. Quando si utilizza un operatore di confronto, il valoresul lato sinistro viene confrontato con il valore sul lato destro.

-eq per l’uguaglianza

Il -eq esegue un controllo di uguaglianza tra due valori per assicurarsi che siano uguali tra loro.,

$value = Get-MysteryValueif ( 5 -eq $value ){ # do something}

In questo esempio, sto prendendo un valore noto di5e confrontandolo con il mio$value per vedere se theymatch.

Un possibile caso d’uso è quello di controllare lo stato di un valore prima di intraprendere un’azione su di esso. È possibile ottenere un servizio e verificare che lo stato fosse in esecuzione prima di chiamare Restart-Service su di esso.

È comune in altri linguaggi come c# usare ==per l’uguaglianza (es: 5 == $value) ma questo non funziona con PowerShell., Un altro errore comune che le persone fanno è usare il segno di uguale (es:5 = $value) che è riservato per l’assegnazione di valori alle variabili. Mettendo il tuo valore conosciuto sulleft, rende quell’errore più imbarazzante da fare.

Questo operatore (e altri) ha alcune varianti.,

  • -eq case-insensitive uguaglianza
  • -ieq case-insensitive uguaglianza
  • -ceq case-sensitive uguaglianza

-ne non è uguale

Molti operatori hanno un correlato operatore di controllo per il risultato opposto. -ne verifica che i valori non siano uguali tra loro.

if ( 5 -ne $value ){ # do something}

Utilizzare questa opzione per assicurarsi che l’azione venga eseguita solo se il valore non è 5., Un buon caso d’uso in cui sarebbe quello di verificare se un servizio era in esecuzione prima di provare ad avviarlo.

le Variazioni:

  • -ne case-insensitive non uguale
  • -ine case-insensitive non uguale
  • -cne maiuscole e minuscole non è uguale

Queste sono le inverse variazioni di -eq. Raggrupperò questi tipi insieme quando elencherò variationsfor altri operatori.,

-gt-ge-lt-le per maggiore o minore di

Questi operatori vengono utilizzati quando si controlla se un valore è maggiore o minore di un altro valore.Il-gt -ge -lt -le sta per GreaterThan, GreaterThanOrEqual, LessThan e LessThanOrEqual.,mangiatore di o uguale, senza maiuscole / minuscole

  • -cge maggiore o uguale distinzione tra maiuscole e minuscole
  • -lt meno
  • -ilt meno, case-insensitive
  • -clt meno di distinzione tra maiuscole e minuscole
  • -le minore o uguale
  • -ile minore o uguale a case-insensitive
  • -cle minore o uguale a case-sensitive
  • non so perché utilizzare maiuscole e minuscole e insensibile opzioni per questi operatori.,

    -come jolly corrisponde

    PowerShell ha una propria sintassi pattern matching basato su jolly e si può usare con il-likeoperatore. Questi modelli di caratteri jolly sono abbastanza semplici.

    • ? corrisponde a qualsiasi carattere singolo
    • * corrisponde a qualsiasi numero di caratteri
    $value = 'S-ATX-SQL01'if ( $value -like 'S-*-SQL??'){ # do something}

    e ‘ importante sottolineare che il modello corrisponde a tutta la stringa. Se è necessario abbinare qualcosa nel mezzo della stringa, è necessario posizionare il * su entrambe le estremità della stringa.,e”>

    le Variazioni:

    • -like case-insensitive jolly
    • -ilike case-insensitive jolly
    • -clike case-sensitive jolly
    • -notlike case-insensitive jolly non abbinato
    • -inotlike case-insensitive jolly non abbinato
    • -cnotlike case-sensitive jolly non abbinato

    -match espressione regolare

    -match operatore permette di controllare una stringa per una delle espressioni regolari-based match., Usa questoquando i modelli jolly non sono abbastanza flessibili per te.

    $value = 'S-ATX-SQL01'if ( $value -match 'S-\w\w\w-SQL\d\d'){ # do something}

    Un modello regex corrisponde in qualsiasi punto della stringa per impostazione predefinita. Quindi puoi specificare una sottostringa che vuoi abbinare in questo modo:

    $value = 'S-ATX-SQL01'if ( $value -match 'SQL'){ # do something}

    Regex è un linguaggio complesso a sé stante e vale la pena esaminare. Parlo di più su -match ei molti modi per usare regex in un altro articolo.,

    Variations:

    • -match case-insensitive regex
    • -imatch case-insensitive regex
    • -cmatch case-sensitive regex
    • -notmatch case-insensitive regex not matched
    • -inotmatch case-insensitive regex not matched
    • -cnotmatch case-sensitive regex not matched

    -is of type

    You can check a value’s type with the -is operator.,

    if ( $value -is ){ # do something}

    Puoi usarlo se stai lavorando con classi o accettando vari oggetti sulla pipeline. Youcould avere un servizio o un nome di servizio come input. Quindi controlla se hai un servizie recupera il servizio se hai solo il nome.,

    if ( $Service -isnot ){ $Service = Get-Service -Name $Service}

    le Variazioni:

    • -is tipo
    • -isnot non è del tipo

    Collezione operatori

    Quando si utilizzano gli operatori precedenti con un solo valore, il risultato è $true o $false. Questo è gestito in modo leggermente diverso quando si lavora con una collezione. Ogni elemento della raccolta viene valutato e l’operatore restituisce ogni valore che viene valutato in $true.,

    PS> 1,2,3,4 -eq 33

    Funziona ancora correttamente in un’istruzione if. Quindi un valore viene restituito dal tuo operatore, quindi l’intera istruzione è $true.

    $array = 1..6if ( $array -gt 3 ){ # do something}

    C’è una piccola trappola che si nasconde nei dettagli qui che devo sottolineare. Quando si utilizza l’operatore-nein questo modo, è facile guardare erroneamente la logica all’indietro. L’utilizzo di-ne con acollection restituisce$true se qualsiasi elemento della raccolta non corrisponde al valore.,

    PS> 1,2,3 -ne 4123

    Questo può sembrare un trucco intelligente, ma abbiamo operatori-containse-in che gestiscono questo piùefficientemente. E-notcontains fa quello che ti aspetti.

    -contiene

    L’operatore-contains controlla la raccolta per il tuo valore. Non appena trova una corrispondenza, itreturns $true.

    $array = 1..6if ( $array -contains 3 ){ # do something}

    Questo è il modo preferito per vedere se una raccolta contiene il tuo valore., UtilizzandoWhere-Object (o-eq) l’intero elenco viene visualizzato ogni volta ed è significativamente più lento.,

    le Variazioni:

    • -contains case-insensitive match
    • -icontains case-insensitive match
    • -ccontains distinzione tra maiuscole e minuscole
    • -notcontains case-insensitive non abbinato
    • -inotcontains case-insensitive non abbinato
    • -cnotcontains maiuscole e minuscole non abbinato

    in

    -in operatore è come il -contains operatore tranne la collezione è sulla destra-lato.,

    $array = 1..6if ( 3 -in $array ){ # do something}

    Variations:

    • -in case-insensitive match
    • -iin case-insensitive match
    • -cin case-sensitive match
    • -notin case-insensitive not matched
    • -inotin case-insensitive not matched
    • -cnotin case-sensitive not matched

    Logical operators

    Logical operators are used to invert or combine other expressions.,

    non

    -not operatore ribalta un’espressione $false $true o del $true $false. Ecco un esempio in cui vogliamo eseguire un’azione quando Test-Path è $false.

    if ( -not ( Test-Path -Path $path ) )

    La maggior parte degli operatori di cui abbiamo parlato ha una variazione in cui non è necessario utilizzare l’operatore-not. Ma ci sono ancora volte che è utile.

    !, operatore

    È possibile utilizzare!come alias per-not.

    if ( -not $value ){}if ( !$value ){}

    Potresti vedere! usato più da persone che provengono da altre lingue come c#. Preferisco digitare itout perché trovo difficile vedere quando guardo rapidamente i miei script.

    -e

    È possibile combinare espressioni con l’operatore-and. Quando lo fai, entrambi i lati devono essere $trueperché l’intera espressione sia$true.,

    if ( ($age -gt 13) -and ($age -lt 55) )

    In questo esempio,$age deve essere uguale o superiore a 13 per il lato sinistro e inferiore a 55 per il lato destro. Ho aggiunto parentesi extra per renderlo più chiaro in quell’esempio, ma sono opzionali purché theexpression sia semplice. Ecco lo stesso esempio senza di loro.

    if ( $age -gt 13 -and $age -lt 55 )

    La valutazione avviene da sinistra a destra. Se il primo elemento viene valutato in $false, esce presto e non esegue il confronto corretto. Questo è utile quando è necessario assicurarsi che un valore esiste beforeyou usarlo., Ad esempio, Test-Path genera un errore se gli si assegna un percorso $null.

    if ( $null -ne $path -and (Test-Path -Path $path) )

    -o

    -or consente di specificare due espressioni e restituisce $true se uno di loro è$true.

    if ( $age -le 13 -or $age -ge 55 )

    Proprio come con l’operatore -and, la valutazione avviene da sinistra a destra., Tranne che se la prima parte è $true, allora l’intera istruzione è $true e non elabora il resto dell’espressione.

    Nota anche come funziona la sintassi per questi operatori. Hai bisogno di due espressioni separate. Ho visto gli utenti provare a fare qualcosa di simile $value -eq 5 -or 6 senza rendersi conto del loro errore.

    -xor exclusive o

    Questo è un po ‘ insolito. -xor consente a una sola espressione di valutare$true., Quindi se entrambi gli elementi sono$false o entrambi gli elementi sono$true, allora l’intera espressione è$false. Un altro modo per guardare a questo è che l’espressione è solo $true quando i risultati dell’espressione sono diversi.

    È raro che qualcuno possa mai usare questo operatore logico e non riesco a trovare un buon esempio come se lo usassi mai.

    Operatori bit a bit

    Gli operatori bit a bit eseguono calcoli sui bit all’interno dei valori e producono un nuovo valore come risultato., Insegnare agli operatori bitwise è oltre lo scopo di questo articolo, ma ecco la lista thethem.

    • -band binario E
    • -bor binario O
    • -bxor binario esclusiva O
    • -bnot binario NON
    • -shl shift a sinistra
    • -shr shift a destra

    PowerShell espressioni

    Si può usare il normale PowerShell all’interno della condizione.,

    if ( Test-Path -Path $Path )

    Test-Pathrestituisce$trueo$false quando viene eseguito. Questo vale anche per i comandi che restituisconoaltri valori.

    if ( Get-Process Notepad* )

    Valuta$truese c’è un processo restituito e$false se non c’è niente., È perfettamente valido utilizzare espressioni pipeline o altre istruzioni PowerShell come questa:

    if ( Get-Process | Where Name -eq Notepad )

    Queste espressioni possono essere combinate tra loro con gli operatori-and e-or, ma è possibile utilizzare le parentesi per suddividerle in sottoespressioni.

    if ( (Get-Process) -and (Get-Service) )

    Controllo per $null

    Avere un risultato o di un $null valore restituisce $false nel if istruzione., Quando si controlla specificatamente per $null, è consigliabile posizionare $null sul lato sinistro.

    if ( $null -eq $value )

    Ci sono alcune sfumature quando si tratta di $null valori in PowerShell. Se sei interessato a fare immersioni più profonde, ho un articolo su tutto ciò che volevi sapere su null null.

    Assegnazione variabile

    Ho quasi dimenticato di aggiungere questo fino a quando Prasoon Karunan V me lo ha ricordato.,

    if ($process=Get-Process notepad -ErrorAction ignore) {$process} else {$false}

    Normalmente quando si assegna un valore a una variabile, il valore non viene passato alla pipeline o alla console. Quando si esegue un’assegnazione variabile in un’espressione secondaria, viene passata a thepipeline.

    PS> $first = 1PS> ($second = 2)2

    Vedi come l’assegnazione $firstnon ha output e l’assegnazione $second? Quando un’assegnazione viene eseguita in un’istruzioneif, viene eseguita proprio come l’assegnazione$second sopra., Ecco un esempio pulito su come è possibile utilizzarlo:

    if ( $process = Get-Process Notepad* ){ $process | Stop-Process}

    Se $process viene assegnato un valore, l’istruzione è $true e $process viene interrotta.

    Assicurati di non confonderlo con-eq perché questo non è un controllo di uguaglianza. Questa è una funzione moreobscure che la maggior parte delle persone non si rende conto funziona in questo modo.,

    Percorso di esecuzione alternativo

    L’istruzioneif consente di specificare un’azione non solo quando l’istruzione è$true, maanche quando è$false. È qui che entra in gioco l’istruzioneelse.

    else

    L’istruzioneelse è sempre l’ultima parte dell’istruzioneif quando viene utilizzata.

    In questo esempio, controlliamo $path per assicurarci che sia un file. Se troviamo il file, lo spostiamo. Ifnot, scriviamo un avvertimento., Questo tipo di logica di ramificazione è molto comune.

    Annidato se

    Le istruzioniif eelse prendono un blocco di script, quindi possiamo inserire qualsiasi comando PowerShell all’interno di esse, inclusa un’altra istruzioneif. Ciò consente di utilizzare una logica molto più complicata.

    In questo esempio, testiamo prima il percorso felice e poi agiamo su di esso. Se ciò non riesce, facciamo un altro controllo e per fornire informazioni più dettagliate all’utente.

    elseif

    Non siamo limitati a un solo controllo condizionale., Possiamo concatenareif eelse statementstogether invece di nidificarli usando l’istruzioneelseif.

    L’esecuzione avviene dall’alto verso il basso. L’istruzione topif viene valutata per prima. Se questo è$false, quindi passa al successivoelseif oelse nell’elenco. Quest’ultimaelse è l’azione predefinita da intraprendere se nessuna delle altre restituisce$true.,

    switch

    A questo punto, ho bisogno di menzionare l’istruzione switch. Fornisce una sintassi alternativa per fare confronti multipli con un valore. Conswitch, si specifica un’espressione e il risultato viene confrontato con diversi valori diversi. Se uno di questi valori corrisponde, il blocco di codice corrispondente isexecuted. Dai un’occhiata a questo esempio:

    $itemType = 'Role'switch ( $itemType ){ 'Component' { 'is a component' } 'Role' { 'is a role' } 'Location' { 'is a location' }}

    Ci sono tre possibili valori che possono corrispondere a $itemType. In questo caso, corrisponde a Role., Ho usato un semplice esempio solo per darti un po ‘ di esposizione all’operatore switch. Parlo moreabout tutto quello che avreste sempre voluto sapere sulla dichiarazione switch in un altro articolo.

    Pipeline

    La pipeline è una caratteristica unica e importante di PowerShell. Qualsiasi valore che non è suppressedor assegnato a una variabile viene inserito nella pipeline. if ci fornisce un modo per sfruttare la pipeline in un modo che non è sempre ovvio.,

    $discount = if ( $age -ge 55 ){ Get-SeniorDiscount}elseif ( $age -le 13 ){ Get-ChildDiscount}else{ 0.00}

    Ogni blocco di script inserisce i risultati i comandi o il valore nella pipeline. Quindi assegniamo il risultato dell’istruzioneif alla variabile$discount. Quell’esempio avrebbe potuto altrettanto facilmente assegnare quei valori alla variabile$discount direttamente in ogni scriptblock. Non posso dire che lo usi spesso con l’istruzione if, ma ho un esempio in cui l’ho usato di recente.,

    Array inline

    Ho una funzione chiamata Invoke-SnowSql che avvia un eseguibile con diversi comandi-linearguments. Ecco una clip da quella funzione in cui costruisco la serie di argomenti.

    Le variabili$Debug e$Path sono parametri sulla funzione forniti dall’utente finale.Li valuto in linea all’interno dell’inizializzazione del mio array. Se $Debugè true, allora quei valuesfall nel$snowSqlParam nella posizione corretta. Lo stesso vale per la variabile $Path.,

    Semplifica operazioni complesse

    È inevitabile che ti imbatti in una situazione che ha troppi confronti da controllare e la tua istruzioneIf scorre via dal lato destro dello schermo.

    Possono essere difficili da leggere e questo ti rende più incline a commettere errori. Ci sono alcune cose che possiamo fare al riguardo.

    Continuazione della riga

    Ci sono alcuni operatori in PowerShell che ti permettono di avvolgere il comando alla riga successiva., I logicaloperators -and e -or sono buoni operatori da utilizzare se si desidera interrompere l’espressione inle linee multiple.

    C’è ancora molto da fare lì, ma posizionare ogni pezzo sulla propria linea fa una grande differenza.Generalmente lo uso quando ottengo più di due confronti o se devo scorrere a destra per leggere una qualsiasi delle logiche.

    Pre-calcolo dei risultati

    Possiamo estrarre tale istruzione dall’istruzioneif e controllare solo il risultato.

    Questo sembra molto più pulito dell’esempio precedente., Ti viene anche data l’opportunità di utilizzare il nome avariable che spiega cosa stai veramente controllando. Questo è anche un esempio di codice di auto-documentazione che salva commenti non necessari.

    Più istruzioni if

    Possiamo suddividere questo in più istruzioni e controllarle una alla volta. In questo caso, usiamo aflag o una variabile di tracciamento per combinare i risultati.

    Ho dovuto invertire la logica per far funzionare correttamente la logica del flag. Ogni valutazione è un’istruzione if., Il vantaggio di questo è che quando si esegue il debug, è possibile tellexactly ciò che la logica sta facendo. Sono stato in grado di aggiungere molto meglio verbosità allo stesso tempo.

    L’ovvio svantaggio è che è molto più codice da scrivere. Il codice è più complesso da guardarecome prende una singola riga di logica e la esplode in 25 o più righe.

    Usando le funzioni

    Possiamo anche spostare tutta quella logica di convalida in una funzione. Guarda come questo sembra pulito aglance.,

    if ( Test-SecureDriveConfiguration -ADUser $user ){ # do something}

    Devi ancora creare la funzione per eseguire la convalida, ma rende questo codice molto più semplice con cui lavorare. Rende questo codice più facile da testare. Nei tuoi test, puoi prendere in giro la chiamata aTest-ADDriveConfiguration e hai solo bisogno di due test per questa funzione. Uno in cui restituisce$true e uno in cui restituisce $false. Testare l’altra funzione è più semplice perché è cosìpiccolo.

    Il corpo di quella funzione potrebbe essere ancora quel one-liner con cui abbiamo iniziato o la logica esplosa che abbiamo usato nell’ultima sezione., Questo funziona bene per entrambi gli scenari e consente di modificare facilmente thatimplementation in seguito.

    Gestione degli errori

    Un uso importante dell’istruzioneif è quello di verificare le condizioni di errore prima di eseguire intoerrors. Un buon esempio è quello di verificare se una cartella esiste già prima di provare a crearla.

    if ( -not (Test-Path -Path $folder) ){ New-Item -Type Directory -Path $folder}

    Mi piace dire che se ti aspetti che si verifichi un’eccezione, allora non è davvero un’eccezione. Quindi controlla i tuoi valori e convalida le tue condizioni dove puoi.,

    Se vuoi immergerti un po ‘ di più nella gestione effettiva delle eccezioni, ho un articolo su tutto ciò che hai sempre voluto sapere sulle eccezioni.

    Parole finali

    L’istruzione if è un’istruzione così semplice ma è un pezzo fondamentale di PowerShell. You willfind te stesso utilizzando questo più volte in quasi ogni script si scrive. Spero che tu abbia una comprensione migliore di prima.

    Lascia un commento

    Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *