2013-12-17 14 views
1

根據我的研究,Perl打印語句中使用的'\ b'字符應該像「退格」一樣,即將光標移回一個字符,並刪除當前字符。出於這個原因,我打算使用此操作在單行上打印操作狀態,並隨着操作的進行而更新。不過,我注意到,雖然光標確實回退,但腳下的字符不會被刪除,因此在較短的打印語句後仍會留有較長的消息。我編了下面的示例代碼來解釋我的發現:perl中的' b'字符是如何工作的?

#!/usr/bin/perl 

use strict; 
use warnings; 
my $m; 

#set to nonzero so that the screen will update before \n 
local $| = 1; 

print "Current number shown: "; 

$m = "LONG MESSAGE TEMP"; 
print $m; 
print "\b" x length($m); 

foreach(1..22) { 
     $m = $_; 
     print $m; 
     print "\b" x length($m); 
     #sleep 1; #Uncomment to see updates 
} 

print "\n"; 

這是輸出:

Current number shown: 22NG MESSAGE TEMP

如果這確實是「\ B」的正確操作,是有另一種刪除字符以及移回光標的逃生?我想避免使用從當前行開始處開始的'\ r'。否則,我如何錯誤地使用轉義?

+1

這不是Perl的功能。 Perl會輸出八位字節,這取決於他們做任何他們想做的事情。 –

+0

重要說明:'\ b'在perl regex中有完全不同的含義。 –

回答

3

"\b"是寫chr(0x08)的只是一種奇特的方式。您的終端可能會移動光標而不是顯示任何內容,但這完全取決於它。

如果你可以依靠它,那麼你可以通過用空格覆蓋來實現你想要的。

my $last_length = 0; 
sub update { 
    my ($s) = @_; 
    print("\b" x $last_length); 
    print(" " x $last_length); 
    print("\b" x $last_length); 
    print($s); 
    $last_length = length($s); 
} 

或者用更少的閃爍:

my $last_length = 0; 
sub update { 
    my ($s) = @_; 
    my $diff = $last_length - length($s); 
    print("\b" x $last_length); 
    print($s); 
    print(" " x $diff); 
    print("\b" x $diff); 
    $last_length = length($s); 
} 
1

只輸出一些額外的空格字符來覆蓋你需要覆蓋的東西。

#!/usr/bin/env perl 

use strict; 
use warnings; 
use Time::HiRes qw(sleep); 

sub backspace { 
    print "\b" x $_[0]; 
    print " " x $_[0]; 
    print "\b" x $_[0]; 
} 

local $| = 1; 

my $m = "LONG MESSAGE TEMP"; 

print "Current number shown: ", $m; 
sleep 1; 

for (1..22) { 
    backspace(length($m)); 
    $m = $_; 
    print $m; 
    sleep 0.2; 
} 

print "\n"; 
1

取決於如何使用它,\ b的有一個Perl命令中有特殊的含義:

\ b是退格字符只有內一個角色類。在字符類外,\ b單獨是一個字 - 字/非字 - 字符邊界。

要替換「DEF」單詞「ABC」的每次出現在文件中,使用Perl命令: perl -pi -e 's/\bABC\b/def/g' file 這將留下字符串,如「ZABCD」不變。