【问题标题】:Text-based loading bar when running Java in command prompt?在命令提示符下运行 Java 时基于文本的加载栏?
【发布时间】:2011-03-14 15:08:55
【问题描述】:

我只是想知道当我使用批处理文件运行我的程序时,是否有一种方法可以使用System.out.println(); 或其他方法来创建一个很酷的加载栏。

这里真正的问题是如何使这个栏看起来好像只打印在一行上。

我不希望它像下面那样分布在多行中:

[aaaaaccccccccccccccc] 25%
[aaaaaaaaaacccccccccc] 50%
[aaaaaaaaaaaaaaaccccc] 75%

一个干净整洁的地方会让事情变得更清洁和友好。

非常感谢,

贾斯蒂安

编辑:

好的。我设法在这里找到了这个链接:How to animate the command line?,但答案是:

  1. 适用于 C++,而不是 Java
  2. 在 Java 中似乎效率不高,必须在循环中退格每一行?

在 Java 中有没有更好的方法来做到这一点?

编辑:

这就是我最终的结果:

static final int PROGRESSBAR_LENGTH = 20;

public static void drawProgressBar(int numerator, int denominator) {
    int percent = (int) (((double) numerator / (double) denominator) * 100);

    String bar = "[";
    int lines = round((PROGRESSBAR_LENGTH * numerator) / denominator);
    int blanks = PROGRESSBAR_LENGTH - lines;

    for (int i = 0; i < lines; i++)
        bar += "|";

    for (int i = 0; i < blanks; i++)
        bar += " ";

    bar += "] " + percent + "%";

    System.out.print(bar + "\r");
}

private static int round(double dbl) {
    int noDecimal = (int) dbl;
    double decimal = dbl - noDecimal;

    if (decimal >= 0.5)
        return noDecimal + 1;
    else
        return noDecimal;
}

样本输出:

[||||||||||||||||....] 80%(. = 空格)

【问题讨论】:

  • 我明白你为什么认为这是重复的,但我的问题肯定更具体。我可能无需使用额外的类就可以完成这项任务。
  • 此方法可能有效:stackoverflow.com/questions/852665/…。我花了一秒钟才考虑搜索“进度条”而不是“加载条”。 >>
  • 我最终制作了一个更高级的加载栏,它支持多个进程(循环)。它将流程分割成多个部分(以 2D 数组的形式组织),然后对各个部分进行处理,直到全部完成。

标签: java batch-file jar


【解决方案1】:

我已经使用退格方法完成了这个 - 它似乎工作正常。

只需使用System.out.print() 而不是System.out.println()——这样您就不会得到回车。

您需要跟踪需要打印多少个退格键,但它工作正常。

顺便说一句 - 要在 java 中打印退格,请使用:

System.out.print("\b");

【讨论】:

  • 不过,这似乎是一个记忆猪。如果这个过程需要时间,为什么要用加载条进一步减慢它?
  • 我不明白你所说的内存猪是什么意思。这如何使用任何额外的内存?也许一两个字节用于存储退格的数量..但真的.. 2个字节?如果您担心这种内存限制,您可能应该使用汇编,而不是 Java。另外 - 是的 - 更多的 CPU 周期.. 但同样,非常少。如果您担心几个额外的 CPU 周期,您可能根本不想打印进度。
  • 是的,我的意思是周期。道歉。与其说它会导致很多滞后,不如说显然有比那个额外循环更好的方法。 "\r" 方法效果更好。感谢您的帮助,无论如何。 :)
【解决方案2】:

作为打印退格字符的替代方法,您可以使用回车符:13(十进制)、0xD(十六进制)或 \r(转义字符)。

一共有三个规定:

  1. 您不能超出控制台宽度(80 个字符宽度可能是一个安全的假设)
  2. 每次迭代都必须打印与前一次迭代一样多的可见字符。
  3. 当您想继续前进时(当您完成加载栏或其他内容时),您需要以换行符开头,否则您将开始用新文本覆盖现有的加载栏。

所以,大致是这样的:

public static void loadMyProgram() {
    while(programStillLoading) {
        doSomeLoading();
        double loadFraction = howCloseToDone(); // A number between 0 and 1

        System.out.print("[");
        int i = 0;
        for( ; i < (int)(loadFraction * 20); i++)
            System.out.print("=");
        for( ; i < 20; i++)
            System.out.print(" ");
        System.out.print("] " + (int)(loadFraction * 100) + "%");

        System.out.print((char)13);
        //System.out.print((char)0xD); // Same as above, but in hex
        //System.out.print("\r"); // Same as above, but as the symbol
    }

    System.out.println();
}

上面将打印[&lt;bar&gt;] &lt;percent&gt;%,其中&lt;bar&gt;0..p '=' 后跟0..(20-p) ''。它将保留在一行上。

假设您计算的负载百分比是单调递增的(换句话说,它不像 Windows 加载栏,在 3 秒内从 20% 到 110% 再到 1%),您不会不必担心确保您的下一个输出等于或长于您之前的输出,因为这始终是正确的。但是,在这种情况下,您可以在“%”之后使用两个空格来处理它。

【讨论】:

【解决方案3】:

这可能是一个开始的地方。

用法:

ProgressBar pb = new ProgressBar(10,1);
while (loadingStuff) {
  doStuff();
  pb.update();
}
pb.finish();

班级:

public class ProgressBar {
    
      private static String[] s;
      private int pos, increment, size;
    
      public ProgressBar(int size, int increment) {
        this.size = size;
        this.increment = increment;
        s = new String[size+2];  
        Arrays.fill(s,"a");
        s[0] = "[";
        s[size+1] = "]";
      }
    
      public void update() {
          System.out.println('\r');
          if (pos+inc<size+2) {
              Arrays.fill(s,pos,pos+inc,"c");
              pos += inc;
          }
          for (String ch : s) {
              System.out.print(ch);
          }  
      }
    
      public void finish() {
          System.out.println();
      }
}

【讨论】:

  • 修复你的课程:PorgressBar=ProgressBar , inc=increment
  • 也没有启动方法。
  • @Derrops 谢谢 - 这只是一个让他们开始的例子,但解决了你提到的那些问题。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-05-15
  • 1970-01-01
  • 2019-11-13
  • 2013-06-27
  • 1970-01-01
  • 2015-10-21
  • 2014-03-18
相关资源
最近更新 更多