سؤال

برنامجي (الذي يحدث أن يكون في بيرل ، على الرغم من أنني لا أعتقد أن هذا السؤال هو بيرل محددة) إخراج رسائل الحالة عند نقطة واحدة في برنامج النموذج Progress: x/yy أين x و yy هي رقم ، مثل: Progress: 4/38.

أرغب في" الكتابة فوق " الإخراج السابق عند طباعة رسالة حالة جديدة حتى لا أقوم بملء الشاشة برسائل الحالة.حتى الآن ، لقد حاولت هذا:

my $progressString = "Progress\t$counter / " . $total . "\n";
print $progressString;
#do lots of processing, update $counter
my $i = 0;
while ($i < length($progressString)) {
    print "\b";
    ++$i;
}

لن تتم طباعة حرف مسافة للخلف إذا قمت بتضمين سطر جديد في $progressString.إذا تركت السطر الجديد ، ومع ذلك ، يتم مسح المخزن المؤقت الإخراج أبدا ولا شيء يطبع.

ما هو الحل الجيد لهذا?

هل كانت مفيدة؟

المحلول

استخدام أوتوفلوش مع ستدوت:

local $| = 1; # Or use IO::Handle; STDOUT->autoflush;

print 'Progress: ';
my $progressString;
while ...
{
  # remove prev progress
  print "\b" x length($progressString) if defined $progressString;
  # do lots of processing, update $counter
  $progressString = "$counter / $total"; # No more newline
  print $progressString; # Will print, because auto-flush is on
  # end of processing
}
print "\n"; # Don't forget the trailing newline

نصائح أخرى

قل

$| = 1

في مكان ما في وقت مبكر من البرنامج الخاص بك لتشغيل أوتوفلوشينغ على المخزن المؤقت الإخراج.

ضع في اعتبارك أيضا استخدام "\ص" لتحريك المؤشر مرة أخرى إلى بداية السطر ، بدلا من محاولة حساب عدد المسافات التي تحتاج إلى الرجوع إليها بشكل صريح.

كما قلت، لا تطبع سطرا جديدا أثناء تشغيل عداد التقدم وإلا ستطبع تقدمك في سطر منفصل بدلا من الكتابة فوق السطر القديم.

أعلم أنه ليس تماما ما طلبته ، ولكن ربما أفضل.لقد حدث على هذه المشكلة نفسها وذلك بدلا من التعامل معها كثيرا ذهب إلى استخدام Term::ProgressBar التي تبدو لطيفة جدا.

يمكنك أيضا استخدام رموز الهروب أنسي للسيطرة مباشرة على المؤشر.أو يمكنك استخدام مصطلح:: مفتاح القراءة أن تفعل الشيء نفسه.

كان علي أن أتناول شيئا مشابها لهذا اليوم.إذا كنت لا تمانع في إعادة طباعة السطر بأكمله ، فيمكنك القيام بشيء من هذا القبيل:

print "\n";
while (...) {
     print "\rProgress: $counter / $total";
     # do processing work here
     $counter++;
}
print "\n";

الحرف" \ ص " هو عودة النقل-فإنه يجلب المؤشر مرة أخرى إلى بداية السطر.بهذه الطريقة ، أي شيء تقوم بطباعته يستبدل نص إشعار التقدم السابق.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top