challenge LL Golf Hole 7 - バイト数を読みやすくする

与えられたバイト数を読みやすくしてください。読みやすくとは、いわゆる human readable な表記とします(詳しくはサンプルのコードを参考にしてください)。

与えるバイト数についてはリテラルで与える、標準入力で与える、引数で与えるなどは自由とします。

余力のあるものはこのプログラムを短くしてください。

※ LL Future実行委員の高野光弘です。この出題は LL Future公式の出題であり、優れたものについてはLL Golfのセッションでご紹介させていただくかもしれません。ご理解の上、ご投稿ください。また、LL Futureのチケットは現在も発売中です。よろしければ、メインイベントの方にもぜひご参加ください。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
b = gets.to_i
if b < 10**3
    puts b
elsif b < 10**6
    puts "%.1fk" % (b.to_f/10**3)
elsif b < 10**9
    puts "%.1fM" % (b.to_f/10**6)
elsif b < 10**12
    puts "%.1fG" % (b.to_f/10**9)
else
    puts "%.1fT" % (b.to_f/10**12)
end

Posted feedbacks - Python

あんまり納得のいく出来ではない。forの中が汚い。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
def readable(byte, base=1024):
  '''
  >>> readable(0)
  '0'
  >>> readable(100)
  '100'
  >>> readable(1024)
  '1.0k'
  >>> readable(1900*1024)
  '1.9M'
  >>> readable(1900*1024*1024)
  '1.9G'
  >>> readable(1900*(1024**7))
  '1.9Y'
  '''
  for c in ['','k', 'M', 'G', 'T', 'P', 'E', 'Z', 'Y']:
    d, m = divmod(byte, base)
    if not d:
      if c:
        return '%.1f%s'%(float(exp)/base, c)
      else:
        return str(m)
    else:
      exp = byte
      byte = d
  return 'Not supported'


if __name__ ==  '__main__':
  import doctest
  doctest.testmod()

大差でこちらだと思う。 **を一杯計算するが・・・。

System Message: WARNING/2 (<string>, line 1); backlink

Inline strong start-string without end-string.
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
def readable(byte, base=1024):
  '''
  >>> readable(0)
  '0'
  >>> readable(100)
  '100'
  >>> readable(1024)
  '1.0k'
  >>> readable(1900*1024)
  '1.9M'
  >>> readable(19000*1024)
  '18.6M'
  >>> readable(190000*1024)
  '185.5M'
  >>> readable(1900*1024*1024)
  '1.9G'
  >>> readable(1900*(1024**7))
  '1.9Y'
  '''
  for i, c in enumerate(['','k', 'M', 'G', 'T', 'P', 'E', 'Z', 'Y']):

    if byte < base **(i+1):
      if c:
        return '%.1f%s'%(float(byte)/base**i, c)
      else:
        return str(byte)

  return 'Not supported'


if __name__ ==  '__main__':
  import doctest
  doctest.testmod()

前出の再帰バージョン。 再帰のありがたみはあまりない。 しいて言えば、Yでかけないやつが来たときもreadableではないが数字列を返す点か。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
def readable(byte, base=1024):
  def sub(byte, k, bound, unit):
    if byte < bound:
      if unit and unit[0]:
        return '%.1f%s'%(float(byte)/k, unit[0])
      else:
        return str(byte)
    else:
      return sub(byte, k*base, bound *base, unit[1:])
  return sub(byte, 1, base, ['', 'k', 'M', 'G', 'T', 'P', 'E', 'Z', 'Y'])

raw_input()を使って書いてみた。86bytes。

1
s=raw_input();p=-min(4,(len(s)-1)/3)*3;print[s,s[:p]+'.'+s[p:1+p]+'kMGT'[-1-p/3]][p<0]

4bytes削った。82bytes

1
s=raw_input();p=-min(4,(len(s)-1)/3)*3;print[s,s[:p]+'.'+s[p]+'kMGT'[-1-p/3]][p<0]

人様のコードだけど、きれいですっきりしていたもので。

1
2
3
4
5
6
7
def f(n):
  for u in iter('BKMGT'):
    if n < 1024:
      return "%.1f%s" % (n,u)
    n /= 1024.0

print f(int(raw_input()))

ワンライナーPythonの限界に挑戦中。91bytes (本体 80bytes).

1
python -c"s=raw_input();p=min(12,len(s)-1)/3*-3;print[s,s[:p]+'.'+s[p]+' kMGT'[-p/3]][p<0]"

Index

Feed

Other

Link

Pathtraq

loading...