Có thể đọc được in ra một python dict () được sắp xếp theo khóa


81

Tôi muốn in từ điển python vào một tệp bằng PrettyPrinter (để con người có thể đọc được) nhưng từ điển được sắp xếp theo khóa trong tệp đầu ra để cải thiện khả năng đọc hơn nữa. Vì thế:

mydict = {'a':1, 'b':2, 'c':3}
pprint(mydict)

hiện đang in tới

{'b':2,
 'c':3,
 'a':1}

Tôi muốn PrettyPrint từ điển nhưng nó đã được in ra được sắp xếp theo khóa, ví dụ.

{'a':1,
 'b':2,
 'c':3}

Cách tốt nhất để làm việc này là gì?

python 

Hóa ra bản in đã được sắp xếp theo khóa. Nên đã kiểm tra kỹ càng hơn.

Câu trả lời:


94

Trên thực tế, pprint dường như sắp xếp các khóa cho bạn trong python2.5

>>> from pprint import pprint
>>> mydict = {'a':1, 'b':2, 'c':3}
>>> pprint(mydict)
{'a': 1, 'b': 2, 'c': 3}
>>> mydict = {'a':1, 'b':2, 'c':3, 'd':4, 'e':5}
>>> pprint(mydict)
{'a': 1, 'b': 2, 'c': 3, 'd': 4, 'e': 5}
>>> d = dict(zip("kjihgfedcba",range(11)))
>>> pprint(d)
{'a': 10,
 'b': 9,
 'c': 8,
 'd': 7,
 'e': 6,
 'f': 5,
 'g': 4,
 'h': 3,
 'i': 2,
 'j': 1,
 'k': 0}

Nhưng không phải lúc nào cũng theo python 2.4

>>> from pprint import pprint
>>> mydict = {'a':1, 'b':2, 'c':3, 'd':4, 'e':5}
>>> pprint(mydict)
{'a': 1, 'c': 3, 'b': 2, 'e': 5, 'd': 4}
>>> d = dict(zip("kjihgfedcba",range(11)))
>>> pprint(d)
{'a': 10,
 'b': 9,
 'c': 8,
 'd': 7,
 'e': 6,
 'f': 5,
 'g': 4,
 'h': 3,
 'i': 2,
 'j': 1,
 'k': 0}
>>> 

Đọc mã nguồn của pprint.py (2.5) nó sắp xếp từ điển bằng cách sử dụng

items = object.items()
items.sort()

cho nhiều dòng hoặc cái này cho một dòng

for k, v in sorted(object.items()):

trước khi nó cố gắng in bất cứ thứ gì, vì vậy nếu từ điển của bạn sắp xếp đúng như vậy thì nó sẽ in đúng cách. Trong 2.4, sắp xếp thứ hai () bị thiếu (khi đó không tồn tại) nên các đối tượng được in trên một dòng sẽ không được sắp xếp.

Vì vậy, câu trả lời dường như là sử dụng python2.5, mặc dù điều này không giải thích rõ kết quả đầu ra của bạn trong câu hỏi.

Cập nhật Python3

Bản in đẹp bởi các phím được sắp xếp (lambda x: x [0]):

for key, value in sorted(dict_example.items(), key=lambda x: x[0]): 
    print("{} : {}".format(key, value))

Bản in đẹp theo các giá trị được sắp xếp (lambda x: x [1]):

for key, value in sorted(dict_example.items(), key=lambda x: x[1]): 
    print("{} : {}".format(key, value))

Giải pháp biểu thức lambda trong Python 3 rất mượt mà. Để rõ ràng, tôi tin rằng (?) keyTrong for key, value in ...không phụ thuộc vào keytrong key=lambda ...như các tác phẩm này, for k,v in sorted(token_dict.items(), key=lambda x: x[0])nhưng for k,v in sorted(token_dict.items(), k=lambda x: x[0])ném một lỗi.
Victoria Stuart

18

Một thay thế khác:

>>> mydict = {'a':1, 'b':2, 'c':3}
>>> import json

Sau đó với python2:

>>> print json.dumps(mydict, indent=4, sort_keys=True) # python 2
{
    "a": 1, 
    "b": 2, 
    "c": 3
}

hoặc với python 3:

>>> print(json.dumps(mydict, indent=4, sort_keys=True)) # python 3
{
    "a": 1, 
    "b": 2, 
    "c": 3
}

14

Một cách dễ dàng để in nội dung được sắp xếp của từ điển, trong Python 3:

>>> dict_example = {'c': 1, 'b': 2, 'a': 3}
>>> for key, value in sorted(dict_example.items()):
...   print("{} : {}".format(key, value))
... 
a : 3
b : 2
c : 1

Biểu thức dict_example.items()trả về các bộ giá trị, sau đó có thể được sắp xếp theo sorted():

>>> dict_example.items()
dict_items([('c', 1), ('b', 2), ('a', 3)])
>>> sorted(dict_example.items())
[('a', 3), ('b', 2), ('c', 1)]

Dưới đây là một ví dụ để in nội dung được sắp xếp của các giá trị của từ điển Python.

for key, value in sorted(dict_example.items(), key=lambda d_values: d_values[1]): 
    print("{} : {}".format(key, value))

Rất đẹp. Dưới đây là một ví dụ để khá in nội dung được sắp xếp của một Python giá trị từ điển:for key, value in sorted(dict_example.items(), key=lambda d_items: d_items[1]): print("{} : {}".format(key, value))
Scott Skiles

1
@ScottSkiles bạn sẽ chỉnh sửa câu trả lời và thêm ví dụ của bạn vào đó - tôi nghĩ nó sẽ giúp ích cho những độc giả trong tương lai
redbeam_ 14/03/18

13

pprintMô-đun Python thực sự đã sắp xếp các từ điển theo khóa. Trong các phiên bản trước Python 2.5, việc sắp xếp chỉ được kích hoạt trên các từ điển có phần biểu diễn in đẹp trải dài nhiều dòng, nhưng trong 2.5.X và 2.6.X, tất cả các từ điển đều được sắp xếp.

Mặc dù vậy, nói chung, nếu bạn đang ghi cấu trúc dữ liệu vào một tệp và muốn chúng có thể đọc và ghi được, bạn có thể muốn xem xét sử dụng một định dạng thay thế như YAML hoặc JSON. Trừ khi chính người dùng của bạn là lập trình viên, việc để họ duy trì cấu hình hoặc trạng thái ứng dụng được kết xuất pprintvà tải qua evalcó thể là một nhiệm vụ khó chịu và dễ xảy ra lỗi.


2
btw, ast.literal_eval("{'a': 0, 'b': 1, 2: 'c'}")-> {2: 'c', 'a': 0, 'b': 1}nên không cần ngấm ngầm eval.
jfs 26/09/09

có và rõ ràng pprint không đưa ra cách nào để tắt hành vi này. Đã lãng phí một hoặc hai giờ để cố gắng tìm ra lý do tại sao một số dữ liệu báo cáo mẫu bản in lại được sắp xếp theo các khóa.
Samantha Atkins

12

Tôi đã viết hàm sau để in các phân số, danh sách và các bộ giá trị ở định dạng dễ đọc hơn:

def printplus(obj):
    """
    Pretty-prints the object passed in.

    """
    # Dict
    if isinstance(obj, dict):
        for k, v in sorted(obj.items()):
            print u'{0}: {1}'.format(k, v)

    # List or tuple            
    elif isinstance(obj, list) or isinstance(obj, tuple):
        for x in obj:
            print x

    # Other
    else:
        print obj

Ví dụ sử dụng trong iPython:

>>> dict_example = {'c': 1, 'b': 2, 'a': 3}
>>> printplus(dict_example)
a: 3
b: 2
c: 1

>>> tuple_example = ((1, 2), (3, 4), (5, 6), (7, 8))
>>> printplus(tuple_example)
(1, 2)
(3, 4)
(5, 6)
(7, 8)

5

Tôi đã có cùng một vấn đề mà bạn đã có. Tôi đã sử dụng vòng lặp for với hàm được sắp xếp truyền vào từ điển như sau:

for item in sorted(mydict):
    print(item)

4

Bạn có thể biến đổi câu lệnh này một chút để đảm bảo rằng (vì các phần không được sắp xếp nội bộ), ví dụ:

pprint([(key, mydict[key]) for key in sorted(mydict.keys())])

0

Một dòng ngắn khác:

mydict = {'c': 1, 'b': 2, 'a': 3}
print(*sorted(mydict.items()), sep='\n')
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.