問題の歴史:
sort()メソッドはPythonの初期バージョンからlist型に組み込まれており、sorted()関数はPython 2.4で登場しました。コレクションのソートはプログラミングで最も一般的なタスクの一つであり、Pythonは解決のための2つの主要なツールを提供しています。
問題:
多くの初心者はsort()(リストメソッド)とsorted()(高階関数)を混同します。インプレースソートを使用するタイミング、ソート可能なオブジェクト、key/reverseによる任意の順序の指定方法、特に複雑なユーザー定義構造に伴う潜在的な罠について理解していません。
解決策:
list.sort()は元のリストをその場でソートし、Noneを返します。元のオブジェクトを変更します。sorted()は新しいソート済みリスト(または異なる型を渡せば別の型)を返し、元のものを変更しません。任意の反復可能なオブジェクト(ジェネレータも含む)で動作します。key(ソート関数)とreverse(逆順ソートのためのブールフラグ)というパラメータをサポートしています。コードの例:
numbers = [5, 2, 9, 1] numbers.sort() # numbers = [1, 2, 5, 9] words = ['aaa', 'ZZZ', 'bbb'] sorted_words = sorted(words, key=str.lower, reverse=True) # sorted_words = ['ZZZ', 'bbb', 'aaa'] # wordsは変更されない
重要な特徴:
sort()はリスト専用でその場でソートし、sorted()はより汎用的で、任意の反復可能オブジェクトと動作します。my_list = my_list.sort()を実行した場合、変数は何を返しますか?
回答: my_listはNoneになります。なぜなら、sortはリストをその場でソートしNoneを返すからです。これは一般的なバグです:常にin-placeでソートを行い、代入せず、または新しいリストとしてソートされたオブジェクトが必要な場合はsortedを使用してください。
コードの例:
lst = [3, 1, 2] lst = lst.sort() # lstは今やNoneです
タプルや文字列をsort()メソッドでソートできますか?
回答: いいえ、変更不可能なオブジェクト(タプル、文字列)にはsortメソッドがないため、要素の新しいソート済みリストを返すsorted()を使用できます。
コードの例:
tpl = (4, 2, 7) sorted_tpl = sorted(tpl) # sorted_tpl = [2, 4, 7]
異なる型の要素を含むリストをソートできますか?
回答: Python 3では異なる比較不可能な型(例えば、intとstr)をソートするとTypeErrorが発生します。Python 2では特定の順序がありましたが、現在はすべての値を比較可能な形に一般化するためにkey関数を明示的に指定する必要があります。
ネガティブケース
プログラマーがmy_list = my_list.sort()を実行し、元のリストへのアクセスを失った、なぜなら変数にNoneが代入されたからです。
利点:
欠点:
ポジティブケース
元のデータを変更せずに新しいバージョンを取得するために注意深くsorted()を使用した、または代入をせずに正しくsortを適用した。
利点:
欠点: