Find last token

June 15, 2009 at 18:27:54
Specs: Windows 7, x86
Greetings,

I am trying to rename files in multiple subdirectories, and break out the file name and the folder one level higher than the file into variables with dos under Windows 7 (or xp/vista).

ie:
1. Find *.mkv files.
2. For each file, put file name (minus extension) into a variable
3. For each file, get the folder name the file is in and put that into a variable.

I am having problems mainly with the getting of the folder that has the file in it b/c I can't be sure what token it will be.

I started:
:: GET LIST OF ALL FOLDERS CONTAINING A *.MKV FILE AND LOOP THROUGH EACH
FOR /f "tokens=* delims=" %%a in ('dir/s/b/a-d \*.mkv') do (

:: CHECK TO SEE IF A FILE HAS ALREADY BEEN PROCESSED, IF SO SKIP IT AND MOVE ON
IF EXIST "%%~dpa%%~na02%%~xa" (
ECHO File %%~na02%%~xa already exists...skipping it.
)ELSE (
:: IF NEED TO BE PROCESSED RENAME THE FILE ADDING 02 TO THE MOVIE
ren "%%a" "%%~na02%%~xa"
)

pause
echo.
)

I run it the first time on a directory containing only a movie.mkv and it works great, it renames the movie.mkv to movie02.mkv. However, the next time around my logic looks for *.mkv and finds movie02.mkv, then I adds an 02 to that making it movie0202.mkv.

So, if I can find out the name of the folder holding the movie.mkv, that will always be the movie name and I can set that to say if exist %MOVIEFOLDER%02.mkv, I will know if I processed it.

This all leads me to where I have no idea how to get the folder holding that file (I am sure I have to not use tokens=* but don't know how to say "last token".)

Any ideas? Does that make any sense? Thanks to all.


See More: Find last token

Report •


#1
June 15, 2009 at 19:19:17
if you can download and install gawk for windows (see my sig)
BEGIN{	FS="[.]" }	
{ 	
	filename=$(NF-1)  	
  	ext = $NF
  	if ( filename !~ /20$/){	 
	 	 newfile = filename"20."ext
	 	 cmd = "move "$0" "newfile
	 	 system(cmd)
                 close(cmd)
	}
}

save the above as myscript.awk
c:\test> dir /b/s *.mkv | gawk -f myscript.awk

GNU win32 packages


Report •

#2
June 15, 2009 at 19:27:15
That might work. I was planning on using that direcotry variable for other things though.

It looks like that script will only do the rename, can you grab the folder name before the *.mkv file and set a dos variable for me to use again?


Report •

#3
June 15, 2009 at 19:59:07
well, you can get the path in gawk itself and do what you want inside gawk. otherwise, just print out the path, then in dos, use for loop to get the results
eg
BEGIN{	FS="[.]" }	
{ 
 filename = $1
 ext = $2
 m=split(filename,f,"\\")
 gsub(f[m],"",filename)
 path = filename  
 if ( filename !~ /20$/){	 
	 	 newfile = $1"20."ext
	 	 cmd = "move "$0" "newfile
	 	 print cmd
	 	# system(cmd) #uncomment to use
        #  close(cmd) #uncomment to use
        # do something with variable 'path'
        print "the path for " $0 " is: " path
 } 
}

output

C:\test>dir /s/b *.mkv | gawk -f test.awk
move C:\test\movie.mkv C:\test\movie20.mkv
the path for C:\test\movie.mkv is: C:\test\
move C:\test\movie1.mkv C:\test\movie120.mkv
the path for C:\test\movie1.mkv is: C:\test\
move C:\test\tmp\movie120.mkv C:\test\tmp\movie12020.mkv
the path for C:\test\tmp\movie120.mkv is: C:\test\tmp\

to get results in DOS , use for loop ( find out yourself)

@echo off
for /F <set options here> %%a in ('dir /s/b *.mkv ^| gawk -f test.awk') do (
 echo %%a
)

GNU win32 packages | Gawk


Report •

Related Solutions

#4
June 15, 2009 at 20:08:41
I can get the full path in dos with the for command, but I need to be able to break apart the full path to just get the last direcotry in that full path:

d:\tmp\test\stuff\file.txt

I need to be able to set mydir=%var%
where %var% equals in this case, the "stuff' directory. That make sense?


Report •

#5
June 15, 2009 at 20:50:03
so you just want to get the directory just above?
then try this
BEGIN{	FS="[.]" }	
{ 
 filename = $1
 ext = $2
 m=split(filename,f,"\\")
 path = f[m-1]
 if ( filename !~ /20$/){	 
	 	 newfile = $1"20."ext
	 	 cmd = "move "$0" "newfile
	 	 print cmd	 	 
	 	# system(cmd)
        #  close(cmd)
        # do something with variable 'path' eg print path , so that in your batch , use for loop to get results
        print "the path for " $0 " is: " path
 } 
}

output
C:\test>dir /s/b *.mkv | gawk -f test.awk
move C:\test\movie.mkv C:\test\movie20.mkv
the path for C:\test\movie.mkv is: test
move C:\test\movie1.mkv C:\test\movie120.mkv
the path for C:\test\movie1.mkv is: test
move C:\test\tmp\movie12.mkv C:\test\tmp\movie1220.mkv
the path for C:\test\tmp\movie12.mkv is: tmp

GNU win32 packages | Gawk


Report •

#6
June 16, 2009 at 00:31:07
Forget DOS

@echo off & setLocal enableDELAYedexpansion

for /f "tokens=* delims= " %%a in ('dir/b/s/a-d c:\files') do (
set name=%%~Na
set fold=%%~DPa
call :sub1
echo !name! is in !fold!
)

goto :eof

:sub1

::set fold=%1

:loop
for /f "tokens=1* delims=\\ " %%f in ("!fold!") do (
::echo %%g
if "%%g" neq "" (
set fold=%%g
goto :loop
)
set fold=!fold:~0,-1!
)

goto :eof


=====================================
If at first you don't succeed, you're about average.

M2


Report •

#7
June 16, 2009 at 05:45:35
@Mechanix2Go

I will be forced to evolve away from DOS one day...but until then... :D

It appears to not like spaces. I think I should modify the:
for /f "tokens=1* delims=\\ "
to
for /f "tokens=1* delims=\\" (remove the space)
Also, why are their two \'s in the delims?

Lastly, I have not seen this or should I saw I don't understand this, I see you are setting fold to fold but what does the ~0,-1 mean in:
set fold=!fold:~0,-1!

Thanks


Report •


Ask Question