2010-04-07 24 views
190

Necesito ejecutar un comando 100-200 veces, y hasta ahora mi investigación indica que tendría que copiar/pegar 100 copias de este comando, O usar un bucle for, pero el bucle for espera un lista de elementos, por lo tanto, necesitaría 200 archivos para operar, o una lista de 200 elementos, por lo tanto, derrotar el punto.Bucle script por lotes

Preferiría no tener que escribir un programa en C y documentar por qué tuve que escribir otro programa para ejecutar mi programa con fines de prueba. La modificación de mi programa tampoco es una opción.

Así, dado un comando, < a>, ¿cómo iba a ejecutarlo N veces a través de un script por lotes?

Respuesta

394

for /l es su amigo:

for /l %x in (1, 1, 100) do echo %x 

comienza en 1, pasos por uno, y termina en 100.

Uso dos % s si está en un archivo por lotes

for /l %%x in (1, 1, 100) do echo %%x 

(que es una de las cosas que realmente odio de windows Scripting)

Si tiene varios comandos para cada iteración del bucle, hacer esto:

for /l %x in (1, 1, 100) do (
    echo %x 
    copy %x.txt z:\whatever\etc 
) 

o en un archivo por lotes

for /l %%x in (1, 1, 100) do (
    echo %%x 
    copy %%x.txt z:\whatever\etc 
) 

Clave:
/l denota que el comando for operará en un numérica moda, en lugar de operar en un conjunto de archivos
%x es la variable de bucles
(valor inicial, incremento de valor, condición final [inclusive])

+0

Mucho mejor que mi solución, a condición de que estemos hablando de un DOS razonablemente moderno. –

+1

@Carl Espero que en 2010, al menos, pueda suponer que NT Command Extensions está presente: P – Jon

+1

Eso depende de qué tan literalmente tomemos la referencia "DOS". La última versión de MS-DOS, 7.1, data de 1997 y AFAIK no tiene estas extensiones. Los shells de comandos entregados con Windows, por otro lado, por supuesto. –

1

DOS no ofrece mecanismos muy elegantes para esto, pero creo que todavía se puede codificar un bucle de 100 o 200 iteraciones con un esfuerzo razonable. Si bien no existe un bucle numérico for, puede usar una cadena de caracteres como una "variable de bucle".

Codifique el ciclo usando GOTO, y para cada iteración use SET X=%X%@ para agregar otro signo @ a una variable de entorno X; y para salir del ciclo, compare el valor de X con una cadena de signos 100 (o 200) @.

nunca dijo que esto era elegante, pero debería funcionar!

+1

La opción '/ a' del' SET 'comando evaluará una expresión numérica para el valor del lado derecho. Consulte la documentación para [SET] (http://www.microsoft.com/resources/documentation/windows/xp/all/proddocs/en-us/set.mspx ? mfr = true). No es necesario hacer el truco de concatenación –

+1

para DOS, * es * necesario, ya que no hay 'set/a' en DOS. Afortunadamente, la qeustion es para' cmd' ... (en el momento de esta respuesta, el título de la pregunta era "bucle de script por lotes DOS" – Stephan

5

O puede disminuir/incrementar una variable por el número de veces que desea reproducir en bucle:

SETLOCAL ENABLEDELAYEDEXPANSION 
SET counter=200 
:Beginning 
IF %counter% NEQ 0 (
echo %x 
copy %x.txt z:\whatever\etc 
SET /A counter=%counter%-1 
GOTO Beginning 
) ELSE (
ENDLOCAL 
SET counter= 
GOTO:eof 

Obviamente, el uso de FOR /L es la carretera y este es el callejón que lleva más tiempo, pero se vuelve a la mismo destino

50

Y para iterar sobre los archivos de un directorio:

@echo off 
setlocal enableDelayedExpansion 

set MYDIR=C:\something 
for /F %%x in ('dir /B/D %MYDIR%') do (
    set FILENAME=%MYDIR%\%%x\log\IL_ERROR.log 
    echo =========================== Search in !FILENAME! =========================== 
    c:\utils\grep motiv !FILENAME! 
) 

Debe utilizar "enableDelayedExpansion" y el nombre! en lugar de $ FILENAME $.En el segundo caso, DOS interpretará la variable solo una vez (antes de ingresar al ciclo) y no cada vez que el programa se repita.

+16

Gracias por publicar esto. Sé que no es lo que el OP estaba pidiendo, pero es lo que estaba buscando cuando terminé aquí. – BrainSlugs83

4

Podría hacer algo con el siguiente efecto evitando el bucle FOR.

set counter=0 
:loop 
echo "input commands here" 
SET /A counter=%counter%+1 
if %counter% GTR 200 
(GOTO exit) else (GOTO loop) 
:exit 
exit 
16

plantilla para un bucle simple pero contado:

set loopcount=[Number of times] 
:loop 
[Commands you want to repeat] 
set /a loopcount=loopcount-1 
if %loopcount%==0 goto exitloop 
goto loop 
:exitloop 

Ejemplo: Diga "Hello World!" 5 veces:

@echo off 
set loopcount=5 
:loop 
echo Hello World! 
set /a loopcount=loopcount-1 
if %loopcount%==0 goto exitloop 
goto loop 
:exitloop 
pause 

Este ejemplo sería:

Hello World! 
Hello World! 
Hello World! 
Hello World! 
Hello World! 
Press any key to continue . . . 
+1

A casi la misma respuesta ya se da – jeb

+1

No hay nada de malo en que si está mejor escrito –

+0

este es el único bacalao de bucle e pude usar en mi pc win7. Todos los otros encontrados por googleing no funcionan. – LaBracca

2

Usted puede hacer esto sin una declaración for:^^.

@echo off 
:SPINNER 
SET COUNTP1=1 

:1 
CLS 
:: YOUR COMMAND GOES HERE 
IF !COUNTP1! EQU 200 goto 2 

SET COUNTP1=1 
) ELSE (
SET /A COUNTP1+=1 
) 
goto 1 

:2 
:: COMMAND HAS FINISHED RUNNING 200 TIMES 

Tiene conocimiento básico. Solo dale una prueba. : P

+1

no necesita expansión retrasada aquí. – Stephan

+1

También su construcción 'if' no está funcionando. – Stephan

0

No estoy seguro si una respuesta como esta ya se ha presentado todavía, pero usted podría intentar algo como esto:

@echo off 
:start 
set /a var+=1 
if %var% EQU 100 goto end 
:: Code you want to run goes here 
goto start 

:end 
echo var has reached %var%. 
pause 
exit 

La variable% var% aumentará en uno hasta que llega a 100, donde el programa luego muestra que ha terminado de ejecutarse. Una vez más, no estoy seguro si esto ha sido enviado o algo así, pero creo que puede ser el más compacto.

-1

Yo uso esto. Es casi lo mismo que los demás, pero es solo otra forma de escribirlo.

@ECHO off 
set count=0 
:Loop 
if %count%==[how many times to loop] goto end 
::[Commands to execute here] 
set count=%count%+1 
goto Loop 
:end 
-2

(Edited) lo hice por lo que se detiene después de 100 veces

@echo off 
goto actual 
set /a loopcount=0 
:actual 
set /a loopcount=%loopcount% + 1 
echo %random% %random% %random% %random% 
timeout 1 /nobreak>nul 
if %loopcount%== 100 goto stop 
goto actual 
:stop 
exit 

Esto generará 4 números aleatorios alcanzada 1 segundo 100 veces. Elimine el "timeout 1/nobreak> nul" para que sea muy rápido.

+3

la pregunta fue "100 - 200 veces", no "ciclo infinito". – Stephan

4

También puede probar esto en vez de un bucle for:

set count=0 
:loop 
set /a count=%count%+1 
(Commands here) 
if %count% neq 100 goto loop 
(Commands after loop) 

Es bastante pequeña y es lo que yo uso todo el tiempo.

+0

Esto es básicamente idéntico a [respuesta de Marcus Culver] (http://stackoverflow.com/a/19271183/3982001). No publique respuestas que no agreguen nada nuevo. ¡Gracias! –

+0

Ups, sry no vio eso, solo voló, lo tiró y solo vio bucles ... Lo siento, entonces :) – BlazeLP

1

manera muy básica para implementar un bucle en la programación cmd usando etiquetas

@echo off 
SET /A "index=1" 
SET /A "count=5" 
:while 
if %index% leq %count% (
    echo The value of index is %index% 
    SET /A "index=index + 1" 
    goto :while 
) 
0

La respuesta realmente depende de cómo usted está familiarizado con el lote, si usted no está tan experimentado, yo recomendaría incrementar una variable de bucle:

@echo off 
set /a loop=1 
:repeat 
echo Hello World! 
set /a loop=%loop%+1 
if %loop%==<no. of times to repeat> (
goto escapedfromrepeat 
) 
goto repeat 
:escapedfromrepeat 
echo You have come out of the loop 
pause 

Pero si tiene más experiencia con el lote, recomendaría el más práctico for /l %loop in (1, 1, 10) do echo %loop es la mejor opción.

   (start at 1, go up in 1's, end at 10) 
for /l %[your choice] (start, step, end) do [command of your choice] 
Cuestiones relacionadas