Batch files - number of command line arguments

后端 未结 8 1895
走了就别回头了
走了就别回头了 2020-12-04 09:48

Just converting some shell scripts into batch files and there is one thing I can\'t seem to find...and that is a simple count of the number of command line arguments.

<
相关标签:
8条回答
  • 2020-12-04 10:00

    A robust solution is to delegate counting to a subroutine invoked with call; the subroutine uses goto statements to emulate a loop in which shift is used to consume the (subroutine-only) arguments iteratively:

    @echo off
    setlocal
    
    :: Call the argument-counting subroutine with all arguments received,
    :: without interfering with the ability to reference the arguments
    :: with %1, ... later.
    call :count_args %*
    
    :: Print the result.
    echo %ReturnValue% argument(s) received.
    
    :: Exit the batch file.
    exit /b
    
    :: Subroutine that counts the arguments given.
    :: Returns the count in %ReturnValue%
    :count_args
      set /a ReturnValue = 0
      :count_args_for
    
        if %1.==. goto :eof
    
        set /a ReturnValue += 1
    
        shift
      goto count_args_for
    
    0 讨论(0)
  • 2020-12-04 10:04

    Try this:

    SET /A ARGS_COUNT=0    
    FOR %%A in (%*) DO SET /A ARGS_COUNT+=1    
    ECHO %ARGS_COUNT%
    
    0 讨论(0)
  • 2020-12-04 10:06

    Googling a bit gives you the following result from wikibooks:

    set argC=0
    for %%x in (%*) do Set /A argC+=1
    
    echo %argC%
    

    Seems like cmd.exe has evolved a bit from the old DOS days :)

    0 讨论(0)
  • 2020-12-04 10:09

    You tend to handle number of arguments with this sort of logic:

    IF "%1"=="" GOTO HAVE_0
    IF "%2"=="" GOTO HAVE_1
    IF "%3"=="" GOTO HAVE_2
    

    etc.

    If you have more than 9 arguments then you are screwed with this approach though. There are various hacks for creating counters which you can find here, but be warned these are not for the faint hearted.

    0 讨论(0)
  • 2020-12-04 10:15

    The last answer was two years ago now, but I needed a version for more than nine command line arguments. May be another one also does...

    @echo off
    setlocal
    
    set argc_=1
    set arg0_=%0
    set argv_=
    
    :_LOOP
    set arg_=%1
    if defined arg_ (
      set arg%argc_%_=%1
      set argv_=%argv_% %1
      set /a argc_+=1
      shift
      goto _LOOP
    )
    ::dont count arg0
    set /a argc_-=1
    echo %argc_% arg(s)
    
    for /L %%i in (0,1,%argc_%) do (
      call :_SHOW_ARG arg%%i_ %%arg%%i_%%
    )
    
    echo converted to local args
    call :_LIST_ARGS %argv_%
    exit /b
    
    
    :_LIST_ARGS
    setlocal
    set argc_=0
    echo arg0=%0
    
    :_LOOP_LIST_ARGS
    set arg_=%1
    if not defined arg_ exit /b
    set /a argc_+=1
    call :_SHOW_ARG arg%argc_% %1
    shift
    goto _LOOP_LIST_ARGS
    
    
    :_SHOW_ARG
    echo %1=%2
    exit /b
    

    The solution is the first 19 lines and converts all arguments to variables in a c-like style. All other stuff just probes the result and shows conversion to local args. You can reference arguments by index in any function.

    0 讨论(0)
  • 2020-12-04 10:16

    The function :getargc below may be what you're looking for.

    @echo off
    setlocal enableextensions enabledelayedexpansion
    call :getargc argc %*
    echo Count is %argc%
    echo Args are %*
    endlocal
    goto :eof
    
    :getargc
        set getargc_v0=%1
        set /a "%getargc_v0% = 0"
    :getargc_l0
        if not x%2x==xx (
            shift
            set /a "%getargc_v0% = %getargc_v0% + 1"
            goto :getargc_l0
        )
        set getargc_v0=
        goto :eof
    

    It basically iterates once over the list (which is local to the function so the shifts won't affect the list back in the main program), counting them until it runs out.

    It also uses a nifty trick, passing the name of the return variable to be set by the function.

    The main program just illustrates how to call it and echos the arguments afterwards to ensure that they're untouched:

    C:\Here> xx.cmd 1 2 3 4 5
        Count is 5
        Args are 1 2 3 4 5
    C:\Here> xx.cmd 1 2 3 4 5 6 7 8 9 10 11
        Count is 11
        Args are 1 2 3 4 5 6 7 8 9 10 11
    C:\Here> xx.cmd 1
        Count is 1
        Args are 1
    C:\Here> xx.cmd
        Count is 0
        Args are
    C:\Here> xx.cmd 1 2 "3 4 5"
        Count is 3
        Args are 1 2 "3 4 5"
    
    0 讨论(0)
提交回复
热议问题