windows command prompt substring in a for loop - windows

I have to say before I describe my problem that I am new in performing command line prompts (Windows 10).
I have a directory with txt files (among other files). I need to perform a command line executable (txt2las) where the txt files are read and a .las file is written. This is what I have so far as a command prompt for /R %f in (.\*.txt) do txt2las -i %f -o %f.laz
However, this creates files like name.txt.laz. What I want is name.laz, therefore somehow take the substring from beginning till the last four characters. Can someone help me how to do that?
I tried the substring "function" but does not write anything.

You can extract the just the name of the file (without the extension) by using the ~n modifier:
for /R %f in (.\*.txt) do txt2las -i %f -o "%~dpnf.laz"
You can read more about the modifiers in the FOR /? help docs.
Edit per comments:
To ensure it is placed in the same directory as the source, add the ~dp modifiers in addition to ~n. This will extract the drive and path in addition to the file name. Also, you will likely want to wrap this entire output in quotes in the event the path has spaces in it.

... do txt2las -i %f -o %~nf.laz
The documentation can be read by executing for /? from the prompt.

Related

Simple "SendTo" script on Windows

I would like to create a simple script containing :
"C:\Users\Professional\NVEncC_5.24_x64\NVEncC64.exe" --codec h265 --preset quality --profile main10 --tier high -i "Project.mkv" -o "Project-Q27.mkv"
that i can reach by Right Click => SendTo.
I Understand that i need to name the file XXX.bat and paste it in SendTo folder.
But i don't know how to get the filename to dynamically add it to the script instead of "Project.mkv".
Can you help me ?
Thanks !
K.
A .bat file with the following should work.
"C:\Users\Professional\NVEncC_5.24_x64\NVEncC64.exe" --codec h265 --preset quality --profile main10 --tier high -i "%~f1" -o "%~n1-Q27.mkv"
pause
I also added the pause so you'll be able to see what happens if it's quick but it can be removed.
%~f1 is the argument for the file you've right clicked and used "SendTo" on (expanded to the full path).
%~n1-Q27.mkv" is essentially the same as argument %~f1 but without the file extension and it adds -Q27.mkv to whatever the filename was.
So if you right click/SendTo/yourbat.bat on a file called Funny.mkv the command (NVEncC64.exe) will be run on that file and output to a file called Funny-Q27.mkv.
I suggest you take backups of your files before testing so that you do not overwrite any existing files by mistake.
To get the name of the PowerShell .ps1 script being run, you can use the following command from MyInvocation:
$MyInvocation.MyCommand
This will return the .ps1 file object.
To get only the name string you could run:
$MyInvocation.MyCommand.Name
While the answer that #notjustme provided works, I have a small addition to it: the output variable should include the drive and path of the filename that was passed to the batch file to have the output file be created in the same directory as the source file.
"C:\Users\Professional\NVEncC_5.24_x64\NVEncC64.exe" --codec h265 --preset quality --profile main10 --tier high -i "%~f1" -o "%~d1%~p1%~n1-Q27.mkv"
pause
The filename that is passed when you right-click --> SendTo --> your_batch_file.cmd is referenced as %1 or the first parameter. Because it is a filename, it can be parsed and expanded further into its parts.
And as mentioned by #notjustme:
%~f1 expands %1 (the filename passed) to its fully qualified path name
%~n1 expands %1 to its file name only
But there is also:
%~d1 expands %1 to its drive letter
%~p1 expands %1 to its full path
%~x1 expands %1 to its file extension only
If you do not add the %~d1%~p1 to the output file variable, by default, the transcoded file will not be created in the same directory as the source file; rather, it will be created in the directory where your batch file is located.
(Additionally, given rigaya's rather short development windows with NVEncC, you might want to install it to a more generally-named directory that does not include the versioning, e.g., "C:\Users\Professional\NVEncC\" instead of "C:\Users\Professional\NVEncC_5.24_x64\". That way, you do not have to update its path in your batch file with every new release.)

Ghostscript: how to merge PDFs with wild card on Windows

I'm trying to merge all *.pdf in directory :
gswin64c -q -dNOPAUSE -sDEVICE=pdfwrite -sOutputFile=Total_Files.pdf -dBATCH *.pdf
This is perfectly work for me on Linux, but when I run it on Windows
I'm getting **Error: /undefinedfilename in *.pdf.**.
Please could some one help me with this.
(My problem was practically exactly the same). My solution (with the help of previous answers) answers the original question slightly better (an actual MS-DOS example is below)
del filename.lst
for %%s in (C:\somefolder\some?wildcards*.pdf) do ECHO %%s >> filename.lst
gswin64c.... #filename.lst
To explain;
'>>' means append in MS-DOS - so firstly we delete file filename.lst
I read (just now in some other place) that %%s in MS-DOS batch files works (instead of %s). Obviously - one day the filenames may contain spaces (as mine did already) so better be safe and quote the filenames. So the better batch file is;
del filename.lst
for %%s in (C:\somefolder\some?wildcards*.pdf) do ECHO "%%s" >> filename.lst
gswin64c.... #filename.lst
Right now I just used this for inputting many EPS files - but many PDF files work fine too; as in the above example - I actually tested it with both - my result is a PDF with many EPS files in it - and many pages from multiple PDF files in one PDF (as per the question).
There was a previous question on this topic, the answer is the same, Ghostscript does not allow wildcards in the input filename, you must specify each file you want to have as input.
Why does it work on Linux ? Because the shell you are using expands '*.ps' to a full list of files before passing the command line to Ghostscript.
To do this in Windows you will need to execute a shell script, pipe the filenames to a file, then supply the file as an argument to GS.
EG, something like
for %s in (*.ps) do ECHO %s >> filename.lst
gswin64c.... #filename.lst
As alternative to the for loop
dir /b /o:n *.ps > filename.lst
gets the job done (/b to get the files only, /o:n to sort by name).
To solve the sorting problem completely, you could rename the first 9 files to 01->09, or open the output file in notepad and handle these few cases manually. But if you will have more than 100 files, this could be bothersome.
Sorry to stir up this one year old thread, which helped me with my problem, but I thought using 'dir' is easier, more flexible and doesn't need you to delete the file list before starting.

how to batch replace the files in a directory windows vista(from .txt.txt to .txt)

I have a couple of flat files(.txt) in a directory.all those files are in the format *.txt.txt so i want to rename it to *.txt ?Is there any simple way to rename all together?
when I tried ren *.txt.txt *.txt is is not working
Any experts please suggest?It is amazing I have not got any answer yet
Please be noted that I need an out of the format filename.txt.
This should work
ren *.txt.txt *.
The reason your command didn't work is because, to windows, the file file.txt.txt is called file.txt with a .txt extension.
Only the last extension is the real extension, the first then becomes part of the filename, hence why your command changes it to what it already is.
If you did ren *.txt.txt *.pdf you would get file.txt.pdf.
My command will just remove the last one, thereby leaving the first, which then becomes the only and real extension.

how to use ren/rename

I want to rename all my avi videos.
All the avi videos are in the current directory.
I do it like this 'ren ./original.avi new.avi'.
But it says the syntax of the command is incorrect.
There's nothing wrong with specifying the directory of the file you want to rename. However, on Windows you must use \ instead of /:
ren .\original.avi new.avi
The ren command thinks you're trying to use one of its command line switches if you use the / character inside a filename. (It's not very smart.)

Can I copy multiple named files on the Windows command line using a single "copy" command?

I'd like to copy several known files to another directory as a part of a post-build event, but I don't want to have lines and lines of "copy [file] [destination] [switches]" in my build event.
If possible, I'd like to list out the files I'd like to copy using a similar format: "copy [file 1] [file 2] [file 3] [etc...] [destination] [switches]". However, Windows doesn't seem to like this type of format. How can I do it?
You can use 'for' either in a batch file or directly from the command prompt:
for %I in (file1.txt file2.txt file3.txt) do copy %I c:\somedir\
Wildcards are supported in the filelist as well:
for %I in (*.txt *.doc *.html) do copy %I c:\somedir\
For more info, just type for /? from a command prompt, or for a much easier to read help use Start->Help and Support and search for "For". On my XP Pro box, it was item 15 in the full text search results.
XP and Vista replaced xcopy with robocopy, and it will do exactly what you want. The syntax for what you want feels backwards at first, but it does the job:
robocopy source\folder a\dest\folder file1.exe file2.bat file3.dll file4.txt
Use the <Copy> MSBuild task.

Resources