TypeVar, geneeriset luokat ja Protocol
Määrittäkää uudelleenkäytettäviä geneerisiä tyyppejä ja rakenteellista alityypitystä Protocolin avulla.
TypeVar, geneeriset luokat ja Protocol on ilmainen Python Academy-oppitunti CoddyKitissä. Tämä on oppitunti 3/4. Voit lukea koko oppitunnin alta ilmaiseksi ja harjoitella sen jälkeen käytännössä selaimessa sisäänrakennetulla koodieditorilla ja ympäri vuorokauden käytettävissä olevan tekoälytuutorin avulla. Oppitunti kuuluu Python Academy-oppimispolkuun, ja edistymisesi synkronoituu verkon ja CoddyKit-sovelluksen välillä. Python Academy-kurssilla on yhteensä 4 oppituntia.
Mikä on TypeVar
TypeVar määrittää tyyppimuuttujan eli paikanhaltijan, joka voi olla mikä tahansa tyyppi ja jota voidaan tarvittaessa rajoittaa. Sitä käytetään geneerisissä funktioissa ja luokissa.
from typing import TypeVar
T = TypeVar("T")
def identity(value: T) -> T:
return value
print(identity(42)) # int
print(identity("hello")) # strGeneeriset funktiot
Kun funktio käyttää TypeVar-muuttujaa sekä parametri- että paluutyypeissä, mypy voi päätellä paluutyypin argumentin tyypin perusteella.
from typing import TypeVar
T = TypeVar("T")
def first(items: list[T]) -> T:
return items[0]
x: int = first([1, 2, 3]) # mypy knows x is int
s: str = first(["a","b","c"]) # mypy knows s is strRajoitettu TypeVar
Välittäkää tyyppirajoitteet TypeVar-kutsulle rajoittaaksenne hyväksyttäviä tyyppejä.
from typing import TypeVar
Numeric = TypeVar("Numeric", int, float)
def double(n: Numeric) -> Numeric:
return n * 2
print(double(5)) # 10
print(double(2.5)) # 5.0
# double("x") # mypy errorGeneeriset luokat
Perikää luokka Generic[T]-luokasta luodaksenne tyyppimuuttujalla parametrisoidun luokan.
from typing import Generic, TypeVar
T = TypeVar("T")
class Stack(Generic[T]):
def __init__(self) -> None:
self._items: list[T] = []
def push(self, item: T) -> None:
self._items.append(item)
def pop(self) -> T:
return self._items.pop()
stack: Stack[int] = Stack()
stack.push(1)
print(stack.pop()) # 1Useita TypeVar-muuttujia
Käyttäkää useita TypeVar-muuttujia parametrisoidaksenne luokan tai funktion kahdella toisistaan riippumattomalla tyypillä.
from typing import Generic, TypeVar
K = TypeVar("K")
V = TypeVar("V")
class Pair(Generic[K, V]):
def __init__(self, key: K, value: V) -> None:
self.key = key
self.value = value
p: Pair[str, int] = Pair("age", 30)
print(p.key, p.value) # age 30Protocol — rakenteellinen alityypitys
Protocol määrittää rajapinnan luokan edellyttämien metodien ja attribuuttien avulla ilman nimenomaista perintää ("duck typing", tyyppitarkistettu).
from typing import Protocol
class Drawable(Protocol):
def draw(self) -> None: ...
def render(obj: Drawable) -> None:
obj.draw()
class Circle:
def draw(self) -> None:
print("Drawing circle")
render(Circle()) # works — Circle satisfies DrawableProtocol ja runtime_checkable
Lisätkää @runtime_checkable Protocol-määrittelyyn, jotta isinstance()-tarkistukset voidaan tehdä ajonaikaisesti.
from typing import Protocol, runtime_checkable
@runtime_checkable
class Closeable(Protocol):
def close(self) -> None: ...
class File:
def close(self) -> None: print("closed")
print(isinstance(File(), Closeable)) # TrueProtocol ja ABC
ABC:t edellyttävät nimenomaista perintää (class Dog(Animal)). Protokollat toimivat rakenteellisen yhteensopivuuden perusteella: jos luokalla on oikeat metodit, se täyttää protokollan perinnästä riippumatta.
from typing import Protocol
from abc import ABC, abstractmethod
# ABC: nominal typing
class Printable(ABC):
@abstractmethod
def display(self) -> None: ...
# Protocol: structural typing
class Displayable(Protocol):
def display(self) -> None: ...TypeVar ja bound
TypeVar("T", bound=BaseClass) rajoittaa T:n BaseClass-luokkaan tai mihin tahansa sen aliluokkaan.
from typing import TypeVar
class Animal:
def speak(self) -> str: return "..."
A = TypeVar("A", bound=Animal)
def make_speak(animal: A) -> str:
return animal.speak()Geneerinen alias — Python 3.12
Python 3.12 esittelee type-lauseen selkeiden tyyppialiasten määrittämiseen sekä geneerisen syntaksin class Foo[T] ilman TypeVar-muuttujan tuontia.
# Python 3.12+
type Vector = list[float]
type Matrix = list[Vector]
class Stack[T]:
def __init__(self) -> None: self._items: list[T] = []
def push(self, item: T) -> None: self._items.append(item)
def pop(self) -> T: return self._items.pop()Self-tyyppi
Self (typing-moduulista versiosta 3.11 alkaen) merkitsee nykyisen luokan palauttavat metodit, mikä on hyödyllistä sujuvissa rajapinnoissa ja aliluokissa.
from typing import Self
class Builder:
def __init__(self) -> None:
self.parts: list[str] = []
def add(self, part: str) -> Self:
self.parts.append(part)
return self
b = Builder().add("a").add("b")
print(b.parts) # ["a", "b"]Pikatarkistus
Mikä on Protocolin ja ABC:n keskeinen ero Pythonin tyypityksessä?
Kertaus
TypeVar luo tyyppipaikanhaltijoita geneerisille funktioille ja luokille. Generic[T] parametrisoi luokkia. Protocol mahdollistaa rakenteellisen alityypityksen ilman perintää. Käyttäkää bound=-rajoitetta tai tyyppirajoitteita TypeVar-muuttujissa hyväksyttävien tyyppien rajaamiseen.
Opi Python tekoälytuutorin avulla — ilmaiseksi
Kirjoita ja suorita oikeaa koodia selaimessa, saa välitöntä apua tekoälytuutorilta ympäri vuorokauden ja jatka siitä, mihin jäit, verkossa tai sovelluksessa.
- Kurssit
- 76
- Oppitunnit
- 320
Usein kysytyt kysymykset
Onko oppitunti ”TypeVar, geneeriset luokat ja Protocol” ilmainen?
Kyllä – oppitunnin ”TypeVar, geneeriset luokat ja Protocol” koko tekstin voi lukea täällä verkossa ilmaiseksi. Jos haluat harjoitella interaktiivisesti sisäänrakennetulla koodieditorilla ja ympäri vuorokauden käytettävissä olevan tekoälytuutorin avulla sekä avata koko Python Academy-kurssin, päivitä CoddyKit PROhon. Python Academy-kurssilla on yhteensä 4 oppituntia.
Mitä opin oppitunnilla ”TypeVar, geneeriset luokat ja Protocol”?
Määrittäkää uudelleenkäytettäviä geneerisiä tyyppejä ja rakenteellista alityypitystä Protocolin avulla. Harjoittelet Python Academy-aihetta koodilla, jonka suoritat suoraan selaimessa. Ympäri vuorokauden käytettävissä oleva tekoälytuutori vastaa kysymyksiisi oppitunnin aikana.
Tarvitsenko kokemusta aloittaakseni Python Academy-opiskelun?
Aiempi kokemus ei ole tarpeen. CoddyKitin Python Academy-oppimispolku sopii vasta-alkajista edistyneisiin, joten voit aloittaa tästä tai alusta ja edetä omaan tahtiisi. Tämä on oppitunti 3/4.
Kuinka kauan ”TypeVar, geneeriset luokat ja Protocol”-oppitunnin suorittaminen kestää?
Useimmat CoddyKitin oppitunnit kestävät noin 5–10 minuuttia. Jokainen oppitunti on lyhyt ja interaktiivinen, joten edistyt tasaisesti ja voit jatkaa siitä, mihin jäit – sekä verkossa että sovelluksessa.
Voinko kirjoittaa ja suorittaa koodia tällä Python Academy-oppitunnilla?
Kyllä. Jokainen Python Academy-oppitunti sisältää sisäänrakennetun koodieditorin, joten voit kirjoittaa ja suorittaa oikeaa koodia suoraan selaimessa ja saada välitöntä palautetta tekoälyltä – paikallista asennusta ei tarvita.
Kaikki tämän kurssin oppitunnit
- Tyyppimerkintöjen perusteet
- Monimutkaiset tyypit: List, Dict, Optional, Union
- TypeVar, geneeriset luokat ja Protocol
- mypyn suorittaminen ja tyyppivirheiden korjaaminen