Thursday, April 28, 2011

DOS batch set problem

I had a problem with set not working in a batch file; it took a while to distil the problem; at first I thought it was to do with subroutine calls...

The script

@echo off
setlocal
set a=aaa
echo a = "%a%"
(
set b=bbb
echo b = "%b%"
)

produces the output

a = "aaa"
b = ""

whereas I'd expect

a = "aaa"
b = "bbb"

Why is this please? Is it a bug in DOS? Perhaps there's something about the (...) command grouping syntax that I'm unaware of.

Thanks.

From stackoverflow
  • You need delayed expansion to be on, or the batch interpreter will interpolate all variables at parsing time, instead of run time.

    setlocal enableextensions enabledelayedexpansion
    

    See this question for an example and some great explanation of it.

  • What's happening is that the batch interpreter as treating everything in between the brackets a single line. This means it's doing variable replacement on everything betweeen the brackets before any of the commands are run.

    So:

    (
    set b=bbb
    echo b = "%b%"
    )
    

    Becomes:

    (
    set b=bbb
    echo b = ""
    )
    

    The variable b is being set but obviously isn't set before you run the SET command.

  • User delayed expansion and ! instead of %

    @echo off
    setlocal enableextensions enabledelayedexpansion
    set a=aaa
    echo a = "%a%"
    (
    set b=bbb
    echo b = "!b!"
    )
    
    Rhubbarb : Thanks for the concise reply. Do you happen to know if there's a syntax for the numbered parameters %1 etc.? I have tried !1 and !1!, but these don't work. (I'm asking this in the context of a :subroutine call.)
    Andy Morris : Since they can't change between parsing and execution the way %a% type variables can, I cant see that it matters.
    Rhubbarb : You're quite right. I had other problems with the script that then exhibited the same symptoms. Problem solved. Thanks very much (to all).

0 comments:

Post a Comment