Mengisi Array dalam Script Batch DOS

33

Bagaimana saya bisa mengatur variabel array dalam skrip batch DOS? Saya ingin memuatnya dengan daftar nama file untuk diproses. Saya benar-benar ingin membuat ini sesederhana mungkin. Terima kasih.

Jim Fell
sumber
1
Apakah Anda benar - benar harus kompatibel dengan DOS, atau dapatkah Anda menggunakan PowerShell?
Brian Knoblauch
1
Anda juga dapat menggunakan vbscript dengan mudah untuk ini ...
JNK
@ Brian: DOS diperlukan. Lihat solusi yang saya posting.
Jim Fell
Jika Anda tidak memiliki rambut maka Anda tentu harus tahu perbedaan antara command prompt dan DOS
barlop

Jawaban:

48

Saya menemukan jawabannya:

set FILE_LIST=(file1.dll file2.exe file3.dll file4.dll file5.dll)

set BIN_PATH="C:\Program Files\My App Folder\bin"
set BAK_PATH="C:\Program Files\My App Folder\bin\Backups"
set DEV_PATH="C:\My Dev Path\bin\Debug"

for %%i in %FILE_LIST% do copy %BIN_PATH%\%%i %BAK_PATH%
for %%i in %FILE_LIST% do copy %DEV_PATH%\%%i %BIN_PATH%

Saya melakukan sesuatu seperti ini beberapa tahun yang lalu, jadi hanya perlu beberapa perhitungan. (Btw, saya benci menciptakan kembali roda.) Sekarang sudah diposting di sini, semoga orang lain akan merasakan manfaatnya juga.

Jim Fell
sumber
1
Yah, saya tidak pernah tahu Anda bisa melakukan itu! Saya mencobanya dan berhasil!
Linker3000
Ini tidak mungkin bekerja di DOS. DOS tidak melakukan nama file yang panjang (hanya 8.3), dan seingat saya, DOS juga tidak mengutip dalam path file. Saya tidak memiliki instalasi MS-DOS yang berguna untuk melihat apakah mendukung array menggunakan ()sintaks.
CVn
3
Meskipun ini berfungsi untuk tujuan Anda, perlu dicatat bahwa ini bukan array. Ini hanya string yang sedang dipecah menjadi elemen-elemen individual. Anda tidak dapat merujuk elemen secara langsung dengan melakukan sesuatu seperti FILE_LIST[0].
aforia
@ MichaelKjörling: FreeDOS dapat mendukung LFN dan mungkin kutipan, jadi mungkin dia menggunakan itu?
Nathan Tuggy
@NathanTuggy Poin bagus. Namun, akan lebih baik jika itu dibuat eksplisit.
CVn
12

Ya, Anda dapat melakukan array dalam batch. Meskipun mereka tidak persis seperti array di C atau VB, Anda BISA melakukannya:

@echo off
setlocal enabledelayedexpansion

set  arrayline[0]=############
set  arrayline[1]=#..........#
set  arrayline[2]=#..........#
set  arrayline[3]=#..........#
set  arrayline[4]=#..........#
set  arrayline[5]=#..........#
set  arrayline[6]=#..........#
set  arrayline[7]=#..........#
set  arrayline[8]=#..........#
set  arrayline[9]=#..........#
set arrayline[10]=#..........#
set arrayline[11]=#..........#
set arrayline[12]=############

::read it using a FOR /L statement
for /l %%n in (0,1,12) do (
echo !arrayline[%%n]!
)
pause
Patrick Jackson
sumber
1
itu luar biasa dan menginspirasi .. saya baru saja melakukan jawaban yang dibangun di atas itu dan mengisi array juga
barlop
7

Dari Blog Jakash3, Array di Batch menjelaskan cara mengemulasi array di command prompt.

File batch bernama array.bat termasuk dalam artikel, yang berisi pustaka fungsi yang digunakan untuk menangani array. Anda harus memilih teks dalam artikel dan menempelkannya di dalam file bat.

Misalnya, skrip pengujian berikut:

@echo off
set book[0]=Avatar
set book[1]=The Green Mile
set book[2]=The Count of Monte Cristo
call array.bat add book Babo
call array.bat len book length
echo I have %length% books you can borrow.
echo Pick one:
echo.
echo 0) Avatar
echo 1) The Green Mile
echo 2) The Count of Monte Cristo
echo 3) Babo
echo.
set /p pick=
call array.bat getitem book %pick% title
echo.
echo You picked %title%.

menghasilkan output berikut:

gambar

harrymc
sumber
1
ok meskipun Anda belum mencantumkan konten array.bat meskipun saya melihatnya agak panjang
barlop
4

Ini mengisi array dan mencetaknya

Anda bisa menggunakan names1 names2 names3, daripada nama [1] nama [2] nama [3] dengan menulis nama! I! alih-alih nama [! i!]. Ini menghasilkan array dengan menghasilkan nama variabel. Tidak ada struktur array dalam kumpulan. Tapi itu serapi struktur susunan apa pun, dan mempopulasikan atau mencetak tampak persis seperti bagaimana seseorang akan mengisi atau mencetak array dalam bahasa yang tepat (yang sebenarnya memiliki struktur susunan!)

@echo off
setlocal enabledelayedexpansion enableextensions

set i=-1

for %%f in (bob, tom, joseph) do (
 set /a i=!i!+1
 set names[!i!]=%%f
)
set lastindex=!i!

for /L %%f in (0,1,!lastindex!) do ( 
  echo !names[%%f]!
)

hasil-

c:\blah>a
bob
tom
joseph

c:\blah>

Beberapa penjelasan-

Itu setlocal enabledelayedexpansion enableextensions dengan! Var! daripada% var% diperlukan untuk mencegah perilaku aneh, sehingga variabel berperilaku dengan benar ketika dalam FOR atau IF. Ini adalah keanehan dengan file batch. Lihatset /? mana itu disebutkan lebih lanjut.

Inilah yang mengisi array, dan cukup mudah bagi siapa saja yang tahu tentang array. Anda juga bisa melakukannyanames[0]=bob names[1]=tom names[2]=joseph meskipun salah satu keindahan dari sebuah array adalah kemampuan untuk mengisi sebuah array dengan sebuah loop, yang telah saya lakukan di sini.

for %%f in (bob, tom, joseph) do (
 set /a i=!i!+1
 set names[!i!]=%%f
)
set lastindex=!i!

Ini menampilkan array. %% f jika Anda mengulanginya, Anda akan melihat mulai dari 0 hingga indeks terakhir array, dalam langkah-langkah 1. sehingga akan mencetak nama [0] nama [1] nama [2]

for /L %%f in (0,1,!lastindex!) do ( 
  echo !names[%%f]!
)
barlop
sumber
0

Untuk apa yang ingin Anda lakukan, bagaimana menggunakan variabel input untuk setiap nama file, yang dapat Anda ambil dengan variabel% 1% 2 dll. Mis.: File mybat.bat file1.nam file2.nam dll.

Anda kemudian dapat menggunakan variabel-variabel ini dalam satu lingkaran tetapi hanya perlu menggunakan% 1 sebagai parameter utama karena Anda dapat menggunakan SHIFT untuk membawa variabel-variabel lain ke dalam 'posisi'% 1, melakukan tes untuk null (akhir variabel) dengan sesuatu seperti JIKA "X% 1" == "X"

misalnya:

:LOOP
IF "X%1" == "X" GOTO DONE
COPY %1 C:\TARGET.DIR
SHIFT
GOTO LOOP
:DONE
Linker3000
sumber
0

Jika Anda menyimpan daftar file ke filelist.txt, Anda bisa FORmembaca dan memproses setiap baris file, seperti

FOR /F "delims=|" %i  IN (filelist.txt) DO @echo %i

untuk mencetak setiap baris file (hingga "|" pertama dalam baris. Jika Anda tidak menentukan pembatas Anda sendiri, spasi dan tab akan digunakan, jadi kecuali jalur Anda tidak memiliki spasi, Anda perlu menentukan karakter yang tidak akan muncul dalam file untuk mendapatkan baris lengkap).

Neal
sumber
untuk / f sebenarnya adalah fitur windows 2000 dan yang lebih baru. Itu tidak di DOS.
wendy.krieger
0

Dalam salah satu komentar Anda untuk jawaban yang Anda katakan,

Saya melakukan pekerjaan pengembangan, dan karena sifat kompleks dari aplikasi setiap waktu dan ingin menguji membangun (yang sering) saya harus menyalin lima file dari direktori biner membangun ke direktori biner instal. Ini membosankan. Saat ini, saya memiliki nama file yang dikodekan ke dalam skrip batch saya, tetapi saya ingin memasukkannya ke dalam array agar skrip lebih mudah dipelihara.

Saya percaya bahwa yang Anda cari adalah Makefile, dan mungkin cygwin memberi Anda cangkang yang layak (bash, atau apa pun rasanya).

lorenzog
sumber
0

Ganti string dan huruf dalam teks.

Coba untuk loop dengan memperluas teks ke for for body dan mengganti var dengan var. Seret dan jatuhkan file teks sehingga% 1 adalah input pengguna dengan menjalankan perintah set.

@echo off
setlocal EnableDelayedExpansion
set /p a= enter letter to change:
set /p b= letter to change to:
set /p input=<%1
for /f %%c in ("!input:~!") do (
set "code=!input:%a%=%b%!"
echo !code!>myfile.txt
)
mordex
sumber
0

Sesuatu seperti ini di file batch? Pilih file dalam folder. << adalah komentar, tidak ada kode

:selectapk
SETLOCAL ENABLEDELAYEDEXPANSION      << DELAYED EXPANSION on for counter in For loop
SET /A MAXITEM=0
Echo.
Echo Found these APK files in "add_apk_here" folder.
Echo.
For %%a in (add_apk_here/*.apk) do (
 Set /A MAXITEM+=1
 Set MENUITEM!MAXITEM!=%%a        << Fill n local env vars, one for each file, called MENUITEM1...n
 Echo    !MAXITEM!. %%a
)
Echo.
If !MAXITEM!==0 Echo No APK in "add_apk_here" folder & call :delay & Goto start   << No apk files then go back
SET /P CHOICE=Select APK to work on: 
SET MENUITEM=!MENUITEM%CHOICE%!      << Get the stored filename from MENUITEMx
SETLOCAL DISABLEDELAYEDEXPANSION     << Very important for next ENDLOCAL that doesn't like the delayedexpansion var
ENDLOCAL & SET apk=%MENUITEM%        << put the local MENUITEM var into the global apk var
goto start

:delay
REM %1 like Call :delay 5
SETLOCAL
SET N=%1
If Not Defined N Set N=2
Ping -n %N% -w 1000 127.255.255.255 > nul
ENDLOCAL
Exit /b
tweakradje
sumber
0

Anda tidak dapat benar - benar melakukan array di command prompt (dan juga itu bukan DOS kecuali Anda menjalankan Windows 3.1). Namun, Anda dapat melakukan pemrosesan berbasis set dengan perintah FOR.

Untuk membuat daftar file yang akan diproses, Anda dapat secara manual membuat file teks untuk diproses, atau menggunakan dir /b <mask> perintah di dalam loop FOR.

Sesuatu yang saya pelajari dengan susah payah untuk FOR - Anda perlu menggunakan variabel SINGLE CHARACTER sebagai kursor Anda!

JNK
sumber
+1 Anda berkomentar bahwa downvote harus dijelaskan. Juga, Anda menulis "Anda harus menggunakan variabel SINGLE CHARACTER sebagai kursor Anda!" <- maksudmu
indeksmu
1
Juga perhatikan bahwa jika itu adalah boot disk Win9X, itu adalah DOS (DOS 7). Dan Windows 9X masih dikatakan berjalan di DOS. Dan Anda dapat menambahkan baris ke Saya pikir itu msdos.sys seperti bootscan = 0 dan bootgui = 0 yang akan menghentikannya boot ke Windows dan boot langsung ke DOS prompt.
barlop
0

Lihatlah dokumentasi Microsoft pada perintah FOR batch . Anda dapat menggunakan FOR untuk beralih pada satu set direktori, file dalam direktori, atau file dalam direktori dan semua sub-direktori.

Secara default, FOR menangani set atau hanya file:

FOR %f IN (*.txt) DO ECHO %f

Atau, untuk rekursif:

FOR /R %f IN (*.txt) DO ECHO %f

atau, hanya direktori:

FOR /D %d DO ECHO %d
astaga
sumber
Sayangnya, semua opsi tersebut termasuk semua untuk cakupan masing-masing. Saya melakukan pekerjaan pengembangan, dan karena sifat kompleks dari aplikasi setiap waktu dan ingin menguji membangun (yang sering) saya harus menyalin lima file dari direktori biner membangun ke direktori biner instal. Ini membosankan. Saat ini, saya memiliki nama file yang dikodekan ke dalam skrip batch saya, tetapi saya ingin memasukkannya ke dalam array agar skrip lebih mudah dipelihara.
Jim Fell
0

ini adalah file debug kecil yang saya buat beberapa saat untuk menguji berbagai te dari game tic tac tow saya di BATCH / CMD. itu bisa membaca dan menulis ke dan dari array yang akan menjadi besar dan rumit pada kode.

menggunakannya sederhana:

Menulis ke array

  1. berikan file atau modifikasi untuk mengimpor yang lain.
  2. beri nama pada array.
  3. dan Anda selesai.

Membaca dari sebuah array

  1. Berikan ukuran array atau bagian yang ingin Anda baca.
  2. Masukkan nama array dengan %% a dalam nama
  3. dan Anda selesai.

Kode:

@echo off
setlocal EnableDelayedExpansion

set ID=0

::              Reader                   ::
:: It reads the file called input.txt    ::
:: and stores it in a new variable that  ::
:: for everytime it goes over it it is a ::
:: new ID (Slot in the array).           ::

For /F %%A in (input.txt) do ( 
    set /a ID=ID+1
    set Input!ID!= %%A

    echo !ID! : %%A
)


::             Writer                     ::
:: this is to read all Slots in the array ::
:: and puts it on the screen.             ::

for /L %%a in (1,1,!ID!) do (
    echo !Input%%a!
)
pause>nul
Elforax
sumber