2

EDIT: It appears I had a stray GOTO :EOF at the end of an ECHO statement, and it will actually GOTO :EOF... d'oh! Thanks for responses. I think the bug is squashed now.


I have a script where I want to roll through a text document comparing if the files match.

Script here:

setlocal enabledelayedexpansion
for /f "tokens=1* delims=\" %%a in (NoMatchA.txt) DO (
        set "flag="
        for /f "tokens=1* delims=\" %%i in (NoMatchB.txt) do (
                IF "%%b"=="%%j" SET flag=1
        )
        IF DEFINED flag ECHO FLAG DEFINED
        IF NOT DEFINED flag ECHO FLAG NOT DEFINED
)
endlocal

made up Input from NoMatchA.txt and NoMatchB.txt made up example:

1234567890 \TEMP\ANIMALS\DOGS\FILE1.pdf
0987654321 \TEMP\TREES\I hate willows.docx
1122334455 \TEMP\LINUX ISOS\linustarvolds.iso
1029384756 \COVID\CANSUCk\MYBALLS\prettyflowers.jpg

1231509876 \USERS\HOMERSIMPSON\Doh.wav
1234567890 \TEMP\ANIMALS\DOGS\FILE1.pdf
0987654321 \TEMP\TREES\I hate willows.docx
1029383321 \COVID\CANSUCk\MYBALLS\prettyflowers.jpg

You get the picture. If I ECHO the IF "%%b"=="%%j" SET flag=1 I can clearly see in instances that they are equal, yet flag still shows as not defined.

So basically if the file names match I want to process that data a certain way.

2
  • 1
    Maybe make if case insensitive like IF /I "%%b"=="%%j" SET flag=1?
    – JosefZ
    Jun 3 '20 at 13:53
  • 1
    Do your file or folder names have a % in them, or !. If you can't provide us an actual data set that fails to work, I don't know how we are supposed to help. As it stands, what you posted above works fine unless there are special characters in the file and folder names. The problem is in the contents of the files as you already pointed out, so provide the content that is problematic. Jun 3 '20 at 17:29
1

•| Edit: This will prevent the remaining lines from going through the 2nd for loop when the flag has been set, and the line identities have already occurred.

As the flag has already been set, the loop does not need to continue.

If there are few lines, nothing changes, but if you have many lines, this can make a big difference in the total time process.

When adding the goto :skip, you goto exit the 2nd forcloop immediately, avoiding repetitive processing for each line, because you already been found the same string/line match.

@echo off && setlocal enabledelayedexpansion

cd /d "%~dp0" && if NOT exist NoMatchB.txt call :^) 

for /f "tokens=1*" %%a in (NoMatchA.txt) DO (

     SET "FLAG="
     for /f "tokens=1*" %%i in (NoMatchB.txt)do if NOT defined flag (
         IF /i "%%~b"=="%%~j" ( 
             SET "flag=1"
             goto :skip
            )   
         )

     :skip
     ECHO\value  FLAG==!flag!
     IF DEFINED flag (ECHO\echoed FLAG==1) ELSE ECHO\echoed FLAG==Undefined?

     ECHO\
    )

endlocal && goto :EOF

This is some that I prefer deal using with some different method.

You start the first loop by removing a variable, from there, it will only exist when some value is equal to "%%~b" and "%%~j".

After that point, there is no need to compare any values ​​within "%%~b" and "%%~j" in your 2nd loop.

Use if /i and ~ ("%%~b") to remove double quotes from the string and compare the two variables in the loop with "double quotes"

@echo off && setlocal enabledelayedexpansion

cd /d "%~dp0" && if NOT exist NoMatchB.txt call :^) 

for /f "tokens=1*" %%a in (NoMatchA.txt) DO (

     SET "FLAG="
     for /f "tokens=1*" %%i in (NoMatchB.txt)do if NOT defined flag (
         IF /i "%%~b"=="%%~j" SET "flag=1"
        )

     ECHO\value  FLAG==!flag!
     IF DEFINED flag (ECHO\echoed FLAG==1) ELSE ECHO\echoed FLAG==Undefined?

     ECHO\
    )

endlocal && goto :EOF

:^)
>NoMatchA.txt (
     echo;1231509876 \USERS\HOMERSIMPSON\Doh.wav
     echo;1234567890 \TEMP\ANIMALS\DOGS\FILE1.pdf
     echo;0987654321 \TEMP\TREES\I hate willows.docx
     echo;1029383321 \COVID\CANSUCk\MYBALLS\prettyflowers.jpg
     echo;9999999999 \COVID\CANSUCk\MYBALLS\FlowersOnly.jpg
    ) && (
>NoMatchB.txt (
    echo;1234567890 \TEMP\ANIMALS\DOGS\FILE1.pdf
    echo;0987654321 \TEMP\TREES\I hate willows.docx
    echo;1122334455 \TEMP\LINUX ISOS\linustarvolds.iso
    echo;1029384756 \COVID\CANSUCk\MYBALLS\prettyflowers.jpg
    echo;9999999999 \COVID\CANSUCk\MYBALLS\OnlyFlowers.jpg
    ) ) && exit /b

If I'm wrong or not, not sure, but this work for me, see the results:

value  FLAG==
echoed FLAG==Undefined?

value  FLAG==1
echoed FLAG==1

value  FLAG==1
echoed FLAG==1

value  FLAG==1
echoed FLAG==1

value  FLAG==
echoed FLAG==Undefined?
  1. In all loops pass in your 1st loop, you remove the variable flag:
set "flag="
  1. In first for loop remove the variable flag, in your 2nd for, you first check if your flag is not yet defined, if true, compare your variable %%~b and then set your flag variable to value 1:
 if not defined flag IF /i "%%~b"=="%%~j" SET "flag=1"
  1. Refer edit after setting its variable flag, because %%~b == %%~j, there is no need to continue comparing with the remaining lines of the file in this 2nd loop, then just use a goto :label to exit the loop immediately and continue the main loop.
    IF /i "%%~b"=="%%~j" (
       SET "flag=1"
       Goto :skip
       )   
  )

 :skip

2
  • Ah yes, I'll give that a try. Thank you very much. Should be more efficient.
    – HTWingNut
    Jun 3 '20 at 21:56
  • This will prevents unnecessary if in 2nd for loop after flag are set., But, you also can add goto :skip in 2nd loop. See edit:
    – Io-ol
    Jun 3 '20 at 22:00

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.