Je dois définir une variable globale à partir d'une fonction et je ne sais pas trop comment le faire.
# Set variables
$global:var1
$global:var2
$global:var3
function foo ($a, $b, $c)
{
# Add $a and $b and set the requested global variable to equal to it
$c = $a + $b
}
Appelez la fonction:
foo 1 2 $global:var3
Résultat final:
$ global: var3 est défini sur 3
Ou si j'ai appelé la fonction comme ceci:
foo 1 2 $global:var2
Résultat final:
$ global: var2 est défini sur 3
J'espère que cet exemple a du sens. La troisième variable transmise à la fonction est le nom de la variable à définir.
Vous pouvez utiliser la cmdlet Set-Variable
. Passer $global:var3
envoie le value de $var3
, ce qui n'est pas ce que vous voulez. Vous voulez envoyer le name.
$global:var1 = $null
function foo ($a, $b, $varName)
{
Set-Variable -Name $varName -Value ($a + $b) -Scope Global
}
foo 1 2 var1
Ce n'est cependant pas une très bonne pratique de programmation. Ci-dessous serait beaucoup plus simple, et moins susceptible d'introduire des bogues plus tard:
$global:var1 = $null
function ComputeNewValue ($a, $b)
{
$a + $b
}
$global:var1 = ComputeNewValue 1 2
Aussi simple que:
$A="1"
function changeA2 () { $global:A="0"}
changeA2
$A
Vous devrez passer vos arguments en tant que types de référence.
#First create the variables (note you have to set them to something)
$global:var1 = $null
$global:var2 = $null
$global:var3 = $null
#The type of the reference argument should be of type [REF]
function foo ($a, $b, [REF]$c)
{
# add $a and $b and set the requested global variable to equal to it
# Note how you modify the value.
$c.Value = $a + $b
}
#You can then call it like this:
foo 1 2 [REF]$global:var3
J'ai rencontré cette question lors du dépannage de mon propre code.
Donc, cela ne fonctionne pas ...
$myLogText = ""
function AddLog ($Message)
{
$myLogText += ($Message)
}
AddLog ("Hello")
Write-Host $myLogText
Cela semble fonctionner, mais uniquement dans le PowerShell ISE :
$myLogText = ""
function AddLog ($Message)
{
$global:myLogText += ($Message)
}
AddLog ("Hello")
Write-Host $myLogText
C'est ce qui fonctionne à la fois dans ISE et en ligne de commande:
$global:myLogText = ""
function AddLog ($Message)
{
$global:myLogText += ($Message)
}
AddLog ("Hello")
Write-Host $global:myLogText
La première suggestion dans la réponse de Latkin semble bonne, bien que je suggère la voie la moins longue en dessous.
PS c:\temp> $global:test="one"
PS c:\temp> $test
one
PS c:\temp> function changet() {$global:test="two"}
PS c:\temp> changet
PS c:\temp> $test
two
Sa seconde suggestion, cependant, à propos d’une mauvaise pratique de programmation, est assez juste dans un calcul simple comme celui-ci, mais qu’en est-il si vous voulez retourner une sortie plus compliquée de votre variable? Par exemple, si vous vouliez que la fonction retourne un tableau ou un objet? C’est là que, pour moi, les fonctions de PowerShell semblent échouer lamentablement. Cela signifie que vous n'avez pas d'autre choix que de le renvoyer de la fonction à l'aide d'une variable globale. Par exemple:
PS c:\temp> function changet([byte]$a,[byte]$b,[byte]$c) {$global:test=@(($a+$b),$c,($a+$c))}
PS c:\temp> changet 1 2 3
PS c:\temp> $test
3
3
4
PS C:\nb> $test[2]
4
Je sais que cela peut sembler être un peu une digression, mais je pense que pour répondre à la question initiale, nous devons déterminer si les variables globales sont une mauvaise pratique de programmation et si, dans des fonctions plus complexes, il existe un meilleur moyen. (S'il y en a un, cela m'intéresserait.)
@zdan. Bonne réponse. Je l'améliorerais comme ça ...
Je pense que le plus proche possible d'une valeur de retour vraie dans PowerShell consiste à utiliser une variable locale pour transmettre la valeur et à ne jamais utiliser return
car elle peut être "corrompue" par tout type de situation
function CheckRestart([REF]$retval)
{
# Some logic
$retval.Value = $true
}
[bool]$restart = $false
CheckRestart( [REF]$restart)
if ( $restart )
{
Restart-Computer -Force
}
La variable $restart
est utilisée de part et d'autre de l'appel de la fonction CheckRestart
en précisant le champ d'application de la variable. La valeur de retour peut par convention être le premier ou le dernier paramètre déclaré. Je préfère dernier.
Pour moi cela a fonctionné:
function changeA2 () { $global:A="0"}
changeA2
$A