blueberry
Goto Top

for schleife, Variable wird gesetzt, aber beim Echo wird die Variable nicht angezeigt

Hallo Zusammen,

Ich hoffe ich habe nicht falsch gesucht und das Thema, dass ich hier anspreche wurde schon zig-Mal angeschaut...

Na jedenfalls habe ich den Folgenden Code:
for /f "delims=" %%i in ('dir /ad /s /b "C:\Programme\Acronis"') do (   
Set pfad=%%i
echo %pfad%
pause)
Und wenn ich ein Echo on habe sehe ich, dass die Variable definiert wird, aber beim Echo die Variable in "vergessenheit" geht... Es heisst nur immer "Echo ist on" oder so ähnlich... Kann mir da jemand helfen ?

Ich danke schon im voraus

Mit freundlichen Grüssen

Blueberry

Content-ID: 104500

Url: https://administrator.de/contentid/104500

Ausgedruckt am: 25.11.2024 um 20:11 Uhr

Biber
Biber 20.12.2008 um 01:05:15 Uhr
Goto Top
Moin Blueberry,

für den CMD-Interpreter ist die FOR-Anweisung, auch wenn sie über mehrere Zeilen formatiert geschrieben wird, eine einzige Anweisung und erst mit der schliessenden Klammer-Zu beendet.
Alle Variablen der Form %var% werden entsprechen einmalig aufgelöst, nämlich dann, wenn diese Zeile als syntaktisch verwertbar eingestuft wurde und die Ausführung losgehen kann.

Wenn die Variablen innerhalb dieser Anweisung neu gesetzt und neu ausgelesen werden, dann musst Du die so genannte "verzögerte Variablenauflösung" oder aus Neudeutsch "Delayed Expansion" aktivieren.
SetLocal EnableDelayedExpansion
for /f "delims=" %%i in ('dir /ad /s /b "C:\Programme\Acronis"') do (   
Set pfad=%%i
echo !pfad!
pause)
Diejenigen Variablen, die immer erst "zum Zeitpunkt des Anfassens" aufgelöst werden sollen, müssen dann in der Form !var! statt %var% geschrieben werden.

Grüße
Biber
Blueberry
Blueberry 20.12.2008 um 10:01:39 Uhr
Goto Top
Hallo Biber,

Ich danke dir für deine schnelle Lösung für das Problem. Das mit dem "SetLocal EnableDelayedExpansion " hab ich schon mal gesehen wusste aber nie für was das genau war. Jetzt begreiffe ich das schon ein bisschen mehr. Ich wünsche noch ein schönes Weihnachten und ein schönes neues Jahr!

Und wie kann ich die Variable noch ein 3tes mal brauchen sprich wenn ich noch ein Call :sub1 einbauen möchte ?

Mit freundlichen Grüssen

BLueberry
bastla
bastla 20.12.2008 um 12:47:18 Uhr
Goto Top
Hallo Blueberry!

Wenn Du ohnehin ein Unterprogramm verwenden wolltest, wäre "delayedExpansion" gar nicht erforderlich - das sähe dann so aus:
@echo off & setlocal
for /f "delims=" %%i in ('dir /ad /s /b "C:\Programme\Acronis"') do call :sub1 "%%i"  
goto :eof

:sub1
set "pfad=%~1"  
echo %pfad%
:: was sonst noch anliegt
pause
goto :eof
Im "sub1" kommmt der übergebene Pfad als erster (und hier einziger) Paramer (%1) an. Mit der Schreibweise %~1 werden die den Parameter umgebenden Anführungszeichen entfernt.

Das "goto :eof" in Zeile 3 sorgt dafür, dass das Unterprogramm nach dem Ende der Schleife nicht noch ein weiteres Mal durchlaufen wird, und das "goto :eof" ("Beende das Unterprogramm und springe zurück ins Hauptprogramm!") in der letzten Zeile wäre gar nicht nötig - es dient nur als Vorsichtsmaßnahme, falls (zukünftig) noch ein weiteres Unterprogramm oder ein Sprung vom Hauptprogramm zu einem "Ende"-Teil folgen sollte.

Grüße
bastla
Blueberry
Blueberry 20.12.2008 um 17:31:07 Uhr
Goto Top
Hallo Bastla,

Ich möchte mit dem Dir in der For-Schleife einen anderen Batch aufrufen ist das möglich ?

for /f "delims=" %%a in ('dir /S /b "C:\Programme\Acronis" ^| find "test2.bat"') do (  
Call %%a :sub1)
Den Code habe ich bereits... Er startet zwar den anderen Batch, aber nicht bei Sub1, sondern von Anfang an...

Mit freundlichen Grüssen

Blueberry
bastla
bastla 20.12.2008 um 18:59:54 Uhr
Goto Top
Hallo Blueberry!

Mein Beispiel oben war für ein internes Unterprogramm gedacht - wenn in einem aufgerufenen externen Batch an einer bestimmten Stelle gestartet werden soll, musst Du dies auch dort festlegen, etwa:
@echo off & setlocal
if "%~1" neq "" goto %~1  
Jetzt kannst Du den "call" aus Deinem Beispiel verwenden und es wird sofort zu der als Parameter angegebenen Stelle gesprungen - falls es diese nicht geben sollte, bricht der Batch allerdings ab ...

Mehr Kontrolle (aber auch mehr Aufwand) hast Du, wenn Du jedes mögliche Sprungziel abfragst, also etwa
@echo off & setlocal
if "%~1"=="" goto :NormalStart  
if "%~1"==":sub1" goto :sub1  
if "%~1"==":sub2" goto :sub2  
:: und so weiter
echo Das Sprungziel "%~1" wurde  nicht gefunden ...  
goto :eof

:NormalStart
echo Start erfolgte ohne Parameter
::
goto :eof

:sub1
echo Starte bei ":sub1"  
::
goto :eof

:sub2
echo Starte bei ":sub2"  
::
goto :eof

Grüße
bastla
Blueberry
Blueberry 21.12.2008 um 11:16:14 Uhr
Goto Top
Hallo bastla,

Wieder einmal hast du recht :D Aber was ich noch gerne wissen möchte, warum wird die Marke "sub1" als %~1 übergeben ? also ich nehme an das es sich bei dem %~1 um eine eins und nicht um das kleine "L" handelt, den die sehen mehr oder weniger gleich aus...

Mit freundlichen Grüssen

Blueberry
bastla
bastla 21.12.2008 um 15:15:05 Uhr
Goto Top
Hallo Blueberry!

warum wird die Marke "sub1" als %~1 übergeben ?
Falls sich die Frage tatsächlich vor allem auf die "1" bezieht: Es handelt sich tatsächlich um die Ziffer. Jeder Batch kann die Parameter %0 bis %9 verwenden, wobei %0 die Batchdatei selbst repräsentiert und ab %1 die an den Batch übergebenen Parameter - ein in "C:\Scripts\Params.cmd" gespeicherter Batch würde bei einem Aufruf mit
C:\Scripts\Params.cmd ParamEins "Param Zwei" "ParamDrei"
folgende Parametervariablen liefern:
%0=C:\Scripts\Params.cmd
%1=ParamEins
%2="Param Zwei"
%3="ParamDrei"
Wie zu erkennen ist, werden umgebende Anführungszeichen, egal ob erforderlich (wie für "Param Zwei") oder nicht, in der Variablen "mitgeliefert". Um sicher sein zu könnnen, dass keine solchen Anführungszeichen in der Variablen stehen, können diese mit der Schreibweise
%~2
entfernt werden (was ich zumeist gewohnheitsmäßig mache); waren ohnehin keine da, ist dies auch kein Problem - im Ergebnis sind auf jeden Fall keine Anführungszeichen mehr vorhanden.

Grüße
bastla
Blueberry
Blueberry 21.12.2008 um 17:14:01 Uhr
Goto Top
Hallo bastla,

Das mit dem übergeben wusste ich, aber ich wusste nicht das indiesem Fall auch ":sub1" so über geben wird... Danke nochma

Gruss
Blueberry