【问题标题】:Listing contents of a dictionary in two columns在两列中列出字典的内容
【发布时间】:2016-05-20 23:03:34
【问题描述】:

我想在两列中显示一个字典。我基本上是在尝试做this question 试图通过列表实现的目标,但我需要用字典来完成。

我的脚本打印当前文件夹的目录列表,并带有数字。

这是脚本:

import os

files = os.listdir(os.curdir)       #get directory listing

final_dic = dict()                  #initialize the dictionary

x = 1

for item in files:                  #associate index numbers with the filenames
    final_dic[x] = item
    x+=1

print '''
       -------------
       | FILE LIST |
       -------------
       '''

for k, v in final_dic.iteritems():              #print out the enumerated listing
    print ('{0}: {1}'.format(k, v))

num = int(raw_input('\nEnter no. of file: '))   #have user select file by no.

print ('\n{0}\n'.format(final_dic[num]))        #print out corresp. filename

文件列表的输出是:

   -------------
   | FILE LIST |
   -------------

1: file1
2: file2
3: file3
etc.

问题是在有很多文件的文件夹中,列表会滚动到屏幕顶部,所以我希望能够像这样显示列表:

1: file1     4: file4
2: file2     5: file5
3: file3     6: file6
etc.

从上面链接的问题来看,zip 似乎需要两个列表并从中创建一个字典,但我已经有了一个字典。

那么,有没有办法做到这一点?

添加评论:一些 cmets 提到我应该使用列表,但不幸的是它必须是字典。这只是更大脚本的一部分。

【问题讨论】:

  • 是的,但是没有很好的分栏器;你必须自己编写逻辑来确定你想要多少列,然后以总/列作为你的步进循环。你会对行而不是列感到满意吗?这样会更容易。
  • 不回答您的问题,但您不需要字典,您可以使用列表,因为您希望键只是数字
  • 我确实需要它作为字典,因为索引号。还与文件 ID 相关联,这是脚本实际设计使用的文件 ID。我把其余的都省略了,因为它与问题无关。
  • 这比您想象的要困难,具体取决于您希望事情的动态程度,因为几乎可以有任意数量的文件(因此文件编号中的位数可能会有所不同)和一些文件名可能很长——您希望在某些(未定义的)最大打印宽度内将所有文件名放入两列中。足够强大以优雅地处理所有这些变量的东西将相对较长和复杂。最好的办法是找到一个现有的模块来完成你需要的部分或全部工作。
  • @martineau 我也是这么想的。我想链接到某个模块,但找不到合适的模块。有tabulate,它打印出非常漂亮的表格,但它没有执行要求的分列...知道要使用什么吗?

标签: python dictionary formatting


【解决方案1】:

以下内容仅使用简单的列格式,但至少应该让您了解如何解决该问题。文件名被简单地截断到最大长度以保持列对齐。请注意,文件编号比其在创建的files 列表中的索引大一,因此必须在接受用户输入时进行处理。

from itertools import islice
import os

files = sorted(os.listdir(os.curdir))  # get directory listing

desired_cols = 2
whole_rows, partial_rows = divmod(len(files), desired_cols)
num_rows = whole_rows + (1 if partial_rows > 0 else 0)

iterators = islice(files, None), islice(files, num_rows, None)

for i, f1 in enumerate(iterators[0], start=1):
    j = i + num_rows
    try:
        f2 = next(iterators[1])
    except StopIteration:
        print('{:2d}: {:38}'.format(i, f1[:38]))  # second column empty
        break
    print('{:2d}: {:38}  {:2d}: {:38}'.format(i, f1[:38], j, f2[:38]))

num = int(raw_input('\nEnter no. of file: '))  # have user select file by no.
index = num - 1
print ('\n{0}\n'.format(files[index]))  # print out corresp. filename

【讨论】:

    【解决方案2】:

    我不能说我非常喜欢你指出的解决方案。

    但是您可以通过生成列表l 直接回收该代码,就像那里使用的一样:

    l = []
    for k, v in final_dic.iteritems():
        l.append('{0}: {1}'.format(k, v))
    

    ... 在您打印代码的地方。然后你使用你链接到的答案。


    我之前链接到https://pypi.python.org/pypi/tabulate,但似乎记错了它的功能。虽然它确实打印了带有对齐/填充的漂亮表格,但它不会按要求破坏列......

    【讨论】:

      【解决方案3】:

      由于字典是任意排序的,并且您在打印之前没有对其进行排序,因此您可以简单地获取成对的项目并打印它们:

      it = final_dic.iteritems()
      for item in it:
          try:
              n = next(it)
          except StopIteration:
              print '{}: {}'.format(*item)
          else:
              print '{}: {}\t'.format(*item), '{}: {}'.format(*n)
      

      另一种方法,itertools.izip_longest():

      it = final_dic.iteritems()
      for a,b in itertools.izip_longest(it, it):
          print '{}: {}'.format(*a), '\t{}: {}'.format(*b) if b else ''
      

      使用list 而不是字典,以便输出是按列而不是逐行排序的:

      final_list = list(enumerate(files))
      half = len(final_list)//2+1
      for (idx1,val1),(idx2,val2) in itertools.izip_longest(
                                     final_list[:half], final_list[half:], fillvalue=(0,'')):
          print '{}: {}'.format(idx1+1, val1) if val1 else '', '\t{}: {}'.format(idx2+1, val2) if val2 else ''
      

      final_list = list(enumerate('abcde')) 的测试结果:

      1: a    4: d
      2: b    5: e
      3: c
      

      【讨论】:

      • 谢谢;我重构时错过了一个参考。
      • 我赞成您的解决方案,因为这是更好的做法。然而,根据他想要“做这个问题试图通过列表实现的目标”的严格程度,这可能不是他想要的?!另外,我不喜欢在循环中手动下一个迭代器...
      • 嗯,总是有itertools.zip_longest(it, it) 并检查None
      • 你不觉得哪个更好?
      • 我补充一下;当然。还有一些关于使用list;为什么不呢。
      猜你喜欢
      • 2021-12-01
      • 1970-01-01
      • 2014-06-13
      • 2011-10-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多