Toplu iş dosyasından komut çıktısında aynı satırın üzerine yazma


13

Bir şey yaptığımda son satırın yerini alan bazı durum bilgileri yazmak istiyorum.

Aşağıdaki örnek bat dosyasında, metnin komut çıktısında aynı satıra Step 2yazılmasını istiyorum Step 1.

echo off

echo Step 1
REM Do some stuff...

echo Step 2
REM do some other stuff...

Yanıtlar:


8

Bu komut dosyası tam olarak sorduğunuz şeyi yapacak:

@echo off

setlocal enableextensions enabledelayedexpansion
for /f %%a in ('copy /Z "%~dpf0" nul') do set "ASCII_13=%%a"

set /p "=Step 1" <NUL
REM Do some stuff...

set /p "=!ASCII_13!Step 2" <NUL
REM do some other stuff...

Bu cevabı, Dave Benham tarafından CharLib adlı bir toplu senaryo karakter manipülasyon kütüphanesindeki koda bakarak buldum .

Bu kütüphane, 1..255 aralığındaki tüm karakterleri oluşturabilir.

Daha fazla bilgi için "Bir karakteri ASCII değerine dönüştürmek mümkün mü?"

Edit 2017-4-26: Yukarıdaki kod artık çalışmıyor gibi görünüyor . Bu davranışın ne zaman değişeceğinden emin değilim, ama kesinlikle işe yaradı. Bundan CRsonraki karakter komut =tarafından kaldırılır set. Ah, setXP ve Windows'un sonraki sürümleri arasında çalışma biçiminde bir değişiklik gibi görünüyor . Windows toplu iş dosyasında satırın üzerine yaz'daki mükemmel yanıtı görüyor musunuz? (çoğalt) ve daha fazla kod örneği için.

O zaman bir alternatif, önüne boşluk olmayan bir karakter koymak !ASCII_13!ve silinmesini de ayarlamaktır, belki de bir arka boşluk (soyulmadan) ve ardından bir boşluk ekleyerek veya satırın sonuna boşluk ekleyerek bilgi istemi dizesi (soyulmamış.)

Örneğin şöyle:

@echo off

setlocal enableextensions enabledelayedexpansion
for /f %%a in ('copy /Z "%~dpf0" nul') do set "ASCII_13=%%a"

set /p "=Step 1" <NUL
REM Do some stuff...

set /p "=x!ASCII_13!Step 2 " <NUL
REM do some other stuff...

2
Benim için, bu sadece ekranda "Adım 2" yerine "Adım 1 Adım 2" yazdırır.
galmok

@galmok Bu da benim başıma başladı, ama emin değilim (Ben mükemmel açıkladığınız davranışıyla değişti. Son zamanlarda koymak iş için kullanılan bir komut dosyası var gibi) için hiç kullanılmamış O görünen setkomut artık herhangi şeritler CR ve LF karakterleri (boşlukların yanı sıra) =. Arasında bir boşluk olmayan karakter koyarak deneyin =ve!ACSII_13!
timfoden

Tüm bunları yapmanın bir yolu var ... Aslında başka birinin fark edip etmediğini görmek için geldim, çünkü ne kadar ileri gittiğini keşfettiler mi görmek istedim. ... Yığın taşmasına CEVAP yazabilir miyim? VEYA .. bir Soru gibi ve hemen cevap? Sanırım onunla ne yapabileceğiniz hakkında soru formunda yazabilirim .. Bir şeyler yemeye gitmem gerekiyor ama bunu sizin için bir linkle güncelleyeceğim.
Brent Rittenhouse

ASCII_13 yazın! sıyırma önlemek için Adım 1 sonra, bu nedenle adım 2 kod:set /p "=Step 2 " <NUL
Zimba

6

Soruyu cevaplamak için:

@echo off
CALL :EVALUATE "chr(8)"
SET backspace=%result%
<nul set /p =Step 1
:: DO SOME STUFF....
<nul set /p =%backspace%
<nul set /p =2
:: DO SOME OTHER STUFF....
<nul set /p =%backspace%%backspace%%backspace%%backspace%%backspace%%backspace%
<nul set /p =End   
GOTO:EOF



:EVALUATE           -- evaluate with VBS and return to result variable
::                  -- %~1: VBS string to evaluate
:: extra info: http://groups.google.com/group/alt.msdos.batch.nt/browse_thread/thread/9092aad97cd0f917

@IF [%1]==[] ECHO Input argument missing & GOTO :EOF 

@ECHO wsh.echo "result="^&eval("%~1") > %temp%\evaluate_tmp_67354.vbs 
@FOR /f "delims=" %%a IN ('cscript //nologo %temp%\evaluate_tmp_67354.vbs') do @SET "%%a" 
@DEL %temp%\evaluate_tmp_67354.vbs
::ECHO %result%
@GOTO:EOF

Çıktı:

End

Temelde, script ne işe yaradığı yazıyor ise Step 1o zaman, geriye tek bir yerde, üzerine yazar gider 1ve sonunda tamamen geri üzerinde yazma gider Step 2ile End.

Bu geri dönme özel ASCII karakteri 8 ile geri yapacağım. Ben cmd yazmak nasıl bilmiyorum, çünkü VBS Chr () işlevini çalıştıran ve geri boşluk karakteri değişkene koyar: EVALUATE işlevini kullanın result. Birisi daha iyi bir yol biliyorsa, lütfen tavsiye edin.


1
PowerShell'de, $host.ui.RawUI.CursorPositionimlecin bulunduğunuz yere geri dönmesini ve çıktınızın üzerine yazmasını sağlamak için bir değişkende depolayıp daha sonra geri yükleyebilirsiniz. PowerShell için sadece bir seçenek, ama VBS şeylerinizden biraz daha temiz olabilir :-)
mihi

4
@echo off
for /F "tokens=1 delims=# " %%a in ('"prompt #$H# & echo on & for %%b in (1) do rem"') do set "BSPACE=%%a"
<nul set /p =Step 1
ping 127.0.0.1 >nul
<nul set /p =%BSPACE%
<nul set /p =2
ping 127.0.0.1 >nul
<nul set /p =%BSPACE%
<nul set /p =3
ping 127.0.0.1 >nul
<nul set /p =%BSPACE%%BSPACE%%BSPACE%%BSPACE%%BSPACE%%BSPACE%
<nul set /p =End.  
pause

AÇIKLAMA:

for /F "tokens=1 delims=# " %%a in ('"prompt #$H# & echo on & for %%b in (1) do rem"') do set "BSPACE=%%a"

bu, backspace karakterini BSPACE değişkenine ayarlar. Şimdi sonucu görmek için şunu yazın:

echo ab%BSPACE%c

çıktı: ac

birden fazla karakteri silmek için bu BSPACE değişkenini bir kereden fazla kullanabilirsiniz.

Şimdi, bir değişkende satır başı ayarlamak istiyorsanız şunu kullanın:

for /F "usebackq" %%a in (kopyala / Z "% ~ dpf0" boş) DO (set "cr=%%a")

sonucu görmek için şunu yazın: setlocal EnableDelayedExpansion & echo asfasdhlfashflkashflksa!CR!***

çıktı: ***asfasdhlfashflkashflksa

@ davour'un cevabı da çok güzel ama @ timfoden'in cevabı benim için çalışmadı.


@ timfoden'ın cevabı işe yaramadı çünkü! CR! önceki adımın sonuna gitmelidir. Ayrıca, tüm bu% BSPACE% s yerine! CR! ve boşluklarla doldurun:set /p "=.!CR!End. " <NUL&echo:
Zimba

3

Yapamazsın. Genellikle bu tür bir şey, imleci aynı satırdaki ilk sütuna geri getirecek bir satırbaşı karakteri (0x0D) ekleyerek dosyaya ulaşabilirsiniz. Ancak bu durumda işe yaramıyor; CR sadece sessizce yenir.

Dahası, CR'yi içeri almak biraz zor ve en azından burada bir metin editörü içeriyordu. Bunu sizin için yapacak küçük bir yardımcı program yazmanızı öneririm, aslında çok zor değil. Aşağıdaki küçük C programı yeterli olabilir (Unicode'a ihtiyacınız yoksa):

#include <stdio.h>

int main(int argc, char* argv[]) {
  if (argc < 2) return 1;
  printf("\r%s", argv[1]);
}

CR karakteri ve ardından ilk argüman olarak belirttiğiniz metni yazdırmaktan başka bir şey yapmaz. Kullanım aşağıdaki gibi:

@echo off
<nul set /P X=Step 1
pause>nul 2>nul
over.exe "Step 2"

Son satır, o programa yapılan çağrıdır. İkinci satır, sondaki satır sonu olmadan metin yazdırmak için normal toplu iş deyimidir (aksi takdirde satırın üzerine yazamadığınız için bu durumda önemlidir). Yine de yukarıdaki programı da o yerde kullanabilirsiniz.

Hafif bir hacky yolu, ancak nerede sonuçlandıracağınızdan emin olabileceğiniz tek yol, clsadım çıktınızdan önce kullanmak olacaktır . Titreyecek ama bu şekilde daima sol üst tarafa yazacaksınız. Ve konsolda görünür olan her şeyi titriyor (bu yüzden tavsiye etmem); çoğu kullanıcı bunu çok sevmez.


Tamam, temiz komut satırı ile yapmanın mümkün olmadığından şüphe duydum. Bunu yapmak için bir yardımcı program yapmak istersem, her şeyi bir yardımcı programa koyabilirim. Gerçekten istediğim, 5 saniye bekleyip bitene kadar her saniyeyi geri sayan görünür bir geri sayımdı.
huşu

4
huşu: Eğer Vista ya da daha yenisiyseniz, o timeout 5zaman çalışacaktır.
Joey

Harika! teşekkür ederim! zaman aşımı 5 çalışıyor!
korku

4
Gerçek sayımı ilk kez yayınlamalıydım ...
awe

Tabi ki yapabilirsin; sadece adım 1'den sonra satır başı ekleyin! Ayrıca, metin editörü olmadan satır başı almak için bazı kodlar:for /f %%a in ('copy /Z "%~f0" nul') do set "CR=%%a"
Zimba

1

Yeni satır karakteri alın, bir sonraki adımı yazın, satırın başına geri dönün, sonraki satırı yazın:

@echo off
cls
setlocal enabledelayedexpansion
echo Here's how it's done:

for /f %%a in ('copy /Z "%~f0" nul') do set "Newline=%%a"
set /p "=Step 1!Newline!" <NUL
REM Do some stuff...
ping -n 2 localhost > nul
set /p "=Step 2!Newline!" <NUL
ping -n 2 localhost > nul
set /p "=Step 3 " <NUL
REM do some other stuff...
ping -n 2 localhost > nul
echo:
echo Done.

Bu yalnızca Step 1 Step 2 Step 3hepsi aynı uzunlukta olduğunda çalışır. Aksi takdirde ilk metin set /pkalır. Bunu nasıl düzelteceğinizden emin değilim.
Ste

Bu sorun, sonraki istemde ek boşluk karakterleri kullanılarak giderilebilir. önceki karakterleri kapsamak için. Bunun set /p "=Step 2SPACESPACESPACESPACE!Newline!" <NUL aksine örnekset /p "=Step 2!Newline!" <NUL . Değiştirin SPACEkarakter için.
Ste

Önceki satırlar daha uzunsa, fazladan karakterleri boşaltmak için boşluk ekleyin veya satır sonundan başlayarak geri tuşuna veya yalnızca ekstra karakterlere geri alın.
Zimba

0

Sen gibi bir ekran-imleç kitaplığı gerekiyordu cursesya ncurses, ama onların kullanımı ile aşırı aşina değilim. Her iki kütüphane Unix sistemleri için geliştirilmiştir, ancak bunları Windows için bulabilirsiniz ( Cygwin ortamında veya GnuWin32'de ).

DOS tarzı bir toplu iş dosyasında onlara erişmek için kolay bir yol bilmiyorum. Derlenmiş bir dilde programlama yapmak daha iyi olabilir. Yararlı olup olmayacağı konusunda daha iyi bir fikir edinmek için Ncurses NASIL belgesine bakın .


lanetler sadece terminaller ve terminal emülatörleri içindir. Gerçekten Windows'un yerel konsol API'siyle eşleşmezler.
Joey

Harici kütüphanelere gerek YOK; CMD araçlarıyla iyi çalışır.
Zimba

0

Çözüm 1

Notepad ++ ile ASCII Kodları Ekleme Panelini (Düzenle> Karakter Paneli) Backspace ←kullanarak karakteri (ASCII 0x08) doğrudan eklemek mümkündür .

Benim çözümüm [BS]karakteri doğrudan eklemek ve daha sonra, burada yayınlanan diğer çözümler gibi, önceki karakterleri silmek için birden çok kez kullanmaktır:

kod

@ECHO OFF

SET "BACKSPACE_x7=[BS][BS][BS][BS][BS][BS][BS]"

SET /P "DUMMY_VAR=Step 1" < NUL
REM Do some stuff...

SET /P "DUMMY_VAR=%BACKSPACE_x7%Step 2" < NUL
REM Do some other stuff...

GOTO :EOF

Notepad ++ ekran görüntüsü

Windows toplu işinin üzerine yazma


Çıktı

CMD çıkışı


Çözüm 2

Başka bir olasılık, bir unicode karakter (U + 000D) olarak eklemek için cecho (renk desteğine sahip echo komutu Carriage Return ↵) kullanmaktır:

kod

@ECHO OFF

SET CARRIAGE_RETURN={\u000D}

cecho Step 1
REM Do some stuff...

cecho %CARRIAGE_RETURN%Step 2
REM Do some other stuff...

GOTO :EOF

Not: cecho_x64.exeMakinemde olduğundan çok daha hızlı çalışır cecho.exe.

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.