10

I have the following string:

MyProject/Architecture=32bit,BuildType=Debug,OS=winpc

I would like to be able to grab the values 32bit, Debug, and winpc and store them in variables named Architecture, BuildType, and OS to reference later in the batch script. I'm normally a Unix guy so this is new territory for me. Any help would be greatly appreciated!

3 Answers 3

31

This should do it:

FOR /F "tokens=1-6 delims==," %%I IN ("MyProject/Architecture=32bit,BuildType=Debug,OS=winpc") DO (
    ECHO I %%I, J %%J, K %%K, L %%L, M %%M, N %%N
)
REM output is: I MyProject/Architecture, J 32bit, K BuildType, L Debug, M OS, N winpc

The batch FOR loop is a pretty interesting piece of machinery. Type FOR /? in a console for a description of some of the crazy stuff it can do.

Sign up to request clarification or add additional context in comments.

Comments

9

Here is an interesting solution that doesn't care how many or what order the name=value pairs are specified. The trick is to replace each comma with a linefeed character so that FOR /F will iterate each name=value pair. This should work as long as there is only one / in the string.

@echo off
setlocal enableDelayedExpansion
set "str=MyProject/Architecture=32bit,BuildType=Debug,OS=winpc"

::Eliminate the leading project info
set "str=%str:*/=%"

::Define a variable containing a LineFeed character
set LF=^


::The above 2 empty lines are critical - do not remove

::Parse and set the values
for %%A in ("!LF!") do (
  for /f "eol== tokens=1* delims==" %%B in ("!str:,=%%~A!") do set "%%B=%%C"
)

::Display the values
echo Architecture=%Architecture%
echo BuildType=%BuildType%
echo OS=%OS%

With a bit more code it can selectively parse out only name=value pairs that we are interested in. It also initializes the variables to undefined in case the variable is missing from the string.

@echo off
setlocal enableDelayedExpansion
set "str=MyProject/Architecture=32bit,BuildType=Debug,OS=winpc"

::Eliminate the leading project info
set "str=%str:*/=%"

::Define a variable containing a LineFeed character
set LF=^


::The above 2 empty lines are critical - do not remove

::Define the variables we are interested in
set "vars= Architecture BuildType OS "

::Clear any existing values
for %%A in (%vars%) do set "%%A="

::Parse and conditionally set the values
for %%A in ("!LF!") do (
  for /f "eol== tokens=1* delims==" %%B in ("!str:,=%%~A!") do (
    if !vars: %%B ! neq !vars! set "%%B=%%C"
  )
)

::Display the values
for %%A in (%vars%) do echo %%A=!%%A!

5 Comments

This looks amazing, and incomprehensible. I'd love more detail on "%str=%str:*/=%", and "!str:,=%%~A!". The first one doesn't make sense why there's an '=' at the end, the second has a mystery ~ in it.
Works for smaller sets of data, but I'm querying a list of 24k items now, and the assignment of a command output appears to be longer than the maximum allowed length for batch file variables.
@Kieveli - Yes, environment variables used by CMD.EXE are limited to maximum length of about 8191 bytes long.
looking for a windows batch guru? go retire early :)
Amazing: If you believe one empty line would be enough try this: echo 1!LF!2!LF!3!LF!4!LF!\n ::The above 2 empty lines are critical - do not remove\n echo 1!LF!2!LF!3!LF!4!LF!\n Can anyone explain?
4

Try the following:

@ECHO OFF

SET Var=MyProject/Architecture=32bit,BuildType=Debug,OS=winpc

FOR /F "tokens=1,2,3 delims=," %%A IN ("%Var%") DO (
    FOR /F "tokens=1,2 delims==" %%D IN ("%%A") DO (
        SET Architecture=%%E
    )
    FOR /F "tokens=1,2 delims==" %%D IN ("%%B") DO (
        SET BuildType=%%E
    )
    FOR /F "tokens=1,2 delims==" %%D IN ("%%C") DO (
        SET OS=%%E
    )
)

ECHO %Architecture%
ECHO %BuildType%
ECHO %OS%

PAUSE

1 Comment

Just for fun, consider replacing your three inner FOR loops with the single line SET %%A & SET %%B & SET %%C. Great name BTW.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.