Quick tip: Dynamically create and use variables

Creating and using variables in PowerShell is simple. Unlike most other languages you don’t need to initialize a variable before use – you don’t even need to type them; PowerShell will attempt to set the type based on the value you give it. Because they are so simple to use, it’s easy to forget that we actually have a set of cmdlets for working with variables. (Get/Set/New/Clear/Remove-Variable) But that’s ok, they are seldom needed. But in this quick tip I will show you how to create and use variables dynamically, and then they come in handy indeed.

Consider the following code:

$prefixes = @(
    'p1',
    'p2',
    'p3',
    'p4'
)

We have an array of prefixes that we want to use to prefix some variables that we will be using in our script. Our variables should be named ‘p1_var‘, ‘p2_var‘ and so on.

Using the New-Variable cmdlet we could achieve this the following way:

$count = 0
foreach ($prefix in $prefixes) {
    $count++
    New-Variable -Name "$($prefix)_var" -Value $count -Force
}

I’m using a counter to be able to give each variable a unique value. You see that the New-Variable have a Name parameter as well as a Value parameter. And since the Name parameter takes a string, it’s quite easy to create a dynamic name using a loop on our prefixes array, and by using an expression in the string to dynamically build our variable name. Notice that I’m using the Force switch to make sure that the variables will be created even if a variable with the same name exists already. If you just want to update the value of a variable, you could use the Set-Variable cmdlet instead.

Likewise, if we want to use these variables in a dynamic way, consider the following example:

foreach ($prefix in $prefixes) {
    Write-Host "Variable '$((Get-Variable -Name "$($prefix)_var").Name)' have a value of $((Get-Variable -Name "$($prefix)_var").Value)"
}

Again we are iterating through our array of prefixes, but this time we are using the Get-Variable to get the name and the value of the variables, which we write to the host.

I’ll not be surprised if there is an even easier way to achieve the same thing in PowerShell, so if you know of a better approach, please let me know in the comments section below.

3 comments

  1. Value sets the current value of the new variable you’re creating.

    It’s the same as writing:
    $myVariable = 5

    In Øyvind’s description, he iterates over the strings and also increments the counter. This counter is then set as the value of the variable.

    Like

  2. While this way of achieving programmatic variable names is perfectly valid, the syntactic (i.e. typing) and computational (i.e. runtime) effort seems excessive. I suspect most people asking this question are hoping for an answer like:

    ${“var_$count”}

    i.e. the variable’s name is the value of the expression between the {}. Too bad that the string between the {} is treated literally so the variable’s name is actually “var_$count” (including the “).

    If you don’t really need programmatic variable names but just programmatically identifiable storage locations, use a hash table. The example becomes:

    $var = @{}
    $count = 0
    foreach ($prefix in $prefixes)
    {
    $count++
    $var[$prefix] = $count
    }

    So much easier.

    (Yes, I know $prefix is not actually a prefix anymore but is there any real difference between p1_var, var_p1 and var[‘p1’] as far as the algorithm is concerned.)

    Like

Leave a comment