python使用泛型

2022-09-21 15:06:13 字數 3269 閱讀 8227

所謂的泛型, 就是將資料型別作為引數進行傳遞, 即在我們用的時候確定資料型別, 這是一種在物件導向語言中經常使用的特性

以sqlalchemy舉例

比如: 我們統一寫個將資料儲存到資料庫的介面, 只有將資料庫鏈結表物件資料傳入即可, 返回的是表物件的例項, 為了讓ide可以識別返回物件, 我們可以使用泛型

這裡需要用到:

typingtypevartype

typevar是型別變數, 主要用於泛型型別與泛型函式定義的引數, 第乙個引數是名稱,bound引數用於規定該型別為bound值的子類

type[c]的形式為協變數, 表明c的所有子類都應使用c相同的 構造器簽名 及 類方法簽名, 假如我們需要返回泛型型別的話, 需要用到

更多使用方法, 見: typing使用

使用了pydantic規範要建立資料的型別

關於pydantic的一般使用, 見: pydantic使用

from typing import typevar, type

from sqlalchemy.orm import session

from pydantic import basemodel

from orm.models import category

from orm.schemas import writecategorymodel

# 定義型別

modelt = typevar("modelt")

datat = typevar("datat", bound=basemodel) # bound表明該類為basemodel的子類

"""為節省空間, 表結構和模型不展示

"""def create_category(session: session, data: writecategorymodel) -> type[category]:

cate_obj = s**e_one_to_db(session=session, model_class=category, data=data)

return cate_obj

def s**e_one_to_db(session: session, model_class: modelt, data: datat) -> modelt:

"""儲存一條到資料庫

:param session: sqlalchemy session

:param model_class: sqlalchemy模型類

:param data: pydantic模型物件

:return: 對應sqlalchemy模型類的物件

"""try:

obj = model_class(**data.dict())

session.add(obj)

session.commit()

# 手動將 資料 重新整理到資料庫

session.refresh(obj)

return obj

except exception as e:

# 別忘記發生錯誤時回滾

session.rollback()

raise e

在使用pydantic時, 亦可以使用泛型

比如: 在fastapi中返回統一返回格式為:

我們的data可能是列表或物件, 而且對應的pydantic模型也不一樣, 這時我們就可以使用泛型了

router = apirouter(prefix="/test", tags=["測試泛型"])

# 為了方便, 在這裡定義pydantic模型

datat = typevar("datat")

class genericresponse(genericmodel, generic[datat]):

"""通用返回資料

"""status: bool

msg: str

data: optional[datat] = none # 可能連data都沒有

# 設定response_model_exclude_unset=true即可

class bookmodel(basemodel):

id: int

name: str

# 偽資料

fake_book_data = [,,

,,,]@router.get("/books", response_model=genericresponse[list[bookmodel]])

def get_books():

return

@router.get("/books/", response_model=genericresponse[bookmodel])

def retrieve_book(bid: int):

for item in fake_book_data:

if item.get("id") == bid:

return

# 不存在

raise httpexception(status_code=status.http_404_not_found, detail="該書不存在")

訪問/docs頁面, 成功通過測試

C 泛型 使用泛型List

一 泛型的優點 效能高。從前面的例子可以看出使用不需進行型別轉換,可以避免裝箱和拆箱操作,提高效能。型別安全。泛型集合對其儲存物件進行了型別約束,不是定義時宣告的型別,是無法儲存到泛型集合中的,保證了資料型別的安全。重用。使用泛型型別可以最大限度地重用 保護型別的安全以及提高效能。使用泛型 使用泛型...

C 泛型 使用泛型List

一 泛型的優點 效能高。從前面的例子可以看出使用不需進行型別轉換,可以避免裝箱和拆箱操作,提高效能。型別安全。泛型集合對其儲存物件進行了型別約束,不是定義時宣告的型別,是無法儲存到泛型集合中的,保證了資料型別的安全。重用。使用泛型型別可以最大限度地重用 保護型別的安全以及提高效能。使用泛型 使用泛型...

泛型結構使用大全(泛型類 泛型介面)

1 泛型類可能有多個引數,此時應將多個引數一起放到尖括號內,比如 2 泛型類的構造器如下 public genericclass 錯誤示例 public genericclass 3 例項化後,操作原來泛型位置的結構必須與指定的泛型型別一致。4 泛型不同的引用不能互相賦值。儘管在編譯時arrayli...