2011-08-09 45 views
22

Tôi muốn tạo ra một tập tin batch, batch.bat, chấp nhận 2 đối số bắt buộc:Làm thế nào để trở về thư mục gốc sau khi gọi thư mục thay đổi trong lô DOS?

  • %1 đại diện cho một đường dẫn tương đối đến thư mục hiện hành.
  • %2 đại diện cho một filaname.

Giả sử thư mục hiện tại là father\me\.

Người dùng có thể sử dụng đợt này như sau:

  • batch child/grandchild log
  • batch ../brother log

Các mô tả công việc của batch.bat là như sau.

  1. Di chuyển đến %1 thư mục,
  2. lặp tất cả *.tex tập tin trong thư mục %1.
  3. Lưu kết quả vào thư mục trước khi di chuyển.

Sau đây là mã không đầy đủ:

rem batch.bat takes 2 arguments. 
cd %1 
dir /b *.tex > <original directory>\%2.txt 

Làm thế nào để trở về thư mục gốc sau khi cách gọi thay đổi thư mục trong DOS batch?

Trả lời

34

Nếu bạn muốn RETURN về thư mục gốc, thực hiện thay đổi đầu tiên với PUSHD và quay lại với POPD. Đó là, di chuyển đến thư mục% 1 phải đạt được với

PUSHD %1 

thay vì CD% 1, và sự trở lại đạt được với

POPD 

thay vì CD ở đâu?

Nếu bạn muốn truy cập vào thư mục gốc sau khi thay đổi nó, lưu nó trong một biến theo cách này:

SET ORIGINAL=%CD% 

và sử dụng% ORIGINAL% sau, ví dụ:

dir /b *.tex > %original%\%2.txt 
+7

+1: bổ sung pushd được sử dụng để CD vào ổ đĩa gắn mạng, vì CD sẽ không cho phép bạn. – Mechaflash

+2

Lời nhận xét đó ở đâu một năm trước khi tôi đang sử dụng hàng loạt và phải làm việc xung quanh các ổ đĩa được nối mạng? +100 nếu tôi có thể – WernerCD

1

Bạn có thể luôn đặt% cd% thành biến trước khi thay đổi thư mục:

set current="%cd%" 
cd "C:\Some\Other\Folder" 
cd "%current%" 

Trong hầu hết các trường hợp, tạo biến với thư mục được sử dụng trong Batch Scripts. Nếu kịch bản là bán dài, tôi sẽ xác định các biến của tôi ở đầu tập lệnh bao gồm các đường dẫn, tệp, subs và/hoặc các lệnh dài quan trọng.

@ECHO OFF 
REM Variables 
::Programs 
SET save_attachments=C:\Program Files\APED\Program\save_attachments.vbs 
SET sendemail=C:\Program Files\APED\Program\sendkeys.vbs 
SET tb=C:\Program Files\Mozilla Thunderbird\thunderbird.exe 
SET fox=C:\Program Files\Foxit Software\Foxit Reader\Foxit Reader.exe 
SET spool=C:\WINDOWS\system32\PRNJOBS.vbs 

::Directories 
SET new=C:\Program Files\APED\New 
SET printing=C:\Program Files\APED\Printing 
SET finish=C:\Program Files\APED\Finish 
SET messages=C:\Program Files\APED\Script_Messages 
SET nonpdf=C:\Program Files\APED\NonPDFfiles 
SET errorfiles=C:\Program Files\APED\Error Files 

::Important Files 
SET printlog=C:\Program Files\APED\Script_Messages\PrintLOG.txt 
SET printemail=C:\Program Files\APED\Script_Messages\EmailPrintLOG.txt 
SET errorlog=C:\Program Files\APED\Script_Messages\ErrorLOG.txt 
SET erroremail=C:\Program Files\APED\Script_Messages\EmailErrorLOG.txt 
SET movefiles=C:\Program Files\APED\Script_Messages\MoveFiles.txt 

Tuy nhiên, PUSHD và POPD là các giải pháp tuyệt vời nếu nó ngắn và ngọt.

11

Chắc chắn PUSHD/POPD là cách ưu tiên để thực hiện việc này. Nhưng có một tính năng (không có giấy tờ?) Của SETLOCAL/ENDLOCAL hoàn thành điều tương tự (ngoài mọi thứ khác mà SETLOCAL làm).

Nếu bạn thay đổi thư mục sau SETLOCAL, thì bạn sẽ trở lại thư mục gốc khi ENDLOCAL.

cd OriginalLocation 
setlocal 
cd NewLocation 
endlocal 
rem we are back to OriginalLocation 

Một điều khác với setlocal rằng tài liệu - Bất kỳ setlocal trong vòng một được gọi là lô hay: thói quen nhãn sẽ được chấm dứt với một endlocal ngầm lúc đi ra khỏi hàng loạt hoặc thói quen. ENDLOCAL ẩn sẽ trở lại thư mục gốc giống như một ENDLOCAL rõ ràng.

cd OriginalLocation 
call :ChangeLocation 
rem - We are back to OriginalLocation because :ChangeLocation did CD after a SETLOCAL 
rem - and there is an implicit ENDLOCAL upon return 
exit /b 

:ChangeLocation 
setlocal 
cd NewLocation 
exit /b 

Tôi sẽ không khuyên bạn sử dụng SETLOCAL/ENDLOCAL thay vì PUSHD/POPD. Nhưng đó là một hành vi bạn nên biết.

Response to comment johnny của

Nó có thể gây nhầm lẫn khi pushd/popd và setlocal/endlocal được kết hợp. Các endlocal không không rõ ràng pushd chồng, bằng chứng là sau:

setlocal 
cd test 
@cd 
pushd new 
@cd 
endlocal 
@cd 
popd 
@cd 

--OUTPUT--

D:\test>setlocal 

D:\test>cd test 
D:\test\test 

D:\test\test>pushd new 
D:\test\test\new 

D:\test\test\new>endlocal 
D:\test 

D:\test>popd 
D:\test\test 
+0

@johnny - Không đúng (ít nhất là không đúng trên Win 7 nơi tôi đã thử nghiệm). Ngăn xếp pushd được giữ nguyên. Xem câu trả lời cập nhật của tôi. – dbenham

+0

xấu của tôi; Tôi thề rằng tôi đã kiểm tra nhiều lần trước khi đăng bài (vì nó có vẻ lạ), nhưng tôi đã xóa các kịch bản thử nghiệm của mình khi tôi hoàn thành chúng và bây giờ không thể lặp lại những gì tôi nghĩ ... tôi đã thấy ... chưa từng có pushd/popd trong kịch bản hoặc các chương trình con vẫn có thể là một vấn đề, mặc dù ... – johnny

4
set ORIGINAL_DIR=%CD% 

REM #YOUR BATCH LOGIC HERE 

chdir /d %ORIGINAL_DIR% 
Các vấn đề liên quan