【问题标题】:Convert milliseconds to human readable time lapse将毫秒转换为人类可读的时间间隔
【发布时间】:2012-04-03 13:04:19
【问题描述】:

我想以人类可读的格式格式化一些命令执行时间,例如:

3 -> 3ms
1100 -> 1s 100ms
62000 -> 1m 2s
etc ..

考虑到天、小时、分钟、秒……

可以使用C#吗?

【问题讨论】:

  • 基本上你只需要使用模和除法。
  • new TimeSpan(30000).ToString() 怎么样?
  • 好吧,我问是因为我在公司还有其他事情要做,比基本的编程练习更好;-)
  • @DanielPeñalba:那么,与其问是否可以使用 C#(是的,可以),不如问“是否有现成的类可以做到这一点?”
  • 所以您基本上是在要求TimeSpan.Format 自定义字符串不会导致“0 年 0 个月 0 天 0 小时 0 分钟 1 秒 100 毫秒”?

标签: c# .net format timespan


【解决方案1】:

您可以使用 TimeSpan 类,如下所示:

TimeSpan t = TimeSpan.FromMilliseconds(ms);
string answer = string.Format("{0:D2}h:{1:D2}m:{2:D2}s:{3:D3}ms", 
                        t.Hours, 
                        t.Minutes, 
                        t.Seconds, 
                        t.Milliseconds);

和我刚刚找到的这个帖子很相似:

What is the best way to convert seconds into (Hour:Minutes:Seconds:Milliseconds) time?

【讨论】:

  • 这将产生00h:00m:00s:003ms 而不是3ms 作为输入3,所以我不认为这正是OP想要的;)
  • @Nuffin,他总是可以根据自己的需要更改代码;)我刚刚提供了一个示例...
【解决方案2】:

我知道这是旧的,但我想用一个很棒的 nuget 包来回答。

Install-Package Humanizer

https://www.nuget.org/packages/Humanizer

https://github.com/MehdiK/Humanizer

readme.md 中的示例

TimeSpan.FromMilliseconds(1299630020).Humanize(4) => "2 weeks, 1 day, 1 hour, 30 seconds"

【讨论】:

    【解决方案3】:

    您可以使用静态TimeSpan.FromMilliseconds 方法以及生成的TimeSpanDaysHoursMinutesSecondsMilliseconds 属性。

    但是我现在很忙,所以剩下的留给你练习。

    【讨论】:

      【解决方案4】:

      这个怎么样?

      var ts = TimeSpan.FromMilliseconds(86300000 /*whatever */);
      var parts = string
                      .Format("{0:D2}d:{1:D2}h:{2:D2}m:{3:D2}s:{4:D3}ms",
                          ts.Days, ts.Hours, ts.Minutes, ts.Seconds, ts.Milliseconds)
                      .Split(':')
                      .SkipWhile(s => Regex.Match(s, @"00\w").Success) // skip zero-valued components
                      .ToArray();
      var result = string.Join(" ", parts); // combine the result
      
      Console.WriteLine(result);            // prints '23h 58m 20s 000ms'
      

      【讨论】:

      • 不错的代码,但作为输入失败了 100 毫秒。解决方法是使用 @"^00\w" 作为正则表达式。
      【解决方案5】:

      .NET 4 接受TimeSpan.Tostring() 中的格式。

      对于其他你可以实现扩展方法,如

          public static string Format(this TimeSpan obj)
          {
              StringBuilder sb = new StringBuilder();
              if (obj.Hours != 0)
              {
                  sb.Append(obj.Hours);
                  sb.Append(" "); 
                  sb.Append("hours");
                  sb.Append(" ");
              }
              if (obj.Minutes != 0 || sb.Length != 0)
              {
                  sb.Append(obj.Minutes);
                  sb.Append(" "); 
                  sb.Append("minutes");
                  sb.Append(" ");
              }
              if (obj.Seconds != 0 || sb.Length != 0)
              {
                  sb.Append(obj.Seconds);
                  sb.Append(" "); 
                  sb.Append("seconds");
                  sb.Append(" ");
              }
              if (obj.Milliseconds != 0 || sb.Length != 0)
              {
                  sb.Append(obj.Milliseconds);
                  sb.Append(" "); 
                  sb.Append("Milliseconds");
                  sb.Append(" ");
              }
              if (sb.Length == 0)
              {
                  sb.Append(0);
                  sb.Append(" "); 
                  sb.Append("Milliseconds");
              }
              return sb.ToString();
          }
      

      并调用为

      foreach (TimeSpan span in spans)
      {
          MessageBox.Show(string.Format("{0}",  span.Format()));
      }
      

      【讨论】:

      • 我已经使用了这种方法,我只是想注意最高间隔(在这种情况下为obj.Hours)应该是obj.TotalHours,ToString("0").TotalHours 可以显示 24 小时以上的值,,ToString("0") 可以将其转换为单个数字而不是逗号分隔值。
      【解决方案6】:
      public static string ReadableTime(int milliseconds)
      {
          var parts = new List<string>();
          Action<int, string> add = (val, unit) => { if (val > 0) parts.Add(val+unit); };
          var t = TimeSpan.FromMilliseconds(milliseconds);
      
          add(t.Days, "d");
          add(t.Hours, "h");
          add(t.Minutes, "m");
          add(t.Seconds, "s");
          add(t.Milliseconds, "ms");
      
          return string.Join(" ", parts);
      }
      

      【讨论】:

      • 这是一个适用于更长时间跨度的好方法(t.TotalDays 也适用)。
      • 很好的方法,以及可选的格式。 Action add = (val, unit, zeroplaceholder) => {if (val > 0) parts.Add( string.Format( "{0:DZ}X".Replace("X", unit .ToString()) .Replace("Z",zeroplaceholder.ToString()) , val ); }; 并调用 add(t.Milliseconds, "ms", 4); 得到 2m 37s 0456ms
      【解决方案7】:

      这可能与请求的输出略有不同,但结果是人类可读的 - 它可以适应许多其他用例。

      private static List<double> _intervals = new List<double>
      {
          1.0 / 1000 / 1000,
          1.0 / 1000,
          1,
          1000,
          60 * 1000,
          60 * 60 * 1000
      };
      private static List<string> _units = new List<string>
      {
          "ns",
          "µs",
          "ms",
          "s",
          "min",
          "h"
      };
      
      public string FormatUnits(double milliseconds, string format = "#.#")
      {
          var interval = _intervals.Last(i=>i<=milliseconds);
          var index = _intervals.IndexOf(interval);
      
          return string.Concat((milliseconds / interval).ToString(format) , " " , _units[index]);
      }
      

      示例调用...

      Console.WriteLine(FormatUnits(1));
      Console.WriteLine(FormatUnits(20));
      Console.WriteLine(FormatUnits(300));
      Console.WriteLine(FormatUnits(4000));
      Console.WriteLine(FormatUnits(50000));
      Console.WriteLine(FormatUnits(600000));
      Console.WriteLine(FormatUnits(7000000));
      Console.WriteLine(FormatUnits(80000000));
      

      ...和结果:

      1000 µs
      20 ms
      300 ms
      4 s
      50 s
      10 min
      1.9 h
      22.2 h
      

      【讨论】:

        【解决方案8】:

        也许是这样的?

        DateTime.Now.ToString("%d 'd' %h 'h' %m 'm' %s 'seconds' %ms 'ms'")
        

        【讨论】:

        • 问题是关于TimeSpans,而不是DateTimes。使用DateTime,您总是会得到至少一天,这与输入的 3 毫秒不匹配。
        【解决方案9】:

        例如,要将00:01:35.0090000 设为 0 小时、1 分钟、35 秒和 9 毫秒,您可以使用:

        Console.WriteLine("Time elapsed:" +TimeSpan.FromMilliseconds(numberOfMilliseconds).ToString());
        

        你的输出:

        Time elapsed: 00:01:35.0090000
        

        【讨论】:

          【解决方案10】:

          你可以使用TimeSpan.FromMilliseconds函数

          var tspan = TimeSpan.FromMilliseconds(YOUR_MILLI_SECONDS);
          int h = tspan.Hours;
          int m = tspan.Minutes;
          int s = tspan.Seconds;
          

          【讨论】:

            【解决方案11】:

            老问题,新答案:

            public static string GetReadableTimeByMs(long ms)
            {
               TimeSpan t = TimeSpan.FromMilliseconds(ms);
               if (t.Hours > 0) return $"{t.Hours}h:{t.Minutes}m:{t.Seconds}s";
               else if (t.Minutes > 0) return $"{t.Minutes}m:{t.Seconds}s";
               else if (t.Seconds > 0) return $"{t.Seconds}s:{t.Milliseconds}ms";
               else return $"{t.Milliseconds}ms";
            }
            

            【讨论】:

              【解决方案12】:

              好吧,我通常讨厌写 if 语句,但有时你真正拥有的是钉子,需要一把锤子。

              string time;
              if (elapsedTime.TotalMinutes > 2)
                  time = string.Format("{0:n2} minutes", elapsedTime.TotalMinutes);
              else if (elapsedTime.TotalSeconds > 15)
                  time = string.Format("{0:n2} seconds", elapsedTime.TotalSeconds);
              else
                  time = string.Format("{0:n0}ms", elapsedTime.TotalMilliseconds);
              

              【讨论】:

                猜你喜欢
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 2018-12-13
                • 2012-01-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                相关资源
                最近更新 更多