Was ist neu in Python 3.10

Herausgeber:

Pablo Galindo Salgado

Dieser Artikel erklärt die neuen Features in Python 3.10 im Vergleich zu 3.9. Python 3.10 wurde am 4. Oktober 2021 veröffentlicht. Alle Einzelheiten stehen im Änderungsprotokoll.

Zusammenfassung - Release Höhepunkte

Neue Syntax-Features:

  • PEP 634, Strukturelles Mustervergleichen: Spezifikation

  • PEP 635, Strukturelles Mustervergleichen: Motivation und Begründung

  • PEP 636, Strukturelles Mustervergleichen: Einführung

  • bpo-12782, Kontextmanager in Klammern sind jetzt offiziell erlaubt.

Neue Features in der Standardbibliothek:

  • PEP 618, Optionale Längenprüfung für zip hinzufügen.

Verbesserungen am Interpreter:

  • PEP 626, Genaue Zeilennummern für Debugger und andere Werkzeuge.

Neue Typisierungsfunktionen:

  • PEP 604, Vereinigungstypen als X | Y schreiben dürfen

  • PEP 612, Variablen zur Parameterspezifikation

  • PEP 613, Ausdrückliche Typaliase

  • PEP 647, Selbst definierte Typwächter

Wichtige Markierungen als veraltet, Entfernungen oder Einschränkungen:

  • PEP 644, OpenSSL 1.1.1 oder neuer voraussetzen

  • PEP 632, Das Modul distutils als veraltet markieren.

  • PEP 623, Das Element wstr in PyUnicodeObject als veraltet markieren und seine Entfernung vorbereiten.

  • PEP 624, Die Py_UNICODE-Encoder-APIs entfernen

  • PEP 597, Optionale EncodingWarning hinzufügen

Neue Funktionen

Kontextmanager in Klammern

Umgebende Klammern zu verwenden, um Kontextmanager über mehrere Zeilen fortzusetzen, wird jetzt unterstützt. Damit lässt sich eine lange Reihe von Kontextmanagern über mehrere Zeilen formatieren, so wie es bisher schon bei Import-Anweisungen möglich war. Alle diese Beispiele sind jetzt zum Beispiel gültig:

with (CtxManager() as example):
    ...

with (
    CtxManager1(),
    CtxManager2()
):
    ...

with (CtxManager1() as example,
      CtxManager2()):
    ...

with (CtxManager1(),
      CtxManager2() as example):
    ...

with (
    CtxManager1() as example1,
    CtxManager2() as example2
):
    ...

Es ist auch möglich, am Ende der eingeklammerten Gruppe ein abschließendes Komma zu setzen:

with (
    CtxManager1() as example1,
    CtxManager2() as example2,
    CtxManager3() as example3,
):
    ...

Diese neue Syntax nutzt die Nicht-LL(1)-Fähigkeiten des neuen Parsers. Weitere Einzelheiten unter PEP 617.

(Beigetragen von Guido van Rossum, Pablo Galindo und Lysandros Nikolaou in bpo-12782 und bpo-40334.)

Bessere Fehlermeldungen

SyntaxErrors

Wertet der Interpreter Code aus, der nicht geschlossene runde oder eckige Klammern enthält, nennt er jetzt die Stelle der nicht geschlossenen Klammer, statt SyntaxError: unexpected EOF while parsing anzuzeigen oder auf eine falsche Stelle zu verweisen. Nimm zum Beispiel den folgenden Code (beachte die nicht geschlossene ‚{‚):

expected = {9: 1, 18: 2, 19: 2, 27: 3, 28: 3, 29: 3, 36: 4, 37: 4,
            38: 4, 39: 4, 45: 5, 46: 5, 47: 5, 48: 5, 49: 5, 54: 6,
some_other_code = foo()

Frühere Versionen des Interpreters nannten verwirrende Stellen als Ort des Syntaxfehlers:

File "example.py", line 3
    some_other_code = foo()
                    ^
SyntaxError: invalid syntax

In Python 3.10 kommt dagegen eine aussagekräftigere Fehlermeldung:

File "example.py", line 1
    expected = {9: 1, 18: 2, 19: 2, 27: 3, 28: 3, 29: 3, 36: 4, 37: 4,
               ^
SyntaxError: '{' was never closed

Auf ähnliche Weise verweisen Fehler bei nicht beendeten Zeichenkettenliteralen (mit einfachen und mit dreifachen Anführungszeichen) jetzt auf den Anfang der Zeichenkette, statt EOF/EOL zu melden.

Diese Verbesserungen sind von früheren Arbeiten am PyPy-Interpreter angeregt.

(Beigetragen von Pablo Galindo in bpo-42864 und Batuhan Taskaya in bpo-40176.)

SyntaxError-Ausnahmen, die der Interpreter auslöst, heben jetzt den vollen Fehlerbereich des Ausdrucks hervor, der den Syntaxfehler ausmacht, statt nur die Stelle, an der das Problem erkannt wird. Statt der folgenden Anzeige (vor Python 3.10):

>>> foo(x, z for z in range(10), t, w)
  File "<stdin>", line 1
    foo(x, z for z in range(10), t, w)
           ^
SyntaxError: Generator expression must be parenthesized

zeigt Python 3.10 die Ausnahme jetzt so an:

>>> foo(x, z for z in range(10), t, w)
  File "<stdin>", line 1
    foo(x, z for z in range(10), t, w)
           ^^^^^^^^^^^^^^^^^^^^
SyntaxError: Generator expression must be parenthesized

Diese Verbesserung wurde von Pablo Galindo in bpo-43914 beigetragen.

Eine erhebliche Menge neuer, auf den Einzelfall zugeschnittener Meldungen für SyntaxError-Ausnahmen ist aufgenommen worden. Die bemerkenswertesten sind:

  • Fehlender : vor Blöcken:

    >>> if rocket.position > event_horizon
      File "<stdin>", line 1
        if rocket.position > event_horizon
                                          ^
    SyntaxError: expected ':'
    

    (Beigetragen von Pablo Galindo in bpo-42997.)

  • Tupel ohne Klammern in Comprehension-Zielen:

    >>> {x,y for x,y in zip('abcd', '1234')}
      File "<stdin>", line 1
        {x,y for x,y in zip('abcd', '1234')}
         ^
    SyntaxError: did you forget parentheses around the comprehension target?
    

    (Beigetragen von Pablo Galindo in bpo-43017.)

  • Fehlende Kommas in Sammlungsliteralen und zwischen Ausdrücken:

    >>> items = {
    ... x: 1,
    ... y: 2
    ... z: 3,
      File "<stdin>", line 3
        y: 2
           ^
    SyntaxError: invalid syntax. Perhaps you forgot a comma?
    

    (Beigetragen von Pablo Galindo in bpo-43822.)

  • Mehrere Ausnahmetypen ohne Klammern:

    >>> try:
    ...     build_dyson_sphere()
    ... except NotEnoughScienceError, NotEnoughResourcesError:
      File "<stdin>", line 3
        except NotEnoughScienceError, NotEnoughResourcesError:
               ^
    SyntaxError: multiple exception types must be parenthesized
    

    (Beigetragen von Pablo Galindo in bpo-43149.)

  • Fehlende : und fehlende Werte in Dictionary-Literalen:

    >>> values = {
    ... x: 1,
    ... y: 2,
    ... z:
    ... }
      File "<stdin>", line 4
        z:
         ^
    SyntaxError: expression expected after dictionary key and ':'
    
    >>> values = {x:1, y:2, z w:3}
      File "<stdin>", line 1
        values = {x:1, y:2, z w:3}
                            ^
    SyntaxError: ':' expected after dictionary key
    

    (Beigetragen von Pablo Galindo in bpo-43823.)

  • try-Blöcke ohne except- oder finally-Block:

    >>> try:
    ...     x = 2
    ... something = 3
      File "<stdin>", line 3
        something  = 3
        ^^^^^^^^^
    SyntaxError: expected 'except' or 'finally' block
    

    (Beigetragen von Pablo Galindo in bpo-44305.)

  • Verwendung von = statt == in Vergleichen:

    >>> if rocket.position = event_horizon:
      File "<stdin>", line 1
        if rocket.position = event_horizon:
                           ^
    SyntaxError: cannot assign to attribute here. Maybe you meant '==' instead of '='?
    

    (Beigetragen von Pablo Galindo in bpo-43797.)

  • Verwendung von * in f-Strings:

    >>> f"Black holes {*all_black_holes} and revelations"
      File "<stdin>", line 1
        (*all_black_holes)
         ^
    SyntaxError: f-string: cannot use starred expression here
    

    (Beigetragen von Pablo Galindo in bpo-41064.)

IndentationErrors

Viele IndentationError-Ausnahmen haben jetzt mehr Kontext dazu, welche Art von Block eine Einrückung erwartet hat, einschließlich der Stelle der Anweisung:

>>> def foo():
...    if lel:
...    x = 2
  File "<stdin>", line 3
    x = 2
    ^
IndentationError: expected an indented block after 'if' statement in line 2

AttributeErrors

Beim Ausgeben eines AttributeError schlägt PyErr_Display() ähnliche Attributnamen aus dem Objekt vor, aus dem die Ausnahme ausgelöst wurde:

>>> collections.namedtoplo
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: module 'collections' has no attribute 'namedtoplo'. Did you mean: namedtuple?

(Beigetragen von Pablo Galindo in bpo-38530.)

Warnung

Beachte, dass das nicht funktioniert, wenn der Fehler nicht über PyErr_Display() angezeigt wird, was vorkommen kann, wenn eine andere, eigene Funktion zur Fehleranzeige verwendet wird. Das ist in manchen REPLs wie IPython häufig der Fall.

NameErrors

Beim Ausgeben eines NameError, den der Interpreter ausgelöst hat, schlägt PyErr_Display() ähnliche Variablennamen aus der Funktion vor, aus der die Ausnahme ausgelöst wurde:

>>> schwarzschild_black_hole = None
>>> schwarschild_black_hole
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'schwarschild_black_hole' is not defined. Did you mean: schwarzschild_black_hole?

(Beigetragen von Pablo Galindo in bpo-38530.)

Warnung

Beachte, dass das nicht funktioniert, wenn der Fehler nicht über PyErr_Display() angezeigt wird, was vorkommen kann, wenn eine andere, eigene Funktion zur Fehleranzeige verwendet wird. Das ist in manchen REPLs wie IPython häufig der Fall.

PEP 626: Genaue Zeilennummern für Debugger und andere Werkzeuge

PEP 626 bringt genauere und zuverlässigere Zeilennummern für Werkzeuge zur Fehlersuche, zum Profiling und zur Abdeckungsmessung. Tracing-Ereignisse mit der richtigen Zeilennummer werden für alle ausgeführten Codezeilen erzeugt – und nur für Codezeilen, die ausgeführt werden.

Das Attribut f_lineno von Rahmenobjekten enthält jetzt immer die erwartete Zeilennummer.

Das Attribut codeobject.co_lnotab von Codeobjekten ist als veraltet markiert und wird in 3.12 entfernt. Code, der von einem Versatz auf eine Zeilennummer umrechnen muss, sollte stattdessen die neue Methode co_lines() verwenden.

PEP 634: Strukturelles Mustervergleichen

Strukturelles Mustervergleichen ist in Form einer match-Anweisung und von case-Anweisungen mit Mustern und zugehörigen Aktionen hinzugekommen. Muster bestehen aus Folgen, Mappings, einfachen Datentypen und Klasseninstanzen. Mit Mustervergleichen können Programme Informationen aus komplexen Datentypen herausziehen, anhand der Struktur der Daten verzweigen und je nach Gestalt der Daten bestimmte Aktionen ausführen.

Syntax und Arbeitsweise

Die allgemeine Syntax des Mustervergleichens ist:

match subject:
    case <pattern_1>:
        <action_1>
    case <pattern_2>:
        <action_2>
    case <pattern_3>:
        <action_3>
    case _:
        <action_wildcard>

Eine match-Anweisung nimmt einen Ausdruck und vergleicht seinen Wert mit aufeinanderfolgenden Mustern, die als ein oder mehrere case-Blöcke angegeben sind. Im Einzelnen arbeitet das Mustervergleichen so:

  1. Es werden Daten mit Typ und Gestalt verwendet (das subject)

  2. das subject wird in der match-Anweisung ausgewertet

  3. das Subjekt wird von oben nach unten mit jedem Muster in einer case-Anweisung verglichen, bis eine Übereinstimmung feststeht.

  4. die zum übereinstimmenden Muster gehörende Aktion wird ausgeführt

  5. Steht keine genaue Übereinstimmung fest, wird der letzte Fall, ein Platzhalter _, als passender Fall verwendet, sofern er angegeben ist. Steht keine genaue Übereinstimmung fest und gibt es keinen Platzhalterfall, bleibt der gesamte match-Block ohne Wirkung.

Deklarativer Ansatz

Manche kennen Mustervergleichen vielleicht aus dem einfachen Beispiel, ein Subjekt (ein Datenobjekt) über die switch-Anweisung aus C, Java oder JavaScript (und vielen anderen Sprachen) mit einem Literal (dem Muster) zu vergleichen. Oft wird die switch-Anweisung verwendet, um ein Objekt oder einen Ausdruck mit case-Anweisungen zu vergleichen, die Literale enthalten.

Mächtigere Beispiele für Mustervergleichen finden sich in Sprachen wie Scala und Elixir. Beim strukturellen Mustervergleichen ist der Ansatz „deklarativ“ und nennt die Bedingungen (die Muster) ausdrücklich, auf die Daten passen sollen.

Mit einer „imperativen“ Folge von Anweisungen aus verschachtelten „if“-Anweisungen ließe sich etwas Ähnliches wie strukturelles Mustervergleichen erreichen, aber weniger übersichtlich als mit dem „deklarativen“ Ansatz. Der „deklarative“ Ansatz nennt stattdessen die Bedingungen, die für eine Übereinstimmung erfüllt sein müssen, und ist durch seine ausdrücklichen Muster besser lesbar. Strukturelles Mustervergleichen lässt sich zwar auch in seiner einfachsten Form verwenden, um in einer case-Anweisung eine Variable mit einem Literal zu vergleichen, sein eigentlicher Wert für Python liegt aber darin, wie es mit Typ und Gestalt des Subjekts umgeht.

Einfaches Muster: Vergleich mit einem Literal

Sehen wir uns dieses Beispiel als Mustervergleichen in seiner einfachsten Form an: ein Wert, das Subjekt, wird mit mehreren Literalen, den Mustern, verglichen. Im Beispiel unten ist status das Subjekt der match-Anweisung. Die Muster sind die einzelnen case-Anweisungen, in denen Literale die Statuscodes einer Anfrage darstellen. Die zum Fall gehörende Aktion wird nach einer Übereinstimmung ausgeführt:

def http_error(status):
    match status:
        case 400:
            return "Bad request"
        case 404:
            return "Not found"
        case 418:
            return "I'm a teapot"
        case _:
            return "Something's wrong with the internet"

Wird der obigen Funktion ein status von 418 übergeben, kommt „I’m a teapot“ zurück. Wird ihr ein status von 500 übergeben, passt die case-Anweisung mit _ als Platzhalter, und es kommt „Something’s wrong with the internet“ zurück. Beachte den letzten Block: Der Variablenname _ wirkt als Platzhalter und stellt sicher, dass das Subjekt immer passt. Die Verwendung von _ ist optional.

Du kannst mehrere Literale in einem einzigen Muster mithilfe von | ("oder") kombinieren:

case 401 | 403 | 404:
    return "Not allowed"
Verhalten ohne den Platzhalter

Entfernen wir im obigen Beispiel den letzten case-Block, wird daraus:

def http_error(status):
    match status:
        case 400:
            return "Bad request"
        case 404:
            return "Not found"
        case 418:
            return "I'm a teapot"

Ohne _ in einer case-Anweisung kann es sein, dass keine Übereinstimmung zustande kommt. Kommt keine zustande, bleibt das Ganze ohne Wirkung. Wird zum Beispiel ein status von 500 übergeben, geschieht nichts.

Muster mit einem Literal und einer Variablen

Muster können wie entpackende Zuweisungen aussehen, und ein Muster darf Variablen binden. In diesem Beispiel lässt sich ein Datenpunkt in seine x- und seine y-Koordinate entpacken:

# point ist ein (x, y)-Tupel
match point:
    case (0, 0):
        print("Origin")
    case (0, y):
        print(f"Y={y}")
    case (x, 0):
        print(f"X={x}")
    case (x, y):
        print(f"X={x}, Y={y}")
    case _:
        raise ValueError("Not a point")

Das erste Muster hat zwei Literale, (0, 0), und lässt sich als Erweiterung des oben gezeigten Literalmusters verstehen. Die beiden folgenden Muster verbinden ein Literal und eine Variable, und die Variable bindet einen Wert aus dem Subjekt (point). Das vierte Muster fängt zwei Werte ein, was es der entpackenden Zuweisung (x, y) = point gedanklich ähnlich macht.

Muster und Klassen

Wenn du deine Daten mit Klassen strukturierst, kannst du als Muster den Klassennamen gefolgt von einer Argumentliste verwenden, die einem Konstruktor gleicht. Dieses Muster kann Instanzattribute in Variablen einfangen:

class Point:
    def __init__(self, x, y):
        self.x = x
        self.y = y

def location(point):
    match point:
        case Point(x=0, y=0):
            print("Origin is the point's location.")
        case Point(x=0, y=y):
            print(f"Y={y} and the point is on the y-axis.")
        case Point(x=x, y=0):
            print(f"X={x} and the point is on the x-axis.")
        case Point():
            print("The point is located somewhere else on the plane.")
        case _:
            print("Not a point")
Muster mit positionsbezogenen Parametern

Du kannst Positions-Parameter mit einigen eingebauten Klassen verwenden, die eine Reihenfolge für ihre Attribute festlegen (z. B. dataclasses). Du kannst auch eine spezifische Position für Attribute in Mustern definieren, indem du das spezielle Attribut __match_args__ in deinen Klassen setzt. Wenn es auf ("x", "y") gesetzt ist, sind die folgenden Muster alle äquivalent (und binden alle das Attribut y an die Variable var):

Point(1, var)
Point(1, y=var)
Point(x=1, y=var)
Point(y=var, x=1)

Verschachtelte Muster

Muster lassen sich beliebig tief verschachteln. Sind unsere Daten zum Beispiel eine kurze Liste von Punkten, ließe sich das so abgleichen:

match points:
    case []:
        print("No points in the list.")
    case [Point(0, 0)]:
        print("The origin is the only point in the list.")
    case [Point(x, y)]:
        print(f"A single point {x}, {y} is in the list.")
    case [Point(0, y1), Point(0, y2)]:
        print(f"Two points on the Y axis at {y1}, {y2} are in the list.")
    case _:
        print("Something else is found in the list.")

Komplexe Muster und der Platzhalter

Bis hierher haben die Beispiele _ allein in der letzten case-Anweisung verwendet. Ein Platzhalter lässt sich auch in komplexeren Mustern verwenden, etwa in ('error', code, _). Zum Beispiel:

match test_variable:
    case ('warning', code, 40):
        print("A warning has been received.")
    case ('error', code, _):
        print(f"An error {code} occurred.")

Im obigen Fall passt test_variable auf (‚error‘, code, 100) und auf (‚error‘, code, 800).

Wächter

Wir können einem Muster eine if-Klausel hinzufügen, die als "Guard(Wächter) bezeichnet wird. Wenn der Guard nicht zutrifft, fährt match mit dem nächsten case-Block fort. Beachte, dass das Erfassen der Werte erfolgt, bevor der Guard ausgewertet wird:

match point:
    case Point(x, y) if x == y:
        print(f"The point is located on the diagonal Y=X at {x}.")
    case Point(x, y):
        print(f"Point is not on the diagonal.")

Weitere wichtige Features

Mehrere weitere wichtige Features:

  • Wie bei entpackenden Zuweisungen haben Tupel- und Listenmuster genau dieselbe Bedeutung und passen tatsächlich auf beliebige Folgen. Technisch gesehen muss das Subjekt eine Folge sein. Eine wichtige Ausnahme ist daher, dass Muster nicht auf Iteratoren passen. Außerdem passen Folgenmuster nicht auf Zeichenketten, um einem häufigen Fehler vorzubeugen.

  • Folgenmuster unterstützen Platzhalter: [x, y, *rest] und (x, y, *rest) arbeiten ähnlich wie Platzhalter in entpackenden Zuweisungen. Der Name nach * darf auch _ sein, sodass (x, y, *_) auf eine Folge mit mindestens zwei Elementen passt, ohne die übrigen Elemente zu binden.

  • Mapping-Muster: {"bandwidth": b, "latency": l} fängt die Werte "bandwidth" und "latency" aus einem Dictionary ein. Anders als bei Folgenmustern werden zusätzliche Schlüssel übergangen. Ein Platzhalter **rest wird ebenfalls unterstützt. (**_ wäre aber überflüssig und ist daher nicht erlaubt.)

  • Untermuster können mit dem Schlüsselwort as abgefangen werden:

    case (Point(x1, y1), Point(x2, y2) as p2): ...
    

    Das bindet x1, y1, x2, y2 so, wie du es ohne die as-Klausel erwarten würdest, und p2 an das gesamte zweite Element des Subjekts.

  • Die meisten Literale werden über Gleichheit verglichen. Die Singletons True, False und None werden allerdings über Identität verglichen.

  • Benannte Konstanten dürfen in Mustern verwendet werden. Diese benannten Konstanten müssen Namen mit Punkt sein, damit die Konstante nicht als einfangende Variable aufgefasst wird:

    from enum import Enum
    class Color(Enum):
        RED = 0
        GREEN = 1
        BLUE = 2
    
    color = Color.GREEN
    match color:
        case Color.RED:
            print("I see red!")
        case Color.GREEN:
            print("Grass is green")
        case Color.BLUE:
            print("I'm feeling the blues :(")
    

Die vollständige Spezifikation steht in PEP 634. Motivation und Begründung stehen in PEP 635, eine ausführlichere Einführung in PEP 636.

Optionale EncodingWarning und die Option encoding="locale"

Die voreingestellte Kodierung von TextIOWrapper und open() hängt von Plattform und Gebietsschema ab. Da auf den meisten Unix-Plattformen UTF-8 verwendet wird, ist es ein sehr häufiger Fehler, die Option encoding beim Öffnen von UTF-8-Dateien (etwa JSON, YAML, TOML, Markdown) weglassen. Zum Beispiel:

# FEHLER: Es sollte der Modus "rb" oder encoding="utf-8" verwendet werden.
with open("data.json") as f:
    data = json.load(f)

Um Fehler dieser Art zu finden, ist eine optionale EncodingWarning hinzugekommen. Sie wird ausgegeben, wenn sys.flags.warn_default_encoding wahr ist und die vom Gebietsschema abhängige voreingestellte Kodierung verwendet wird.

Die Option -X warn_default_encoding und PYTHONWARNDEFAULTENCODING sind hinzugekommen, um die Warnung einzuschalten.

Mehr dazu unter Text encoding.

Andere sprachliche Änderungen

  • Der Typ int hat eine neue Methode int.bit_count(), die die Anzahl der Einsen in der Binärdarstellung einer gegebenen ganzen Zahl zurückgibt, auch Population Count genannt. (Beigetragen von Niklas Fiekas in bpo-29882.)

  • Die Sichten, die dict.keys(), dict.values() und dict.items() zurückgeben, haben jetzt alle ein Attribut mapping, das ein types.MappingProxyType-Objekt um das ursprüngliche Dictionary liefert. (Beigetragen von Dennis Sweeney in bpo-40890.)

  • PEP 618: Die Funktion zip() hat jetzt einen optionalen Schalter strict, mit dem sich verlangen lässt, dass alle Iterables gleich lang sind.

  • Eingebaute und aus Erweiterungen stammende Funktionen, die ganzzahlige Argumente nehmen, nehmen keine Decimals, Fractions und andere Objekte mehr an, die sich nur verlustbehaftet in ganze Zahlen umwandeln lassen (die also die Methode __int__(), aber nicht die Methode __index__() haben). (Beigetragen von Serhiy Storchaka in bpo-37999.)

  • Gibt object.__ipow__() den Wert NotImplemented zurück, fällt der Operator jetzt wie erwartet richtig auf object.__pow__() und object.__rpow__() zurück. (Beigetragen von Alex Shkop in bpo-38302.)

  • Zuweisungsausdrücke lassen sich jetzt ohne Klammern in Mengenliteralen und Mengen-Comprehensions verwenden, ebenso in Folgenindizes (nicht aber in Slices).

  • Funktionen haben ein neues Attribut __builtins__, über das beim Ausführen einer Funktion nach eingebauten Symbolen gesucht wird, statt in __globals__['__builtins__'] nachzusehen. Das Attribut wird aus __globals__["__builtins__"] vorbelegt, sofern es vorhanden ist, sonst aus den aktuellen eingebauten Symbolen. (Beigetragen von Mark Shannon in bpo-42990.)

  • Zwei neue eingebaute Funktionen – aiter() und anext() – sind hinzugekommen. Sie sind die asynchronen Gegenstücke zu iter() beziehungsweise next(). (Beigetragen von Joshua Bronson, Daniel Pope und Justin Wang in bpo-31861.)

  • Statische Methoden (@staticmethod) und Klassenmethoden (@classmethod) erben jetzt die Methodenattribute (__module__, __name__, __qualname__, __doc__, __annotations__) und haben ein neues Attribut __wrapped__. Darüber hinaus sind statische Methoden jetzt wie gewöhnliche Funktionen aufrufbar. (Beigetragen von Victor Stinner in bpo-43682.)

  • Annotationen für komplexe Ziele (alles außer den Zielen simple name, die PEP 526 festlegt) haben mit from __future__ import annotations keine Wirkung zur Laufzeit mehr. (Beigetragen von Batuhan Taskaya in bpo-42737.)

  • Klassen- und Modulobjekte erzeugen leere Annotations-Dictionaries jetzt verzögert und nur bei Bedarf. Die Annotations-Dictionaries liegen aus Gründen der Rückwärtsverträglichkeit im __dict__ des Objekts. Damit verbessern sich die bewährten Vorgehensweisen beim Umgang mit __annotations__. Mehr dazu unter Best Practices für Annotationen. (Beigetragen von Larry Hastings in bpo-43901.)

  • Annotationen, die aus yield, yield from, await oder benannten Ausdrücken bestehen, sind unter from __future__ import annotations wegen ihrer Nebenwirkungen jetzt verboten. (Beigetragen von Batuhan Taskaya in bpo-42725.)

  • Die Verwendung ungebundener Variablen, von super() und anderer Ausdrücke, die die Verarbeitung der Symboltabelle verändern könnten, bleibt in Annotationen unter from __future__ import annotations jetzt ohne Wirkung. (Beigetragen von Batuhan Taskaya in bpo-42725.)

  • Die Hashwerte von NaN-Werten sowohl des Typs float als auch des Typs decimal.Decimal hängen jetzt von der Objektidentität ab. Früher ergaben sie immer 0, obwohl NaN-Werte untereinander nicht gleich sind. Das führte beim Erzeugen von Dictionaries und Mengen mit mehreren NaNs wegen der vielen Hash-Kollisionen zu möglicherweise quadratischem Laufzeitverhalten. (Beigetragen von Raymond Hettinger in bpo-43475.)

  • Beim Löschen der Konstanten __debug__ wird jetzt ein SyntaxError statt eines NameError ausgelöst. (Beigetragen von Donghee Na in bpo-45000.)

  • SyntaxError-Ausnahmen haben jetzt die Attribute end_lineno und end_offset. Sie sind None, wenn sie nicht bestimmt werden können. (Beigetragen von Pablo Galindo in bpo-43914.)

Neue Module

  • Keine.

Verbesserte Module

asyncio

Die fehlende Methode connect_accepted_socket() ist hinzugekommen. (Beigetragen von Alex Grönholm in bpo-41332.)

argparse

Die missverständliche Formulierung „optional arguments“ ist in der Hilfe von argparse durch „options“ ersetzt. Manche Tests müssen unter Umständen angepasst werden, wenn sie auf genaue Übereinstimmung der Ausgabe setzen. (Beigetragen von Raymond Hettinger in bpo-9694.)

Array

Die Methode index() von array.array hat jetzt die optionalen Parameter start und stop. (Beigetragen von Anders Lorentsen und Zackery Spytz in bpo-31956.)

asynchat, asyncore, smtpd

Diese Module sind in ihrer Moduldokumentation seit Python 3.6 als veraltet gekennzeichnet. Jetzt ist in allen drei Modulen eine DeprecationWarning beim Import hinzugekommen.

base64

base64.b32hexencode() und base64.b32hexdecode() sind hinzugekommen, um die Base32-Kodierung mit erweitertem Hex-Alphabet zu unterstützen.

bdb

clearBreakpoints() ist hinzugekommen, um alle gesetzten Haltepunkte zurückzusetzen. (Beigetragen von Irit Katriel in bpo-24160.)

bisect

Die Möglichkeit, den APIs im Modul bisect eine key-Funktion zu übergeben, ist hinzugekommen. (Beigetragen von Raymond Hettinger in bpo-4356.)

codecs

Eine Funktion codecs.unregister() ist hinzugekommen, um eine Suchfunktion für Codecs abzumelden. (Beigetragen von Hai Shi in bpo-41842.)

collections.abc

Die __args__ des parametrisierten generischen Typs für collections.abc.Callable stimmen jetzt mit typing.Callable überein. Der generische Typ collections.abc.Callable flacht Typparameter jetzt ab, ähnlich wie es typing.Callable derzeit tut. Das heißt, dass collections.abc.Callable[[int, str], str] jetzt __args__ von (int, str, str) hat. Vorher war es ([int, str], str). Um diese Änderung zu ermöglichen, lässt sich types.GenericAlias jetzt ableiten, und beim Indizieren des Typs collections.abc.Callable wird eine Unterklasse zurückgegeben. Beachte, dass für ungültige Formen der Parametrisierung von collections.abc.Callable jetzt ein TypeError ausgelöst werden kann, die in Python 3.9 vielleicht stillschweigend durchgingen. (Beigetragen von Ken Jin in bpo-42195.)

contextlib

Ein Kontextmanager contextlib.aclosing() ist hinzugekommen, um asynchrone Generatoren und Objekte, die asynchron freigegebene Ressourcen darstellen, gefahrlos zu schließen. (Beigetragen von Joongi Kim und John Belmonte in bpo-41229.)

Unterstützung für asynchrone Kontextmanager ist in contextlib.nullcontext() hinzugekommen. (Beigetragen von Tom Gringauz in bpo-41543.)

AsyncContextDecorator ist hinzugekommen, um asynchrone Kontextmanager als Dekoratoren verwenden zu können.

curses

Die in ncurses 6.1 hinzugekommenen erweiterten Farbfunktionen werden von curses.color_content(), curses.init_color(), curses.init_pair() und curses.pair_content() jetzt ohne weiteres Zutun verwendet. Eine neue Funktion, curses.has_extended_color_support(), zeigt an, ob die zugrunde liegende ncurses-Bibliothek die erweiterte Farbunterstützung bietet. (Beigetragen von Jeffrey Kintscher und Hans Petter Jansson in bpo-36982.)

Die BUTTON5_*-Konstanten sind jetzt im Modul curses zugänglich, sofern die zugrunde liegende curses-Bibliothek sie bereitstellt. (Beigetragen von Zackery Spytz in bpo-39273.)

dataclasses

__slots__

Der Parameter slots ist im Dekorator @dataclasses.dataclass hinzugekommen. (Beigetragen von Yurii Karabas in bpo-42269)

Felder nur über Schlüsselwort

dataclasses unterstützt jetzt Felder, die in der erzeugten __init__-Methode nur über Schlüsselwort angebbar sind. Es gibt mehrere Möglichkeiten, solche Felder anzugeben.

Du kannst festlegen, dass jedes Feld nur über Schlüsselwort angebbar ist:

from dataclasses import dataclass

@dataclass(kw_only=True)
class Birthday:
    name: str
    birthday: datetime.date

name und birthday sind beide nur über Schlüsselwort angebbare Parameter der erzeugten __init__-Methode.

Du kannst auch je Feld festlegen, dass es nur über Schlüsselwort angebbar ist:

from dataclasses import dataclass, field

@dataclass
class Birthday:
    name: str
    birthday: datetime.date = field(kw_only=True)

Hier ist nur birthday nur über Schlüsselwort angebbar. Setzt du kw_only an einzelnen Feldern, beachte, dass es Regeln für die Neuanordnung der Felder gibt, weil Felder, die nur über Schlüsselwort angebbar sind, hinter den übrigen stehen müssen. Einzelheiten stehen in der vollständigen Dokumentation zu dataclasses.

Du kannst außerdem festlegen, dass alle Felder nach einer KW_ONLY-Markierung nur über Schlüsselwort angebbar sind. Das wird wahrscheinlich die häufigste Verwendung sein:

from dataclasses import dataclass, KW_ONLY

@dataclass
class Point:
    x: float
    y: float
    _: KW_ONLY
    z: float = 0.0
    t: float = 0.0

Hier sind z und t nur über Schlüsselwort angebbare Parameter, x und y dagegen nicht. (Beigetragen von Eric V. Smith in bpo-43532.)

distutils

Das gesamte Paket distutils ist als veraltet markiert und wird in Python 3.12 entfernt. Seine Funktionalität zum Festlegen von Paket-Builds ist von den Paketen setuptools und packaging von Dritten schon vollständig ersetzt, und die meisten übrigen häufig verwendeten APIs sind an anderer Stelle in der Standardbibliothek zu finden (etwa in platform, shutil, subprocess oder sysconfig). Es ist nicht geplant, weitere Funktionalität aus distutils umzusiedeln; Anwendungen, die andere Funktionen verwenden, sollten eigene Kopien des Codes einplanen. Die Diskussion steht in PEP 632.

Der in Python 3.8 als veraltet markierte Befehl bdist_wininst ist entfernt. Um Binärpakete unter Windows zu verteilen, wird jetzt der Befehl bdist_wheel empfohlen. (Beigetragen von Victor Stinner in bpo-42802.)

doctest

Definiert ein Modul kein __loader__, wird jetzt auf __spec__.loader zurückgegriffen. (Beigetragen von Brett Cannon in bpo-42133.)

encodings

encodings.normalize_encoding() übergeht jetzt Zeichen außerhalb von ASCII. (Beigetragen von Hai Shi in bpo-39337.)

enum

__repr__() von Enum gibt jetzt enum_name.member_name zurück und __str__() jetzt member_name. Enums aus der Standardbibliothek, die als Modulkonstanten verfügbar sind, haben ein repr() von module_name.member_name. (Beigetragen von Ethan Furman in bpo-40066.)

enum.StrEnum ist für Enums hinzugekommen, bei denen alle Mitglieder Zeichenketten sind. (Beigetragen von Ethan Furman in bpo-41816.)

fileinput

Die Parameter encoding und errors sind in fileinput.input() und fileinput.FileInput hinzugekommen. (Beigetragen von Inada Naoki in bpo-43712.)

fileinput.hook_compressed() gibt jetzt ein TextIOWrapper-Objekt zurück, wenn mode „r“ ist und die Datei komprimiert ist, so wie bei unkomprimierten Dateien. (Beigetragen von Inada Naoki in bpo-5758.)

faulthandler

Das Modul faulthandler erkennt jetzt, wenn ein schwerer Fehler während eines Durchlaufs der Speicherbereinigung auftritt. (Beigetragen von Victor Stinner in bpo-44466.)

gc

Audit-Hooks für gc.get_objects(), gc.get_referrers() und gc.get_referents() sind hinzugekommen. (Beigetragen von Pablo Galindo in bpo-43439.)

glob

Die Parameter root_dir und dir_fd sind in glob() und iglob() hinzugekommen. Damit lässt sich das Wurzelverzeichnis für die Suche angeben. (Beigetragen von Serhiy Storchaka in bpo-38144.)

hashlib

Das Modul hashlib setzt OpenSSL 1.1.1 oder neuer voraus. (Beigetragen von Christian Heimes in PEP 644 und bpo-43669.)

Das Modul hashlib unterstützt OpenSSL 3.0.0 vorläufig. (Beigetragen von Christian Heimes in bpo-38820 und weiteren Issues.)

Die reine Python-Rückfallebene von pbkdf2_hmac() ist als veraltet markiert. Künftig steht PBKDF2-HMAC nur dann zur Verfügung, wenn Python mit OpenSSL-Unterstützung gebaut wurde. (Beigetragen von Christian Heimes in bpo-43880.)

hmac

Das Modul hmac verwendet intern jetzt die HMAC-Umsetzung von OpenSSL. (Beigetragen von Christian Heimes in bpo-40645.)

IDLE und idlelib

IDLE ruft jetzt sys.excepthook() auf (wenn es ohne „-n“ gestartet wurde). Hooks der Anwender wurden vorher übergangen. (Beigetragen von Ken Hilton in bpo-43008.)

Der Einstellungsdialog ist neu geordnet. Der Reiter „General“ ist in die Reiter „Windows“ und „Shell/Ed“ aufgeteilt. Die Hilfequellen, die das Hilfemenü erweitern, sind in den Reiter „Extensions“ umgezogen. So entsteht Platz für neue Optionen, und der Dialog wird kürzer. Letzteres lässt ihn besser auf kleine Bildschirme passen. (Beigetragen von Terry Jan Reedy in bpo-40468.) Die Einstellung für die Einrückungsbreite ist vom Reiter „Font“ in den neuen Reiter „Windows“ umgezogen. (Beigetragen von Mark Roseman und Terry Jan Reedy in bpo-33962.)

Die obigen Änderungen sind in eine Wartungsausgabe von 3.9 zurückportiert.

Eine Seitenleiste für die Shell ist hinzugekommen. Der Hauptprompt („>>>“) ist in die Seitenleiste umgezogen. Folgeprompts („…“) sind in der Seitenleiste hinzugekommen. Ein Linksklick und ein wahlweises Ziehen wählen eine oder mehrere Textzeilen aus, so wie in der Seitenleiste mit den Zeilennummern des Editors. Ein Rechtsklick nach dem Auswählen von Textzeilen zeigt ein Kontextmenü mit „copy with prompts“. Das fügt die Prompts aus der Seitenleiste mit den Zeilen des ausgewählten Textes zusammen. Diese Option erscheint auch im Kontextmenü des Textes. (Beigetragen von Tal Einat in bpo-37903.)

Interaktiver Code wird jetzt mit Leerzeichen statt mit Tabulatoren eingerückt. Damit „sehen“ interaktive Codeeingaben „richtig aus“. Das möglich zu machen war ein wichtiger Anlass dafür, die Seitenleiste für die Shell hinzuzufügen. (Beigetragen von Terry Jan Reedy in bpo-37892.)

Die neuen weichen Schlüsselwörter match, case und _ werden in Anweisungen zum Mustervergleichen hervorgehoben. Diese Hervorhebung ist allerdings nicht fehlerfrei und in einigen seltenen Fällen falsch, darunter manche _ in case-Mustern. (Beigetragen von Tal Einat in bpo-44010.)

Neu in den Wartungsausgaben von 3.10.

Syntaxhervorhebung wird jetzt auch auf .pyi-Dateien angewendet. (Beigetragen von Alex Waygood und Terry Jan Reedy in bpo-45447.)

Beim Speichern der Shell mit Ein- und Ausgaben werden die Prompts mitgenommen. (Beigetragen von Terry Jan Reedy in gh-95191.)

importlib.metadata

Gleicher Funktionsumfang wie importlib_metadata 4.6 (Versionsgeschichte).

Einsprungpunkte in importlib.metadata lassen sich jetzt über eine neue Klasse importlib.metadata.EntryPoints angenehmer nach Gruppe und Name auswählen. Mehr zur Abkündigung und zur Verwendung steht im Hinweis zur Verträglichkeit in der Dokumentation.

importlib.metadata.packages_distributions() ist hinzugekommen, um Python-Module und -Pakete der obersten Ebene ihrer importlib.metadata.Distribution zuzuordnen.

inspect

Definiert ein Modul kein __loader__, wird jetzt auf __spec__.loader zurückgegriffen. (Beigetragen von Brett Cannon in bpo-42133.)

inspect.get_annotations() ist hinzugekommen. Die Funktion ermittelt gefahrlos die an einem Objekt definierten Annotationen. Sie umgeht die Eigenheiten des Zugriffs auf die Annotationen verschiedener Objektarten und macht sehr wenige Annahmen über das untersuchte Objekt. inspect.get_annotations() kann Annotationen, die als Zeichenkette vorliegen, auch richtig zurückverwandeln. inspect.get_annotations() gilt jetzt als die bewährte Vorgehensweise, um auf das an einem Python-Objekt definierte Annotations-Dictionary zuzugreifen. Mehr zu den bewährten Vorgehensweisen beim Umgang mit Annotationen steht unter Best Practices für Annotationen. Dazu passend rufen inspect.signature(), inspect.Signature.from_callable() und inspect.Signature.from_function() jetzt inspect.get_annotations() auf, um Annotationen zu holen. Das heißt, dass inspect.signature() und inspect.Signature.from_callable() jetzt ebenfalls Annotationen aus Zeichenketten zurückverwandeln können. (Beigetragen von Larry Hastings in bpo-43817.)

itertools

itertools.pairwise() ist hinzugekommen. (Beigetragen von Raymond Hettinger in bpo-38200.)

linecache

Definiert ein Modul kein __loader__, wird jetzt auf __spec__.loader zurückgegriffen. (Beigetragen von Brett Cannon in bpo-42133.)

os

Unterstützung für os.cpu_count() auf dem Echtzeitbetriebssystem VxWorks ist hinzugekommen. (Beigetragen von Peixing Xin in bpo-41440.)

Eine neue Funktion os.eventfd() und zugehörige Hilfsmittel sind hinzugekommen, die den Systemaufruf eventfd2 unter Linux umhüllen. (Beigetragen von Christian Heimes in bpo-41001.)

os.splice() ist hinzugekommen. Damit lassen sich Daten zwischen zwei Dateideskriptoren verschieben, ohne zwischen Kernel- und Anwenderadressraum zu kopieren, wobei einer der Dateideskriptoren auf eine Pipe verweisen muss. (Beigetragen von Pablo Galindo in bpo-41625.)

O_EVTONLY, O_FSYNC, O_SYMLINK und O_NOFOLLOW_ANY sind für macOS hinzugekommen. (Beigetragen von Donghee Na in bpo-43106.)

os.path

os.path.realpath() nimmt jetzt ein nur über Schlüsselwort angebbares Argument strict an. Ist es True, wird ein OSError ausgelöst, wenn ein Pfad nicht vorhanden ist oder ein Kreis aus symbolischen Verweisen auftritt. (Beigetragen von Barney Gale in bpo-43757.)

pathlib

Unterstützung für Slices ist in PurePath.parents hinzugekommen. (Beigetragen von Joshua Cannon in bpo-35498.)

Unterstützung für negative Indizes ist in PurePath.parents hinzugekommen. (Beigetragen von Yaroslav Pankovych in bpo-21041.)

Die Methode Path.hardlink_to ist hinzugekommen. Sie ersetzt link_to(). Die neue Methode hat dieselbe Argumentreihenfolge wie symlink_to(). (Beigetragen von Barney Gale in bpo-39950.)

pathlib.Path.stat() und chmod() nehmen jetzt ein nur über Schlüsselwort angebbares Argument follow_symlinks an, in Übereinstimmung mit den entsprechenden Funktionen im Modul os. (Beigetragen von Barney Gale in bpo-39906.)

platform

platform.freedesktop_os_release() ist hinzugekommen, um die Kennung des Betriebssystems aus der Standarddatei os-release von freedesktop.org zu lesen. (Beigetragen von Christian Heimes in bpo-28468.)

pprint

pprint.pprint() nimmt jetzt ein neues Schlüsselwortargument underscore_numbers an. (Beigetragen von sblondon in bpo-42914.)

pprint kann jetzt auch dataclasses.dataclass-Instanzen ansprechend ausgeben. (Beigetragen von Lewis Gaul in bpo-43080.)

py_compile

Die Option --quiet ist in der Befehlszeilenschnittstelle von py_compile hinzugekommen. (Beigetragen von Gregory Schevchenko in bpo-38731.)

pyclbr

Ein Attribut end_lineno ist bei den Function- und Class-Objekten im Baum hinzugekommen, den pyclbr.readmodule() und pyclbr.readmodule_ex() zurückgeben. Es passt zum vorhandenen lineno, das die Anfangszeile angibt. (Beigetragen von Aviral Srivastava in bpo-38307.)

shelve

Das Modul shelve verwendet beim Erzeugen von Shelves jetzt von sich aus pickle.DEFAULT_PROTOCOL statt pickle-Protokoll 3. (Beigetragen von Zackery Spytz in bpo-34204.)

statistics

Die Funktionen covariance(), Pearsons correlation() und eine einfache linear_regression() sind hinzugekommen. (Beigetragen von Tymoteusz Wołodźko in bpo-38490.)

site

Definiert ein Modul kein __loader__, wird jetzt auf __spec__.loader zurückgegriffen. (Beigetragen von Brett Cannon in bpo-42133.)

socket

Die Ausnahme socket.timeout ist jetzt ein anderer Name für TimeoutError. (Beigetragen von Christian Heimes in bpo-42413.)

Eine Möglichkeit, MPTCP-Sockets mit IPPROTO_MPTCP zu erzeugen, ist hinzugekommen. (Beigetragen von Rui Cunha in bpo-43571.)

Die Option IP_RECVTOS ist hinzugekommen, um den Dienstgütetyp (ToS) oder die DSCP/ECN-Felder zu empfangen. (Beigetragen von Georg Sauthoff in bpo-44077.)

ssl

Das Modul ssl setzt OpenSSL 1.1.1 oder neuer voraus. (Beigetragen von Christian Heimes in PEP 644 und bpo-43669.)

Das Modul ssl unterstützt OpenSSL 3.0.0 vorläufig und hat eine neue Option OP_IGNORE_UNEXPECTED_EOF. (Beigetragen von Christian Heimes in bpo-38820, bpo-43794, bpo-43788, bpo-43791, bpo-43799, bpo-43920, bpo-43789 und bpo-43811.)

Als veraltet markierte Funktionen und die Verwendung als veraltet markierter Konstanten führen jetzt zu einer DeprecationWarning. In ssl.SSLContext.options sind OP_NO_SSLv2 und OP_NO_SSLv3 von sich aus gesetzt, weshalb nicht gewarnt werden kann, wenn der Schalter erneut gesetzt wird. Der Abschnitt zu den Abkündigungen enthält eine Liste der als veraltet markierten Features. (Beigetragen von Christian Heimes in bpo-43880.)

Das Modul ssl hat jetzt sicherere Voreinstellungen. Verschlüsselungsverfahren ohne vorwärtsgerichtete Geheimhaltung oder mit SHA-1-MAC sind von sich aus abgeschaltet. Sicherheitsstufe 2 verbietet schwache RSA-, DH- und ECC-Schlüssel mit weniger als 112 Bit Sicherheit. SSLContext hat als voreingestellte Mindestprotokollversion TLS 1.2. Die Einstellungen beruhen auf Untersuchungen von Hynek Schlawack. (Beigetragen von Christian Heimes in bpo-43998.)

Die als veraltet markierten Protokolle SSL 3.0, TLS 1.0 und TLS 1.1 werden nicht mehr offiziell unterstützt. Python blockiert sie nicht aktiv. Build-Optionen von OpenSSL, Konfigurationen der Distribution, Patches des Herstellers und Cipher-Suites können einen erfolgreichen Handshake aber verhindern.

Ein Parameter timeout ist in der Funktion ssl.get_server_certificate() hinzugekommen. (Beigetragen von Zackery Spytz in bpo-31870.)

Das Modul ssl verwendet Heap-Typen und eine mehrstufige Initialisierung. (Beigetragen von Christian Heimes in bpo-42333.)

Ein neuer Prüfschalter VERIFY_X509_PARTIAL_CHAIN ist hinzugekommen. (Beigetragen von l0x in bpo-40849.)

sqlite3

Audit-Ereignisse für connect(), enable_load_extension() und load_extension() sind hinzugekommen. (Beigetragen von Erlend E. Aasland in bpo-43762.)

sys

Das Attribut sys.orig_argv ist hinzugekommen: die Liste der ursprünglichen Befehlszeilenargumente, die der ausführbaren Python-Datei übergeben wurden. (Beigetragen von Victor Stinner in bpo-23427.)

sys.stdlib_module_names ist hinzugekommen. Es enthält die Liste der Modulnamen der Standardbibliothek. (Beigetragen von Victor Stinner in bpo-42955.)

_thread

_thread.interrupt_main() nimmt jetzt wahlweise eine Signalnummer, die nachgebildet werden soll (die Voreinstellung ist weiterhin signal.SIGINT). (Beigetragen von Antoine Pitrou in bpo-43356.)

threading

threading.gettrace() und threading.getprofile() sind hinzugekommen, um die Funktionen zu holen, die threading.settrace() beziehungsweise threading.setprofile() gesetzt haben. (Beigetragen von Mario Corchero in bpo-42251.)

threading.__excepthook__ ist hinzugekommen, um den ursprünglichen Wert von threading.excepthook() holen zu können, falls er auf einen fehlerhaften oder anderen Wert gesetzt ist. (Beigetragen von Mario Corchero in bpo-42308.)

traceback

Die Funktionen format_exception(), format_exception_only() und print_exception() können jetzt ein Ausnahmeobjekt als ausschließlich positionsbezogenes Argument nehmen. (Beigetragen von Zackery Spytz und Matthias Bussonnier in bpo-26389.)

types

Die Klassen types.EllipsisType, types.NoneType und types.NotImplementedType sind wieder eingeführt. Sie bieten eine neue Reihe von Typen, die Typprüfer unmittelbar deuten können. (Beigetragen von Bas van Beek in bpo-41810.)

typing

Die wichtigsten Änderungen stehen unter Neue Funktionen im Zusammenhang mit Typ-Hinweisen.

Das Verhalten von typing.Literal ist geändert, damit es PEP 586 entspricht und zum Verhalten statischer Typprüfer passt, wie es das PEP festlegt.

  1. Literal entfernt jetzt doppelte Parameter.

  2. Gleichheitsvergleiche zwischen Literal-Objekten sind jetzt unabhängig von der Reihenfolge.

  3. Literal-Vergleiche beachten jetzt die Typen. Literal[0] == Literal[False] ergab zum Beispiel vorher True. Jetzt ergibt es False. Um diese Änderung zu ermöglichen, kann der intern verwendete Typzwischenspeicher jetzt Typen unterscheiden.

  4. Literal-Objekte lösen bei Gleichheitsvergleichen jetzt eine TypeError-Ausnahme aus, wenn einer ihrer Parameter nicht hashbar ist. Beachte, dass ein Literal mit nicht hashbaren Parametern zu deklarieren keinen Fehler auslöst:

    >>> from typing import Literal
    >>> Literal[{0}]
    >>> Literal[{0}] == Literal[{False}]
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    TypeError: unhashable type: 'set'
    

(Beigetragen von Yurii Karabas in bpo-42345.)

Die neue Funktion typing.is_typeddict() ist hinzugekommen, um zu prüfen, ob eine Annotation ein typing.TypedDict ist. (Beigetragen von Patrick Reader in bpo-41792.)

Unterklassen von typing.Protocol, in denen nur Datenvariablen deklariert sind, lösen bei einer Prüfung mit isinstance jetzt einen TypeError aus, sofern sie nicht mit @~typing.runtime_checkable dekoriert sind. Vorher gingen diese Prüfungen stillschweigend durch. Wer Protokolle zur Laufzeit möchte, sollte seine Unterklassen mit dem Dekorator @runtime_checkable dekorieren. (Beigetragen von Yurii Karabas in bpo-38908.)

Ein Import aus den Untermodulen typing.io und typing.re gibt jetzt eine DeprecationWarning aus. Diese Untermodule sind seit Python 3.8 als veraltet markiert und werden in einer künftigen Python-Version entfernt. Alles, was zu diesen Untermodulen gehört, sollte stattdessen unmittelbar aus typing importiert werden. (Beigetragen von Sebastian Rittau in bpo-38291.)

unittest

Die neue Methode assertNoLogs() ist als Ergänzung zur vorhandenen assertLogs() hinzugekommen. (Beigetragen von Kit Yan Choi in bpo-39385.)

urllib.parse

Python-Versionen vor Python 3.10 erlaubten es, in urllib.parse.parse_qs() und urllib.parse.parse_qsl() sowohl ; als auch & als Trennzeichen für Abfrageparameter zu verwenden. Aus Sicherheitsgründen und in Übereinstimmung mit neueren Empfehlungen des W3C ist das jetzt auf ein einziges Trennzeichen beschränkt, mit & als Voreinstellung. Diese Änderung betrifft auch cgi.parse() und cgi.parse_multipart(), denn sie verwenden die betroffenen Funktionen intern. Weitere Einzelheiten stehen in der jeweiligen Dokumentation. (Beigetragen von Adam Goldschmidt, Senthil Kumaran und Ken Jin in bpo-42967.)

Zeilenumbruch- und Tabulatorzeichen in Teilen einer URL ermöglichen manche Formen von Angriffen. Entsprechend der WHATWG-Spezifikation, die RFC 3986 aktualisiert, entfernt der Parser in urllib.parse die ASCII-Zeichen für Zeilenumbruch, \n und \r, sowie das Tabulatorzeichen \t aus der URL und verhindert so solche Angriffe. Welche Zeichen entfernt werden, steuert eine neue Variable auf Modulebene, urllib.parse._UNSAFE_URL_BYTES_TO_REMOVE. (Siehe gh-88048)

xml

Eine Klasse LexicalHandler ist im Modul xml.sax.handler hinzugekommen. (Beigetragen von Jonathan Gossage und Zackery Spytz in bpo-35018.)

zipimport

Methoden zu PEP 451 sind hinzugekommen: find_spec(), zipimport.zipimporter.create_module() und zipimport.zipimporter.exec_module(). (Beigetragen von Brett Cannon in bpo-42131.)

Die Methode invalidate_caches() ist hinzugekommen. (Beigetragen von Desmond Cheong in bpo-14678.)

Optimierungen

  • Die Konstruktoren str(), bytes() und bytearray() sind jetzt schneller (bei kleinen Objekten etwa 30 bis 40 %). (Beigetragen von Serhiy Storchaka in bpo-41334.)

  • Das Modul runpy importiert jetzt weniger Module. Der Start über python3 -m module-name ist im Mittel um das 1,4-Fache schneller. Unter Linux importiert python3 -I -m module-name in Python 3.9 69 Module, in Python 3.10 dagegen nur 51 (-18). (Beigetragen von Victor Stinner in bpo-41006 und bpo-41718.)

  • Die Anweisung LOAD_ATTR verwendet jetzt einen neuen Mechanismus mit einem „Zwischenspeicher je Opcode“. Sie ist bei gewöhnlichen Attributen jetzt etwa 36 % und bei Slots 44 % schneller. (Beigetragen von Pablo Galindo und Yury Selivanov in bpo-42093 und Guido van Rossum in bpo-42927, auf Grundlage von Ideen, die ursprünglich in PyPy und MicroPython umgesetzt wurden.)

  • Wird Python mit --enable-optimizations gebaut, wird jetzt -fno-semantic-interposition sowohl beim Kompilieren als auch beim Binden hinzugefügt. Damit werden mit gcc erzeugte Builds des Python-Interpreters mit --enable-shared um bis zu 30 % schneller. Weitere Einzelheiten stehen in diesem Artikel. (Beigetragen von Victor Stinner und Pablo Galindo in bpo-38980.)

  • Für die Module bz2, lzma und zlib wird ein neuer Code zur Verwaltung des Ausgabepuffers verwendet, und eine Funktion .readall() ist in der Klasse _compression.DecompressReader hinzugekommen. Das Entpacken mit bz2 ist jetzt um das 1,09- bis 1,17-Fache schneller, das Entpacken mit lzma um das 1,20- bis 1,32-Fache und GzipFile.read(-1) um das 1,11- bis 1,18-Fache. (Beigetragen von Ma Lin, begutachtet von Gregory P. Smith, in bpo-41486)

  • Werden Annotationen als Zeichenketten verwendet, werden die Annotations-Dictionaries für Funktionen nicht mehr beim Erzeugen der Funktion angelegt. Stattdessen liegen sie als Tupel von Zeichenketten vor, und das Funktionsobjekt verwandelt dieses erst bei Bedarf in das Annotations-Dictionary. Diese Optimierung halbiert die CPU-Zeit, die das Definieren einer annotierten Funktion braucht. (Beigetragen von Yurii Karabas und Inada Naoki in bpo-42202.)

  • Funktionen zur Teilzeichenkettensuche wie str1 in str2 und str2.find(str1) verwenden jetzt mitunter den „Two-Way“-Suchalgorithmus von Crochemore und Perrin, um quadratisches Verhalten bei langen Zeichenketten zu vermeiden. (Beigetragen von Dennis Sweeney in bpo-41972)

  • Kleine Optimierungen sind in _PyType_Lookup() hinzugekommen, um die Geschwindigkeit der Suche im Typattribut-Zwischenspeicher im häufigen Fall eines Treffers zu verbessern. Damit ist der Interpreter im Mittel um das 1,04-Fache schneller. (Beigetragen von Dino Viehland in bpo-43452.)

  • Die folgenden eingebauten Funktionen unterstützen jetzt die schnellere Aufrufkonvention Vectorcall aus PEP 590: map(), filter(), reversed(), bool() und float(). (Beigetragen von Donghee Na und Jeroen Demeyer in bpo-43575, bpo-43287, bpo-41922, bpo-41873 und bpo-41870.)

  • BZ2File ist schneller geworden, weil ein internes RLock entfallen ist. Damit ist BZ2File bei mehreren gleichzeitigen Lesern oder Schreibern nicht threadsicher, so wie es die entsprechenden Klassen in gzip und lzma schon immer waren. (Beigetragen von Inada Naoki in bpo-43785.)

Als veraltet markiert

  • Derzeit nimmt Python Zahlenliterale an, auf die unmittelbar ein Schlüsselwort folgt, zum Beispiel 0in x, 1or x, 0if 1else 2. Das erlaubt verwirrende und mehrdeutige Ausdrücke wie [0x1for x in y] (das sich als [0x1 for x in y] oder als [0x1f or x in y] deuten lässt). Ab dieser Ausgabe wird eine Warnung über eine Abkündigung ausgelöst, wenn unmittelbar auf das Zahlenliteral eines der Schlüsselwörter and, else, for, if, in, is oder or folgt. In künftigen Ausgaben wird daraus eine Syntaxwarnung und schließlich ein Syntaxfehler. (Beigetragen von Serhiy Storchaka in bpo-43833.)

  • Ab dieser Ausgabe wird gezielt daran gearbeitet, die alte Importsemantik aufzuräumen, die zur Verträglichkeit mit Python 2.7 erhalten blieb. Im Einzelnen werden find_loader() und find_module() (ersetzt durch find_spec()), importlib.abc.Loader.load_module (ersetzt durch exec_module()), module_repr() (das das Importsystem für dich übernimmt), das Attribut __package__ (ersetzt durch __spec__.parent), das Attribut __loader__ (ersetzt durch __spec__.loader) und das Attribut __cached__ (ersetzt durch __spec__.cached) allmählich entfernt (ebenso weitere Klassen und Methoden in importlib). Dabei werden je nach Lage ImportWarning und DeprecationWarning ausgelöst, um Code zu finden, der während dieses Übergangs angepasst werden muss.

  • Der gesamte Namensraum distutils ist als veraltet markiert und wird in Python 3.12 entfernt. Mehr dazu im Abschnitt Änderungen an den Modulen.

  • Nicht ganzzahlige Argumente für random.randrange() sind als veraltet markiert. Der ValueError ist zugunsten eines TypeError als veraltet markiert. (Beigetragen von Serhiy Storchaka und Raymond Hettinger in bpo-37319.)

  • Die verschiedenen load_module()-Methoden von importlib sind in der Dokumentation seit Python 3.6 als veraltet gekennzeichnet, lösen jetzt aber auch eine DeprecationWarning aus. Verwende stattdessen exec_module(). (Beigetragen von Brett Cannon in bpo-26131.)

  • zimport.zipimporter.load_module() ist zugunsten von exec_module() als veraltet markiert. (Beigetragen von Brett Cannon in bpo-26131.)

  • Verwendet das Importsystem importlib.abc.Loader.load_module, löst das jetzt eine ImportWarning aus, denn exec_module() ist vorzuziehen. (Beigetragen von Brett Cannon in bpo-26131.)

  • Verwendet das Importsystem importlib.abc.MetaPathFinder.find_module() oder importlib.abc.PathEntryFinder.find_module(), löst das jetzt eine ImportWarning aus, denn importlib.abc.MetaPathFinder.find_spec() beziehungsweise importlib.abc.PathEntryFinder.find_spec() sind vorzuziehen. Beim Umstieg hilft importlib.util.spec_from_loader(). (Beigetragen von Brett Cannon in bpo-42134.)

  • Verwendet das Importsystem importlib.abc.PathEntryFinder.find_loader(), löst das jetzt eine ImportWarning aus, denn importlib.abc.PathEntryFinder.find_spec() ist vorzuziehen. Beim Umstieg hilft importlib.util.spec_from_loader(). (Beigetragen von Brett Cannon in bpo-43672.)

  • Die verschiedenen Umsetzungen von importlib.abc.MetaPathFinder.find_module() ( importlib.machinery.BuiltinImporter.find_module(), importlib.machinery.FrozenImporter.find_module(), importlib.machinery.WindowsRegistryFinder.find_module(), importlib.machinery.PathFinder.find_module(), importlib.abc.MetaPathFinder.find_module() ), von importlib.abc.PathEntryFinder.find_module() ( importlib.machinery.FileFinder.find_module() ) und von importlib.abc.PathEntryFinder.find_loader() ( importlib.machinery.FileFinder.find_loader() ) lösen jetzt eine DeprecationWarning aus und sollen in Python 3.12 entfernt werden (vorher waren sie in Python 3.4 als veraltet dokumentiert). (Beigetragen von Brett Cannon in bpo-42135.)

  • importlib.abc.Finder ist als veraltet markiert (einschließlich seiner einzigen Methode find_module()). Weder importlib.abc.MetaPathFinder noch importlib.abc.PathEntryFinder erben noch von dieser Klasse. Leite stattdessen je nach Fall von einer dieser beiden Klassen ab. (Beigetragen von Brett Cannon in bpo-42135.)

  • Bei den Abkündigungen von imp, importlib.find_loader(), importlib.util.set_package_wrapper(), importlib.util.set_loader_wrapper(), importlib.util.module_for_loader(), pkgutil.ImpImporter und pkgutil.ImpLoader ist jetzt überall Python 3.12 als vorgesehene Version der Entfernung angegeben (sie lösten schon in früheren Python-Versionen eine DeprecationWarning aus). (Beigetragen von Brett Cannon in bpo-43720.)

  • Das Importsystem verwendet für die __repr__()-Methode eines Moduls jetzt das Attribut __spec__ am Modul, bevor es auf module_repr() zurückgreift. Die Verwendung von module_repr() soll in Python 3.12 entfallen. (Beigetragen von Brett Cannon in bpo-42137.)

  • importlib.abc.Loader.module_repr(), importlib.machinery.FrozenLoader.module_repr() und importlib.machinery.BuiltinLoader.module_repr() sind als veraltet markiert und sollen in Python 3.12 entfernt werden. (Beigetragen von Brett Cannon in bpo-42136.)

  • sqlite3.OptimizedUnicode ist seit Python 3.3 nicht dokumentiert und überholt, denn seitdem ist es ein anderer Name für str. Es ist jetzt als veraltet markiert, die Entfernung ist für Python 3.12 geplant. (Beigetragen von Erlend E. Aasland in bpo-42264.)

  • Die nicht dokumentierte eingebaute Funktion sqlite3.enable_shared_cache ist jetzt als veraltet markiert, die Entfernung ist für Python 3.12 geplant. Die SQLite3-Dokumentation rät entschieden von ihrer Verwendung ab. Weitere Einzelheiten stehen in der SQLite3-Dokumentation. Muss ein gemeinsamer Zwischenspeicher verwendet werden, öffne die Datenbank im URI-Modus mit dem Abfrageparameter cache=shared. (Beigetragen von Erlend E. Aasland in bpo-24464.)

  • Die folgenden threading-Methoden sind jetzt als veraltet markiert:

    (Beigetragen von Jelle Zijlstra in gh-87889.)

  • pathlib.Path.link_to() ist als veraltet markiert und soll in Python 3.12 entfernt werden. Verwende stattdessen pathlib.Path.hardlink_to(). (Beigetragen von Barney Gale in bpo-39950.)

  • cgi.log() ist als veraltet markiert und soll in Python 3.12 entfernt werden. (Beigetragen von Inada Naoki in bpo-41139.)

  • Die folgenden ssl-Features sind seit Python 3.6, Python 3.7 oder OpenSSL 1.1.0 als veraltet markiert und werden in 3.11 entfernt:

  • Die Thread-Fehlersuche (Umgebungsvariable PYTHONTHREADDEBUG) ist in Python 3.10 als veraltet markiert und wird in Python 3.12 entfernt. Dieses Feature setzt einen Debug-Build von Python voraus. (Beigetragen von Victor Stinner in bpo-44584.)

  • Ein Import aus den Untermodulen typing.io und typing.re gibt jetzt eine DeprecationWarning aus. Diese Untermodule werden in einer künftigen Python-Version entfernt. Alles, was zu diesen Untermodulen gehört, sollte stattdessen unmittelbar aus typing importiert werden. (Beigetragen von Sebastian Rittau in bpo-38291.)

Entfernt

  • Die besonderen Methoden __int__, __float__, __floordiv__, __mod__, __divmod__, __rfloordiv__, __rmod__ und __rdivmod__ der Klasse complex sind entfernt. Sie lösten immer einen TypeError aus. (Beigetragen von Serhiy Storchaka in bpo-41974.)

  • Die Methode ParserBase.error() aus dem privaten und nicht dokumentierten Modul _markupbase ist entfernt. html.parser.HTMLParser ist die einzige Unterklasse von ParserBase, und dort war die Umsetzung von error() schon in Python 3.5 entfernt worden. (Beigetragen von Berker Peksag in bpo-31844.)

  • Das Attribut unicodedata.ucnhash_CAPI ist entfernt. Es war ein internes PyCapsule-Objekt. Die zugehörige private Struktur _PyUnicode_Name_CAPI ist in die interne C-API umgezogen. (Beigetragen von Victor Stinner in bpo-42157.)

  • Das Modul parser ist entfernt. Es war in 3.9 wegen des Wechsels auf den neuen PEG-Parser als veraltet markiert worden. Entfernt sind ebenso alle C-Quell- und Header-Dateien, die nur der alte Parser verwendet hat, darunter node.h, parser.h, graminit.h und grammar.h.

  • Die öffentlichen C-API-Funktionen PyParser_SimpleParseStringFlags, PyParser_SimpleParseStringFlagsFilename, PyParser_SimpleParseFileFlags und PyNode_Compile sind entfernt. Sie waren in 3.9 wegen des Wechsels auf den neuen PEG-Parser als veraltet markiert worden.

  • Das Modul formatter ist entfernt. Es war in Python 3.4 als veraltet markiert worden. Es ist in Teilen überholt, wird kaum verwendet und ist nicht getestet. Ursprünglich sollte es in Python 3.6 entfernt werden, solche Entfernungen wurden aber bis nach dem Ende der Lebensdauer von Python 2.7 verschoben. Wer es noch verwendet, sollte die benötigten Klassen in den eigenen Code kopieren. (Beigetragen von Donghee Na und Terry J. Reedy in bpo-42299.)

  • Die Funktion PyModule_GetWarningsModule() ist entfernt. Sie war nutzlos geworden, weil das Modul _warnings in 2.6 in ein eingebautes Modul umgewandelt wurde. (Beigetragen von Hai Shi in bpo-42599.)

  • Die als veraltet markierten anderen Namen für die Collections Abstract Base Classes sind aus dem Modul collections entfernt. (Beigetragen von Victor Stinner in bpo-37324.)

  • Der Parameter loop ist nach der Abkündigung in Python 3.8 aus dem größten Teil der höheren API von asyncio entfernt. Für diese Änderung gibt es mehrere Gründe:

    1. Sie vereinfacht die höhere API.

    2. Die Funktionen der höheren API holen sich seit Python 3.7 stillschweigend die laufende Ereignisschleife des aktuellen Threads. In den meisten gewöhnlichen Anwendungsfällen muss die Ereignisschleife der API nicht übergeben werden.

    3. Eine Ereignisschleife zu übergeben ist fehleranfällig, besonders bei Schleifen, die in verschiedenen Threads laufen.

    Beachte, dass die tiefer liegende API loop weiterhin annimmt. Beispiele dafür, wie sich bestehender Code ersetzen lässt, stehen unter Änderungen in der Python API.

    (Beigetragen von Yurii Karabas, Andrew Svetlov, Yury Selivanov und Kyle Stanley in bpo-42392.)

Portierung auf Python 3.10

Dieser Abschnitt listet die bereits beschriebenen Änderungen und weitere Fehlerbehebungen auf, die Änderungen an deinem Code nötig machen können.

Änderungen an der Python-Syntax

  • Beim Kompilieren von bisher gültiger Syntax wird jetzt eine Warnung über eine Abkündigung ausgegeben, wenn unmittelbar auf das Zahlenliteral ein Schlüsselwort folgt (wie in 0in x). In künftigen Ausgaben wird daraus eine Syntaxwarnung und schließlich ein Syntaxfehler. Um die Warnung loszuwerden und den Code mit künftigen Ausgaben verträglich zu machen, setze einfach ein Leerzeichen zwischen das Zahlenliteral und das folgende Schlüsselwort. (Beigetragen von Serhiy Storchaka in bpo-43833.)

Änderungen in der Python API

  • Die Parameter etype der Funktionen format_exception(), format_exception_only() und print_exception() im Modul traceback sind in exc umbenannt. (Beigetragen von Zackery Spytz und Matthias Bussonnier in bpo-26389.)

  • atexit: Scheitert beim Beenden von Python eine mit atexit.register() angemeldete Rückruffunktion, wird ihre Ausnahme jetzt protokolliert. Vorher wurden nur manche Ausnahmen protokolliert, und die letzte Ausnahme wurde immer stillschweigend übergangen. (Beigetragen von Victor Stinner in bpo-42639.)

  • Der generische Typ collections.abc.Callable flacht Typparameter jetzt ab, ähnlich wie es typing.Callable derzeit tut. Das heißt, dass collections.abc.Callable[[int, str], str] jetzt __args__ von (int, str, str) hat. Vorher war es ([int, str], str). Code, der über typing.get_args() oder __args__ auf die Argumente zugreift, muss diese Änderung berücksichtigen. Außerdem kann für ungültige Formen der Parametrisierung von collections.abc.Callable ein TypeError ausgelöst werden, die in Python 3.9 vielleicht stillschweigend durchgingen. (Beigetragen von Ken Jin in bpo-42195.)

  • socket.htons() und socket.ntohs() lösen jetzt einen OverflowError statt einer DeprecationWarning aus, wenn der übergebene Parameter nicht in eine vorzeichenlose 16-Bit-Ganzzahl passt. (Beigetragen von Erlend E. Aasland in bpo-42393.)

  • Der Parameter loop ist nach der Abkündigung in Python 3.8 aus dem größten Teil der höheren API von asyncio entfernt.

    Eine Coroutine, die derzeit so aussieht:

    async def foo(loop):
        await asyncio.sleep(1, loop=loop)
    

    sollte dadurch ersetzt werden:

    async def foo():
        await asyncio.sleep(1)
    

    War foo() ausdrücklich darauf angelegt, nicht in der laufenden Ereignisschleife des aktuellen Threads zu laufen (etwa in der Ereignisschleife eines anderen Threads), ziehe stattdessen asyncio.run_coroutine_threadsafe() in Erwägung.

    (Beigetragen von Yurii Karabas, Andrew Svetlov, Yury Selivanov und Kyle Stanley in bpo-42392.)

  • Der Konstruktor types.FunctionType erbt jetzt die aktuellen eingebauten Symbole, wenn das Dictionary globals keinen Schlüssel "__builtins__" hat, statt {"None": None} als eingebaute Symbole zu verwenden – dasselbe Verhalten wie bei den Funktionen eval() und exec(). Eine Funktion in Python mit def function(...): ... zu definieren ist davon nicht betroffen. Globals lassen sich mit dieser Schreibweise nicht überschreiben, und auch sie erbt die aktuellen eingebauten Symbole. (Beigetragen von Victor Stinner in bpo-42990.)

Änderungen an der C-API

  • Die C-API-Funktionen PyParser_SimpleParseStringFlags, PyParser_SimpleParseStringFlagsFilename, PyParser_SimpleParseFileFlags und PyNode_Compile sowie der von diesen Funktionen verwendete Typ struct _node sind wegen des Wechsels auf den neuen PEG-Parser entfernt.

    Quelltext sollte jetzt unmittelbar zu einem Codeobjekt kompiliert werden, zum Beispiel mit Py_CompileString(). Das entstehende Codeobjekt lässt sich dann zum Beispiel mit PyEval_EvalCode() auswerten.

    Im Einzelnen:

    • Ein Aufruf von PyParser_SimpleParseStringFlags gefolgt von PyNode_Compile lässt sich durch einen Aufruf von Py_CompileString() ersetzen.

    • Für PyParser_SimpleParseFileFlags gibt es keinen unmittelbaren Ersatz. Um Code aus einem FILE *-Argument zu kompilieren, musst du die Datei in C lesen und den entstehenden Puffer an Py_CompileString() übergeben.

    • Um eine Datei anhand eines char *-Dateinamens zu kompilieren, öffne die Datei ausdrücklich, lies sie und kompiliere das Ergebnis. Ein Weg dazu führt über das Modul io mit PyImport_ImportModule(), PyObject_CallMethod(), PyBytes_AsString() und Py_CompileString(), wie unten skizziert. (Deklarationen und Fehlerbehandlung sind weggelassen.)

      io_module = Import_ImportModule("io");
      fileobject = PyObject_CallMethod(io_module, "open", "ss", filename, "rb");
      source_bytes_object = PyObject_CallMethod(fileobject, "read", "");
      result = PyObject_CallMethod(fileobject, "close", "");
      source_buf = PyBytes_AsString(source_bytes_object);
      code = Py_CompileString(source_buf, filename, Py_file_input);
      
    • Bei FrameObject-Objekten steht das Element f_lasti jetzt für einen Wordcode-Versatz und nicht mehr für einen einfachen Versatz in die Bytecode-Zeichenkette. Das heißt, dass diese Zahl mit 2 multipliziert werden muss, um sie mit APIs zu verwenden, die stattdessen einen Byte-Versatz erwarten (wie zum Beispiel PyCode_Addr2Line()). Beachte außerdem, dass das Element f_lasti von FrameObject-Objekten nicht als stabil gilt: verwende bitte stattdessen PyFrame_GetLineNumber().

CPython Bytecode Änderungen

  • Die Anweisung MAKE_FUNCTION nimmt als Annotationen der Funktion jetzt entweder ein Dictionary oder ein Tupel von Zeichenketten an. (Beigetragen von Yurii Karabas und Inada Naoki in bpo-42202.)

Build Änderungen

  • PEP 644: Python setzt jetzt OpenSSL 1.1.1 oder neuer voraus. OpenSSL 1.0.2 wird nicht mehr unterstützt. (Beigetragen von Christian Heimes in bpo-43669.)

  • Die C99-Funktionen snprintf() und vsnprintf() werden jetzt benötigt, um Python zu bauen. (Beigetragen von Victor Stinner in bpo-36020.)

  • sqlite3 setzt SQLite 3.7.15 oder höher voraus. (Beigetragen von Sergey Fedoseev und Erlend E. Aasland in bpo-40744 und bpo-40810.)

  • Das Modul atexit muss jetzt immer als eingebautes Modul gebaut werden. (Beigetragen von Victor Stinner in bpo-42639.)

  • Die Option --disable-test-modules ist im Skript configure hinzugekommen: Testmodule werden dann weder gebaut noch installiert. (Beigetragen von Xavier de Gaye, Thomas Petazzoni und Peixing Xin in bpo-27640.)

  • Die Option --with-wheel-pkg-dir=PFAD ist im Skript ./configure hinzugekommen. Ist sie angegeben, sucht das Modul ensurepip in diesem Verzeichnis nach den Wheel-Paketen setuptools und pip: sind beide vorhanden, werden diese Wheel-Pakete statt der mitgelieferten Wheel-Pakete von ensurepip verwendet.

    Die Paketierungsvorgaben einiger Linux-Distributionen raten davon ab, Abhängigkeiten mitzuliefern. Fedora installiert Wheel-Pakete zum Beispiel im Verzeichnis /usr/share/python-wheels/ und installiert das Paket ensurepip._bundled nicht.

    (Beigetragen von Victor Stinner in bpo-42856.)

  • Eine neue Option configure --without-static-libpython ist hinzugekommen, mit der die statische Bibliothek libpythonMAJOR.MINOR.a nicht gebaut und die Objektdatei python.o nicht installiert wird.

    (Beigetragen von Victor Stinner in bpo-43103.)

  • Das Skript configure verwendet jetzt, sofern verfügbar, das Werkzeug pkg-config, um den Ort der Tcl/Tk-Header und -Bibliotheken zu ermitteln. Wie bisher lassen sich diese Orte mit den Konfigurationsoptionen --with-tcltk-includes und --with-tcltk-libs ausdrücklich angeben. (Beigetragen von Manolis Stamatogiannakis in bpo-42603.)

  • Die Option --with-openssl-rpath ist im Skript configure hinzugekommen. Die Option vereinfacht es, Python mit einer eigenen OpenSSL-Installation zu bauen, zum Beispiel ./configure --with-openssl=/path/to/openssl --with-openssl-rpath=auto. (Beigetragen von Christian Heimes in bpo-43466.)

C API Änderungen

PEP 652: Die stabile ABI pflegen

Die stabile ABI (Application Binary Interface) für Erweiterungsmodule oder zum Einbetten von Python ist jetzt ausdrücklich festgelegt. C API and ABI Stability beschreibt die Stabilitätszusagen für C-API und ABI samt bewährten Vorgehensweisen für die Verwendung der stabilen ABI.

(Beigetragen von Petr Viktorin in PEP 652 und bpo-43795.)

Neue Funktionen

  • Das Ergebnis von PyNumber_Index() hat jetzt immer genau den Typ int. Vorher konnte das Ergebnis eine Instanz einer Unterklasse von int sein. (Beigetragen von Serhiy Storchaka in bpo-40792.)

  • Ein neues Element orig_argv ist in der Struktur PyConfig hinzugekommen: die Liste der ursprünglichen Befehlszeilenargumente, die der ausführbaren Python-Datei übergeben wurden. (Beigetragen von Victor Stinner in bpo-23427.)

  • Die Makros PyDateTime_DATE_GET_TZINFO() und PyDateTime_TIME_GET_TZINFO() sind hinzugekommen, um auf die tzinfo-Attribute von datetime.datetime- und datetime.time-Objekten zuzugreifen. (Beigetragen von Zackery Spytz in bpo-30155.)

  • Eine Funktion PyCodec_Unregister() ist hinzugekommen, um eine Suchfunktion für Codecs abzumelden. (Beigetragen von Hai Shi in bpo-41842.)

  • Die Funktion PyIter_Send() ist hinzugekommen, um einen Wert an einen Iterator senden zu können, ohne eine StopIteration-Ausnahme auszulösen. (Beigetragen von Vladimir Matveev in bpo-41756.)

  • PyUnicode_AsUTF8AndSize() ist in der eingeschränkten C-API hinzugekommen. (Beigetragen von Alex Gaynor in bpo-41784.)

  • Die Funktion PyModule_AddObjectRef() ist hinzugekommen: ähnlich wie PyModule_AddObject(), stiehlt im Erfolgsfall aber keine Referenz auf den Wert. (Beigetragen von Victor Stinner in bpo-1635741.)

  • Die Funktionen Py_NewRef() und Py_XNewRef() sind hinzugekommen. Sie erhöhen den Referenzzähler eines Objekts und geben das Objekt zurück. (Beigetragen von Victor Stinner in bpo-42262.)

  • Die Funktionen PyType_FromSpecWithBases() und PyType_FromModuleAndSpec() nehmen jetzt eine einzelne Klasse als Argument bases an. (Beigetragen von Serhiy Storchaka in bpo-42423.)

  • Die Funktion PyType_FromModuleAndSpec() nimmt jetzt einen tp_doc-Slot mit NULL an. (Beigetragen von Hai Shi in bpo-41832.)

  • Die Funktion PyType_GetSlot() kann statische Typen annehmen. (Beigetragen von Hai Shi und Petr Viktorin in bpo-41073.)

  • Eine neue Funktion PySet_CheckExact() ist in der C-API hinzugekommen, um zu prüfen, ob ein Objekt eine Instanz von set, aber keine Instanz eines Untertyps ist. (Beigetragen von Pablo Galindo in bpo-43277.)

  • PyErr_SetInterruptEx() ist hinzugekommen. Damit lässt sich eine Signalnummer übergeben, die nachgebildet werden soll. (Beigetragen von Antoine Pitrou in bpo-43356.)

  • Die eingeschränkte C-API wird jetzt auch unterstützt, wenn Python im Debug-Modus gebaut ist (wenn also das Makro Py_DEBUG definiert ist). In der eingeschränkten C-API sind die Funktionen Py_INCREF() und Py_DECREF() jetzt als undurchsichtige Funktionsaufrufe umgesetzt, statt unmittelbar auf das Element PyObject.ob_refcnt zuzugreifen, sofern Python im Debug-Modus gebaut ist und das Makro Py_LIMITED_API auf Python 3.10 oder neuer zielt. Die eingeschränkte C-API im Debug-Modus zu unterstützen wurde möglich, weil die Struktur PyObject seit Python 3.8 im Release- und im Debug-Modus dieselbe ist (siehe bpo-36465).

    Im besonderen Build mit --with-trace-refs (Makro Py_TRACE_REFS) wird die eingeschränkte C-API weiterhin nicht unterstützt. (Beigetragen von Victor Stinner in bpo-43688.)

  • Die Funktion Py_Is(x, y) ist hinzugekommen, um zu prüfen, ob das Objekt x dasselbe Objekt wie y ist, entsprechend x is y in Python. Hinzugekommen sind außerdem die Funktionen Py_IsNone(), Py_IsTrue() und Py_IsFalse(), um zu prüfen, ob ein Objekt das Singleton None, True beziehungsweise False ist. (Beigetragen von Victor Stinner in bpo-43753.)

  • Neue Funktionen sind hinzugekommen, um die Speicherbereinigung aus C-Code zu steuern: PyGC_Enable(), PyGC_Disable(), PyGC_IsEnabled(). Mit diesen Funktionen lässt sich die Speicherbereinigung aus C-Code heraus ein- und ausschalten und ihr Zustand abfragen, ohne das Modul gc importieren zu müssen.

  • Ein neuer Typschalter Py_TPFLAGS_DISALLOW_INSTANTIATION ist hinzugekommen, um das Erzeugen von Instanzen eines Typs zu verbieten. (Beigetragen von Victor Stinner in bpo-43916.)

  • Ein neuer Typschalter Py_TPFLAGS_IMMUTABLETYPE ist hinzugekommen, um unveränderliche Typobjekte zu erzeugen: Typattribute lassen sich dann weder setzen noch löschen. (Beigetragen von Victor Stinner und Erlend E. Aasland in bpo-43908.)

Portierung auf Python 3.10

  • Das Makro PY_SSIZE_T_CLEAN muss jetzt definiert sein, um Formate von PyArg_ParseTuple() und Py_BuildValue() zu verwenden, die # enthalten: es#, et#, s#, u#, y#, z#, U# und Z#. Siehe Argumente auswerten und Werte bilden und PEP 353. (Beigetragen von Victor Stinner in bpo-40943.)

  • Da Py_REFCNT() in eine statische Inline-Funktion umgewandelt ist, muss Py_REFCNT(obj) = new_refcnt durch Py_SET_REFCNT(obj, new_refcnt) ersetzt werden: siehe Py_SET_REFCNT() (verfügbar seit Python 3.9). Aus Gründen der Rückwärtsverträglichkeit lässt sich dieses Makro verwenden:

    #if PY_VERSION_HEX < 0x030900A4
    #  define Py_SET_REFCNT(obj, refcnt) ((Py_REFCNT(obj) = (refcnt)), (void)0)
    #endif
    

    (Beigetragen von Victor Stinner in bpo-39573.)

  • PyDict_GetItem() ohne gehaltenen GIL aufzurufen war aus historischen Gründen erlaubt. Das ist es jetzt nicht mehr. (Beigetragen von Victor Stinner in bpo-40839.)

  • PyUnicode_FromUnicode(NULL, size) und PyUnicode_FromStringAndSize(NULL, size) löst jetzt eine DeprecationWarning aus. Verwende PyUnicode_New(), um ein Unicode-Objekt ohne Anfangsdaten anzulegen. (Beigetragen von Inada Naoki in bpo-36346.)

  • Die private Struktur _PyUnicode_Name_CAPI der PyCapsule-API unicodedata.ucnhash_CAPI ist in die interne C-API umgezogen. (Beigetragen von Victor Stinner in bpo-42157.)

  • Die Funktionen Py_GetPath(), Py_GetPrefix(), Py_GetExecPrefix(), Py_GetProgramFullPath(), Py_GetPythonHome() und Py_GetProgramName() geben jetzt NULL zurück, wenn sie vor Py_Initialize() aufgerufen werden (also bevor Python initialisiert ist). Verwende die neue Python Initialization Configuration-API, um die Python Path Configuration zu erhalten. (Beigetragen von Victor Stinner in bpo-42260.)

  • Die Makros PyList_SET_ITEM(), PyTuple_SET_ITEM() und PyCell_SET() lassen sich nicht mehr als L-Wert oder R-Wert verwenden. x = PyList_SET_ITEM(a, b, c) und PyList_SET_ITEM(a, b, c) = x scheitern zum Beispiel jetzt mit einem Compiler-Fehler. Das verhindert Fehler wie die Prüfung if (PyList_SET_ITEM (a, b, c) < 0) .... (Beigetragen von Zackery Spytz und Victor Stinner in bpo-30459.)

  • Die Dateien odictobject.h, parser_interface.h, picklebufobject.h, pyarena.h, pyctype.h, pydebug.h, pyfpe.h und pytime.h der nicht eingeschränkten API sind in das Verzeichnis Include/cpython umgezogen. Diese Dateien dürfen nicht unmittelbar eingebunden werden, denn sie sind schon in Python.h enthalten, siehe Include Files. Wurden sie unmittelbar eingebunden, binde besser stattdessen Python.h ein. (Beigetragen von Nicholas Sim in bpo-35134.)

  • Verwende den Typschalter Py_TPFLAGS_IMMUTABLETYPE, um unveränderliche Typobjekte zu erzeugen. Verlasse dich nicht auf Py_TPFLAGS_HEAPTYPE, um zu entscheiden, ob ein Typobjekt veränderlich ist. Prüfe stattdessen, ob Py_TPFLAGS_IMMUTABLETYPE gesetzt ist. (Beigetragen von Victor Stinner und Erlend E. Aasland in bpo-43908.)

  • Die nicht dokumentierte Funktion Py_FrozenMain ist aus der eingeschränkten API entfernt. Die Funktion ist vor allem für eigene Builds von Python nützlich. (Beigetragen von Petr Viktorin in bpo-26241.)

Als veraltet markiert

  • Die Funktion PyUnicode_InternImmortal() ist jetzt als veraltet markiert und wird in Python 3.12 entfernt: verwende stattdessen PyUnicode_InternInPlace(). (Beigetragen von Victor Stinner in bpo-41692.)

Entfernt

  • Die Py_UNICODE_str*-Funktionen zur Bearbeitung von Py_UNICODE*-Zeichenketten sind entfernt. (Beigetragen von Inada Naoki in bpo-41123.)

  • PyUnicode_GetMax() ist entfernt. Steige bitte auf die neuen APIs (PEP 393) um. (Beigetragen von Inada Naoki in bpo-41103.)

  • PyLong_FromUnicode() ist entfernt. Steige bitte auf PyLong_FromUnicodeObject() um. (Beigetragen von Inada Naoki in bpo-41103.)

  • PyUnicode_AsUnicodeCopy() ist entfernt. Verwende bitte PyUnicode_AsUCS4Copy() oder PyUnicode_AsWideCharString(). (Beigetragen von Inada Naoki in bpo-41103.)

  • Die Variable _Py_CheckRecursionLimit ist entfernt: sie ist durch ceval.recursion_limit der Struktur PyInterpreterState ersetzt. (Beigetragen von Victor Stinner in bpo-41834.)

  • Die nicht dokumentierten Makros Py_ALLOW_RECURSION und Py_END_ALLOW_RECURSION sowie das Feld recursion_critical der Struktur PyInterpreterState sind entfernt. (Beigetragen von Serhiy Storchaka in bpo-41936.)

  • Die nicht dokumentierte Funktion PyOS_InitInterrupts() ist entfernt. Python zu initialisieren richtet schon stillschweigend Signalbehandler ein: siehe PyConfig.install_signal_handlers. (Beigetragen von Victor Stinner in bpo-41713.)

  • Die Funktion PyAST_Validate() ist entfernt. Es ist nicht mehr möglich, mit der öffentlichen C-API ein AST-Objekt (Typ mod_ty) zu erzeugen. Die Funktion war aus der eingeschränkten C-API schon ausgenommen (PEP 384). (Beigetragen von Victor Stinner in bpo-43244.)

  • Die Header-Datei symtable.h und die nicht dokumentierten Funktionen sind entfernt:

    • PyST_GetScope()

    • PySymtable_Build()

    • PySymtable_BuildObject()

    • PySymtable_Free()

    • Py_SymtableString()

    • Py_SymtableStringObject()

    Die Funktion Py_SymtableString() gehörte versehentlich zur stabilen ABI, ließ sich aber nicht verwenden, weil die Header-Datei symtable.h aus der eingeschränkten C-API ausgenommen war.

    Verwende stattdessen das Python-Modul symtable. (Beigetragen von Victor Stinner in bpo-43244.)

  • PyOS_ReadlineFunctionPointer() ist aus den Header-Dateien der eingeschränkten C-API und aus python3.dll entfernt, der Bibliothek, die unter Windows die stabile ABI bereitstellt. Da die Funktion ein FILE*-Argument nimmt, lässt sich die Stabilität ihrer ABI nicht gewährleisten. (Beigetragen von Petr Viktorin in bpo-43868.)

  • Die Header-Dateien ast.h, asdl.h und Python-ast.h sind entfernt. Diese Funktionen waren nicht dokumentiert und aus der eingeschränkten C-API ausgenommen. Die meisten Namen, die diese Header-Dateien definierten, hatten kein Py als Präfix und konnten so zu Namenskonflikten führen. Python-ast.h definierte zum Beispiel ein Makro Yield, das mit dem Namen Yield aus der Windows-Header-Datei <winbase.h> kollidierte. Verwende stattdessen das Python-Modul ast. (Beigetragen von Victor Stinner in bpo-43244.)

  • Die Compiler- und Parser-Funktionen, die den Typ struct _mod verwenden, sind entfernt, denn die öffentliche AST-C-API ist entfallen:

    • PyAST_Compile()

    • PyAST_CompileEx()

    • PyAST_CompileObject()

    • PyFuture_FromAST()

    • PyFuture_FromASTObject()

    • PyParser_ASTFromFile()

    • PyParser_ASTFromFileObject()

    • PyParser_ASTFromFilename()

    • PyParser_ASTFromString()

    • PyParser_ASTFromStringObject()

    Diese Funktionen waren nicht dokumentiert und aus der eingeschränkten C-API ausgenommen. (Beigetragen von Victor Stinner in bpo-43244.)

  • Die Header-Datei pyarena.h mit den folgenden Funktionen ist entfernt:

    • PyArena_New()

    • PyArena_Free()

    • PyArena_Malloc()

    • PyArena_AddPyObject()

    Diese Funktionen waren nicht dokumentiert, aus der eingeschränkten C-API ausgenommen und wurden nur intern vom Compiler verwendet. (Beigetragen von Victor Stinner in bpo-43244.)

  • Das Element PyThreadState.use_tracing ist entfernt, um Python zu optimieren. (Beigetragen von Mark Shannon in bpo-43760.)

Erwähnenswertes Sicherheitsfeature in 3.10.7

Die Umwandlung zwischen int und str in anderen Basen als 2 (binär), 4, 8 (oktal), 16 (hexadezimal) oder 32 – etwa in Basis 10 (dezimal) – löst jetzt einen ValueError aus, wenn die Anzahl der Stellen in Zeichenkettenform über einer Grenze liegt. Damit sollen mögliche Denial-of-Service-Angriffe wegen der algorithmischen Komplexität verhindert werden. Das ist eine Gegenmaßnahme zu CVE 2020-10735. Diese Grenze lässt sich über eine Umgebungsvariable, einen Befehlszeilenschalter oder APIs aus sys einstellen oder abschalten. Siehe die Dokumentation zur Längenbegrenzung bei der Umwandlung zwischen Ganzzahl und Zeichenkette. Die voreingestellte Grenze liegt bei 4300 Stellen in Zeichenkettenform.

Erwähnenswertes Sicherheitsfeature in 3.10.8

Das als veraltet markierte Modul mailcap lehnt es jetzt ab, unsicheren Text (Dateinamen, MIME-Typen, Parameter) in Shell-Befehle einzusetzen. Statt solchen Text zu verwenden, warnt es und verhält sich, als wäre keine Übereinstimmung gefunden worden (beziehungsweise bei Testbefehlen, als wäre der Test fehlgeschlagen). (Beigetragen von Petr Viktorin in gh-98966.)

Erwähnenswerte Änderungen in 3.10.12

tarfile

  • Die Methoden zum Entpacken in tarfile und shutil.unpack_archive() haben ein neues Argument filter, mit dem sich tar-Features einschränken lassen, die überraschend oder gefährlich sein können, etwa Dateien außerhalb des Zielverzeichnisses anzulegen. Einzelheiten unter Extraction filters. In Python 3.12 zeigt die Verwendung ohne das Argument filter eine DeprecationWarning. In Python 3.14 wird die Voreinstellung auf 'data' umgestellt. (Beigetragen von Petr Viktorin in PEP 706.)