Toplu iş dosyasında joker karakterle eşleşen dosyalar arasında döngü yapma


194

Bir dizi temel dosya adım var, her isim için 'f' tam olarak iki dosya var, 'f.in' ve 'f.out'. Her dosya için, tüm dosya adlarını geçer bir toplu iş dosyası (Windows XP'de) yazmak istiyorum:

  • Temel adı 'f' göster
  • 'F.in' ile ilgili bir işlem gerçekleştirin
  • 'F.out' ile ilgili başka bir işlem gerçekleştirin

Örneğin * .in (veya * .out) aramak dışında, temel dosya adları kümesini listelemenin bir yolu yok.


10
Gerçekten 111/0 oy sonra bu adam olmak istemiyorum, ancak sorunuz herhangi bir yeniden arama göstermez
phil294

Yanıtlar:


293

İki dosyayı işleyen iki programınız olduğunu varsayarsak, process_in.exe ve process_out.exe:

for %%f in (*.in) do (
    echo %%~nf
    process_in "%%~nf.in"
    process_out "%%~nf.out"
)

%% ~ nf,% f öğesini yalnızca dosya adına genişleten bir ikame değiştiricisidir. Diğer değiştiricilere https://technet.microsoft.com/en-us/library/bb490909.aspx (sayfanın ortasında) veya yalnızca bir sonraki cevapta bakın.


47
Bunu komut satırına yazıyorsanız tek bir '%' kullanın. OP'nin komut satırı hakkında soru sormadığını biliyorum, ancak bu soru Google aramamın en üstünde geldiğinde aradığım şey bu. Diğerleri bu biti takdir edebilir.
Jason

2
Sözdizimini açıklayabilir misiniz? Döngü değişkeni %%fneden %%~nfdaha sonra açıklanır?
Albay Panik

6
@ColonelPanic - örneğimde olduğu gibi, bir ~şeyler yapmak için bir avuç değiştirici var, sadece dosya adını al . *Tam yol falan yaparsa bunu kullanmak benim için bir alışkanlık . Bu değiştiricilerin bir kısmı var (sayfanın ortasında): microsoft.com/resources/documentation/windows/xp/all/proddocs/…
Jim Buck

dosya ve dizinde boşluklar varsa ne olur?
BKSpurgeon

3
Ayrıca, okunabilir ve anlamlı bir şey kullanmaya çalışırsanız %% f değişkeninin tek harfli - şifreli hata iletileri olması gerektiğini unutmayın.
Bruce Dawson

90

Masaüstünüzün içeriğini yazdırmak için bu satırı kullanabilirsiniz:

FOR %%I in (C:\windows\desktop\*.*) DO echo %%I 

%%IDeğişkeni aldıktan sonra, üzerinde bir komut uygulamak kolaydır (sadece echo kelimesini programınızla değiştirin)

Ayrıca, FOR değişken başvurularının ikamesi geliştirildi Artık aşağıdaki isteğe bağlı sözdizimini kullanabilirsiniz:

%~I         - expands %I removing any surrounding quotes (")
%~fI        - expands %I to a fully qualified path name
%~dI        - expands %I to a drive letter only
%~pI        - expands %I to a path only (directory with \)
%~nI        - expands %I to a file name only
%~xI        - expands %I to a file extension only
%~sI        - expanded path contains short names only
%~aI        - expands %I to file attributes of file
%~tI        - expands %I to date/time of file
%~zI        - expands %I to size of file
%~$PATH:I   - searches the directories listed in the PATH
               environment variable and expands %I to the
               fully qualified name of the first one found.
               If the environment variable name is not
               defined or the file is not found by the
               search, then this modifier expands to the
               empty string

https://ss64.com/nt/syntax-args.html

Yukarıdaki örneklerde %Ive PATH diğer geçerli değerlerle değiştirilebilir. %~Sözdizimi geçerli İÇİN değişken adı ile sonlandırılır. Gibi büyük harf değişken isimlerini seçmek %Ionu daha okunabilir hale getirir ve büyük / küçük harfe duyarlı olmayan değiştiricilerle karışıklığı önler.

Tam belgeleri yazarak alabilirsiniz FOR /?


Bu işe yaramıyor gibi görünüyor. %%I was unexpected at this time.
Brad

4
@Bu komut satırında (ve bir toplu iş dosyasında değil) kullanıyorsanız %I,%%I
doubleDown

1
Kabul edilenden çok daha iyi bir cevap. Tüm bayraklar / değiştiriciler üçüncü bir web sitesine değil yanıta dahil edilmiştir ( kimse bağlantınızı tıklamak istemez Louis )
JustCarty

5

En kolay yolu, gördüğüm gibi, ikinci bir toplu iş dosyasını işlemek için çağıran bir for döngüsü kullanmak ve bu ikinci dosyayı taban adını aktarmaktır.

Göre /? yardım, basename şık ~ n seçeneği kullanılarak çıkarılabilir. Böylece, temel komut dosyası şunu okuyacaktır:

for %%f in (*.in) do call process.cmd %%~nf

Daha sonra process.cmd dosyasında,% 0 taban adını içerdiğini varsayın ve buna göre hareket edin. Örneğin:

echo The file is %0
copy %0.in %0.out
ren %0.out monkeys_are_cool.txt

Tek bir komut dosyasında bunu yapmanın daha iyi bir yolu olabilir, ancak her zaman toplu iş dosyasında bir döngü için birden çok komutun nasıl çekileceği konusunda biraz puslu oldum.

EDIT: Bu harika! Bir şekilde, bir FOR döngüsünde çok satırlı bloklar yapabileceğinizi gösteren dokümanlardaki sayfayı kaçırmıştım. Geri dönüp şimdi bazı toplu iş dosyalarını yeniden yazmak zorunda kalacağım ...


4

Nathans yazı üzerine genişleyen . Aşağıdakiler işi bir toplu iş dosyasında yapar.

@echo off

if %1.==Sub. goto %2

for %%f in (*.in) do call %0 Sub action %%~nf
goto end

:action
echo The file is %3
copy %3.in %3.out
ren %3.out monkeys_are_cool.txt

:end

3

Genellikle MS Sunucularında (hatırlayabildiğim kadarıyla) forfiles adı verilen bir araç vardır :

Yukarıdaki bağlantı, yardımın yanı sıra microsoft indirme sayfasına bir bağlantı içerir.


1

Aşağıdaki kod, verilen alt dize ile başlayan dosya adlarını filtreler. Alt ad alt dizesi çıkarma ve IF deyimi üzerinde çalışarak farklı ihtiyaçlara uyacak şekilde değiştirilebilir:

echo off
rem filter all files not starting with the prefix 'dat'
setlocal enabledelayedexpansion
FOR /R your-folder-fullpath %%F IN (*.*) DO (
set fname=%%~nF
set subfname=!fname:~0,3!
IF NOT "!subfname!" == "dat" echo "%%F"
)
pause

0

F.in ve f.out öğelerinin yankılanması, for / f döngüsünde kullanıldığında neyin döngü yapılacağı ve neyin döngüye girmeyeceği kavramını ayıracaktır.

::Get the files seperated
echo f.in>files_to_pass_through.txt
echo f.out>>files_to_pass_through.txt

for /F %%a in (files_to_pass_through.txt) do (
for /R %%b in (*.*) do (
if "%%a" NEQ "%%b" (
echo %%b>>dont_pass_through_these.txt
)
)
)
::I'm assuming the base name is the whole string "f".
::If I'm right then all the files begin with "f".
::So all you have to do is display "f". right?
::But that would be too easy.
::Let's do this the right way.
for /f %%C in (dont_pass_through_these.txt)
::displays the filename and not the extention
echo %~nC
)

Sormadıysanız da, komutları f.in ve f.out'a geçirmenin iyi bir yolu ...

for /F %%D "tokens=*" in (dont_pass_through_these.txt) do (
for /F %%E in (%%D) do (
start /wait %%E
)
)

Tüm Windows XP komutlarına bir bağlantı : link

Buna doğru cevap vermezsem özür dilerim. Soru okumak benim için çok zordu.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.