# 听说小学生也能学会python？大佬自制这份教程，真是太棒了！

Python排序傻傻分不清？下面教你看透sorted与sort用法

1. 排序数字型数据

>>> numbers = [6, 9, 3, 1]

>>> sorted(numbers)

[1, 3, 6, 9]

>>> numbers

[6, 9, 3, 1]

>>> numbers = [6, 9, 3, 1]

>>> numbers_sorted = sorted(numbers)

>>> numbers_sorted

[1, 3, 6, 9]

>>> numbers

[6, 9, 3, 1]

>>> # Python 3

>>> help(sorted)

Help on built-in function sorted in module builtins:

sorted(iterable, /, *, key=None, reverse=False)

Return a new list containing all items from the iterable in ascending order.

A custom key function can be supplied to customize the sort order, and the

reverse flag can be set to request the result in descending order.

>>> numbers_tuple = (6, 9, 3, 1)

>>> numbers_set = {5, 5, 10, 1, 0}

>>> numbers_tuple_sorted = sorted(numbers_tuple)

>>> numbers_set_sorted = sorted(numbers_set)

>>> numbers_tuple_sorted

[1, 3, 6, 9]

>>> numbers_set_sorted

[0, 1, 5, 10]

>>> numbers_tuple = (6, 9, 3, 1)

>>> numbers_set = {5, 5, 10, 1, 0}

>>> numbers_tuple_sorted = sorted(numbers_tuple)

>>> numbers_set_sorted = sorted(numbers_set)

>>> numbers_tuple_sorted

[1, 3, 6, 9]

>>> numbers_set_sorted

[0, 1, 5, 10]

>>> tuple(numbers_tuple_sorted)

(1, 3, 6, 9)

>>> set(numbers_set_sorted)

{0, 1, 10, 5}

2. 排序字符串型数据

>>> string_number_value = '34521'

>>> string_value = 'I like to sort'

>>> sorted_string_number = sorted(string_number_value)

>>> sorted_string = sorted(string_value)

>>> sorted_string_number

['1', '2', '3', '4', '5']

>>> sorted_string

[' ', ' ', ' ', 'I', 'e', 'i', 'k', 'l', 'o', 'o', 'r', 's', 't', 't']

sorted()将字符串视为列表并遍历每个元素。在字符串中，每个元素表示字符串中的一个字符，sorted会以相同的方式处理一个字符串，对每个字符进行排序，包括空格。 .

>>> string_value = 'I like to sort'

>>> sorted_string = sorted(string_value.split())

>>> sorted_string

['I', 'like', 'sort', 'to']

>>> ' '.join(sorted_string)

'I like sort to'

Python排序的局限性和陷阱

1. 具有不能比较数据类型的列表无法进行排序

>>> mixed_types = [None, 0]

>>> sorted(mixed_types)

Traceback (most recent call last):

File "", line 1, in

TypeError: '<' not supported between instances of 'int' and 'NoneType'

>>> mixed_numbers = [5, "1", 100, "34"]

>>> sorted(mixed_numbers)

Traceback (most recent call last):

File "", line 1, in

TypeError: '<' not supported between instances of 'str' and 'int'

>>> # List comprehension to convert all values to integers

>>> [int(x) for x in mixed_numbers]

[5, 1, 100, 34]

>>> sorted([int(x) for x in mixed_numbers])

[1, 5, 34, 100]

mixed_numbers中的每个元素都调用了int()来将任何str值转换为int值。然后调用sorted()并成功比较每个元素并提供排序的输出。

>>> similar_values = [False, 0, 1, 'A' == 'B', 1 <= 0]

>>> sorted(similar_values)

[False, 0, False, False, 1]

'A'=='B'和1 <= 0转换为False并在有序输出中返回。

>>> false_values = [False, 0, 0, 1 == 2, 0, False, False]

>>> sorted(false_values)

[False, 0, 0, False, 0, False, False]

2. 当排序字符串时，大小写很重要

sorted()可用于字符串列表，以按升序对值进行排序，默认情况下按字母顺序排列：

>>> names = ['Harry', 'Suzy', 'Al', 'Mark']

>>> sorted(names)

['Al', 'Harry', 'Mark', 'Suzy']

>>> names_with_case = ['harry', 'Suzy', 'al', 'Mark']

>>> sorted(names_with_case)

['Mark', 'Suzy', 'al', 'harry']

>>> # 每个word中第一个字母的unicode代码点列表推导式

>>> [(ord(name[0]), name[0]) for name in sorted(names_with_case)]

[(77, 'M'), (83, 'S'), (97, 'a'), (104, 'h')]

name [0]返回sorted(names_with_case)的每个元素中的第一个字符，ord()提供Unicode代码点。即使a在字母表中的M之前，M的代码点在a之前，因此排序的输出首先是M。

>>> very_similar_strs = ['hhhhhd', 'hhhhha', 'hhhhhc','hhhhhb']

>>> sorted(very_similar_strs)

['hhhhha', 'hhhhhb', 'hhhhhc', 'hhhhhd']

>>> different_lengths = ['hhhh', 'hh', 'hhhhh','h']

>>> sorted(different_lengths)

['h', 'hh', 'hhhh', 'hhhhh']

>>> names = ['Harry', 'Suzy', 'Al', 'Mark']

>>> sorted(names)

['Al', 'Harry', 'Mark', 'Suzy']

>>> sorted(names, reverse=True)

['Suzy', 'Mark', 'Harry', 'Al']

>>> names_with_case = ['harry', 'Suzy', 'al', 'Mark']

>>> sorted(names_with_case, reverse=True)

['harry', 'al', 'Suzy', 'Mark']

>>> similar_values = [False, 1, 'A' == 'B', 1 <= 0]

>>> sorted(similar_values, reverse=True)

[1, False, False, False]

>>> numbers = [6, 9, 3, 1]

>>> sorted(numbers, reverse=False)

[1, 3, 6, 9]

sorted()使用key参数排序

sorted()最强大的功能之一是一个叫做key的关键字参数。此参数需要将函数传递给它，并且该函数将用于要排序的列表中的每个值，以确定生成的顺序。

>>> word = 'paper'

>>> len(word)

5

>>> words = ['banana', 'pie', 'Washington', 'book']

>>> sorted(words, key=len)

['pie', 'book', 'banana', 'Washington']

>>> names_with_case = ['harry', 'Suzy', 'al', 'Mark']

>>> sorted(names_with_case)

['Mark', 'Suzy', 'al', 'harry']

>>> sorted(names_with_case, key=str.lower)

['al', 'harry', 'Mark', 'Suzy']

... return x + y

...

>>> values_to_add = [1, 2, 3]

Traceback (most recent call last):

File "", line 1, in

TypeError: add() missing 1 required positional argument: 'y'

>>> values_to_cast = ['1', '2', '3', 'four']

>>> sorted(values_to_cast, key=int)

Traceback (most recent call last):

File "", line 1, in

ValueError: invalid literal for int() with base 10: 'four'

key功能非常强大，因为几乎任何内置或用户定义的函数都可用于操作输出顺序。

>>> def reverse_word(word):

... return word[::-1]

...

>>> words = ['banana', 'pie', 'Washington', 'book']

>>> sorted(words, key=reverse_word)

['banana', 'pie', 'book', 'Washington']

word[::-1]切片语法用于反转字符串。每个元素都会应用reverse_word()，排序顺序将基于后向单词中的字符。

>>> words = ['banana', 'pie', 'Washington', 'book']

>>> sorted(words, key=lambda x: x[::-1])

['banana', 'pie', 'book', 'Washington']

>>> words = ['banana', 'pie', 'Washington', 'book']

>>> sorted(words, key=lambda x: x[::-1], reverse=True)

['Washington', 'book', 'pie', 'banana']

>>> from collections import namedtuple

>>> StudentFinal = namedtuple('StudentFinal', 'name grade')

>>> bill = StudentFinal('Bill', 90)

>>> patty = StudentFinal('Patty', 94)

>>> bart = StudentFinal('Bart', 89)

>>> students = [bill, patty, bart]

>>> sorted(students, key=lambda x: getattr(x, 'grade'), reverse=True)

>>> # Python2

Help on method_descriptor:

sort(...)

L.sort(cmp=None, key=None, reverse=False) -- stable sort *IN PLACE*;

cmp(x, y) -> -1, 0, 1

>>> # Python3

>>> help(list.sort)

Help on method_descriptor:

sort(...)

L.sort(key=None, reverse=False) -> None -- stable sort *IN PLACE*

>>> values_to_sort = [5, 2, 6, 1]

>>> # 尝试调用像使用sorted()调用sort()

>>> sort(values_to_sort)

Traceback (most recent call last):

File "", line 1, in

NameError: name 'sort' is not defined

>>> # 尝试在一个元组上使用 .sort()

>>> tuple_val = (5, 1, 3, 5)

>>> tuple_val.sort()

Traceback (most recent call last):

File "", line 1, in

AttributeError: 'tuple' object has no attribute 'sort'

>>> # 排序列表并且赋值给新的变量

>>> sorted_values = values_to_sort.sort()

>>> print(sorted_values)

None

>>> # 打印原始变量

>>> print(values_to_sort)

[1, 2, 5, 6]

1. sort()不产生有序输出，因此对新变量的赋值仅传递None类型。

2. values_to_sort列表已就地更改，并且不以任何方式维持原始顺序。

.sort()具有相同的key和reverse可选关键字参数，这些参数产生与sorted()相同的强大功能。在这里，可以按第三个单词的第二个字母对短语列表进行排序，然后反向返回列表：

>>> phrases = ['when in rome',

... 'what goes around comes around',

... 'all is fair in love and war'

... ]

>>> phrases.sort(key=lambda x: x.split()[2][1], reverse=True)

>>> phrases

['what goes around comes around', 'when in rome', 'all is fair in love and war']

>>> from collections import namedtuple

>>> Runner = namedtuple('Runner', 'bibnumber duration')

>>> runners = []

>>> runners.append(Runner('2528567', 1500))

>>> runners.append(Runner('7575234', 1420))

>>> runners.append(Runner('2666234', 1600))

>>> runners.append(Runner('2425234', 1490))

>>> runners.append(Runner('1235234', 1620))

>>> # Thousands and Thousands of entries later...

>>> runners.append(Runner('2526674', 1906))

>>> runners.sort(key=lambda x: getattr(x, 'duration'))

>>> top_five_runners = runners[:5]

>>> runners_by_duration = sorted(runners, key=lambda x: getattr(x, 'duration'))

>>> top_five_runners = runners_by_duration[:5]

>>> every_thirtyseventh_runners = runners[::37]

.sort()和sorted()都可以准确地提供排序功能，但在输出和修改时，两者都具有非常不同的特性，因此请确定是否要在应用程序中使用.sort()，因为它不可撤销地覆盖数据。