字典物件

type PyDictObject

PyObject 子型別表示一個 Python 字典物件。

PyTypeObject PyDict_Type
作為 穩定 ABI 的一部分。

PyTypeObject 例項表示 Python 字典型別。這與 Python 層中的 dict 物件相同。

int PyDict_Check(PyObject *p)

如果 p 是一個字典物件或是字典型別子類的例項,則返回 true。此函式始終成功。

int PyDict_CheckExact(PyObject *p)

如果 p 是一個字典物件,但不是字典型別子類的例項,則返回 true。此函式始終成功。

PyObject *PyDict_New()
返回值: 新引用。 穩定ABI 的一部分。

返回一個新的空字典,如果失敗則返回 NULL

PyObject *PyDictProxy_New(PyObject *mapping)
返回值: 新引用。 穩定ABI 的一部分。

返回一個 types.MappingProxyType 物件,用於強制執行只讀行為的對映。這通常用於建立一個檢視,以防止對非動態類型別的字典進行修改。

void PyDict_Clear(PyObject *p)
作為 穩定 ABI 的一部分。

清空現有字典中的所有鍵值對。

int PyDict_Contains(PyObject *p, PyObject *key)
作為 穩定 ABI 的一部分。

確定字典 p 是否包含 key。如果 p 中的某個項與 key 匹配,則返回 1,否則返回 0。發生錯誤時,返回 -1。這等價於 Python 表示式 key in p

int PyDict_ContainsString(PyObject *p, const char *key)

這與 PyDict_Contains() 相同,但 key 被指定為 const char* UTF-8 編碼的位元組字串,而不是 PyObject*

在 3.13 版本加入。

PyObject *PyDict_Copy(PyObject *p)
返回值: 新引用。 穩定ABI 的一部分。

返回一個新字典,其中包含與 p 相同的鍵值對。

int PyDict_SetItem(PyObject *p, PyObject *key, PyObject *val)
作為 穩定 ABI 的一部分。

使用 key 作為鍵將 val 插入到字典 p 中。key 必須是可雜湊的;如果不是,將引發 TypeError。成功時返回 0,失敗時返回 -1。此函式 不會 竊取對 val 的引用。

int PyDict_SetItemString(PyObject *p, const char *key, PyObject *val)
作為 穩定 ABI 的一部分。

這與 PyDict_SetItem() 相同,但 key 被指定為 const char* UTF-8 編碼的位元組字串,而不是 PyObject*

int PyDict_DelItem(PyObject *p, PyObject *key)
作為 穩定 ABI 的一部分。

從字典 p 中刪除鍵為 key 的條目。key 必須是可雜湊的;如果不是,將引發 TypeError。如果字典中不存在 key,將引發 KeyError。成功時返回 0,失敗時返回 -1

int PyDict_DelItemString(PyObject *p, const char *key)
作為 穩定 ABI 的一部分。

這與 PyDict_DelItem() 相同,但 key 被指定為 const char* UTF-8 編碼的位元組字串,而不是 PyObject*

int PyDict_GetItemRef(PyObject *p, PyObject *key, PyObject **result)
自 3.13 版本起成為 穩定 ABI 的一部分。

返回對字典 p 中鍵為 key 的物件的新的強引用

  • 如果鍵存在,則將 *result 設定為對該值的新強引用並返回 1

  • 如果鍵缺失,則將 *result 設定為 NULL 並返回 0

  • 如果發生錯誤,則引發異常並返回 -1

在 3.13 版本加入。

另請參見 PyObject_GetItem() 函式。

PyObject *PyDict_GetItem(PyObject *p, PyObject *key)
返回值: 借用引用。 穩定ABI 的一部分。

返回對字典 p 中鍵為 key 的物件的借用引用。如果鍵 key 缺失,則返回 NULL設定異常。

備註

此函式在呼叫 __hash__()__eq__() 方法時發生的異常會被靜默忽略。建議改用 PyDict_GetItemWithError() 函式。

3.10 版中已更改: 出於歷史原因,此前允許在沒有附加執行緒狀態的情況下呼叫此 API。現在不再允許。

PyObject *PyDict_GetItemWithError(PyObject *p, PyObject *key)
返回值: 借用引用。 穩定ABI 的一部分。

PyDict_GetItem() 的變體,不抑制異常。如果發生異常,返回 NULL 設定異常。如果鍵不存在,返回 NULL 而不設定異常。

PyObject *PyDict_GetItemString(PyObject *p, const char *key)
返回值: 借用引用。 穩定ABI 的一部分。

這與 PyDict_GetItem() 相同,但 key 被指定為 const char* UTF-8 編碼的位元組字串,而不是 PyObject*

備註

此函式在呼叫 __hash__()__eq__() 方法或建立臨時 str 物件時發生的異常會被靜默忽略。建議改用 PyDict_GetItemWithError() 函式並使用您自己的 PyUnicode_FromString() key

int PyDict_GetItemStringRef(PyObject *p, const char *key, PyObject **result)
自 3.13 版本起成為 穩定 ABI 的一部分。

類似於 PyDict_GetItemRef(),但 key 被指定為 const char* UTF-8 編碼的位元組字串,而不是 PyObject*

在 3.13 版本加入。

PyObject *PyDict_SetDefault(PyObject *p, PyObject *key, PyObject *defaultobj)
返回值:借用引用。

這與 Python 級別的 dict.setdefault() 相同。如果存在,它返回字典 p 中與 key 對應的值。如果鍵不在字典中,則使用 defaultobj 插入該鍵,並返回 defaultobj。此函式只評估 key 的雜湊函式一次,而不是對查詢和插入分別評估。

在 3.4 版本加入。

int PyDict_SetDefaultRef(PyObject *p, PyObject *key, PyObject *default_value, PyObject **result)

如果鍵尚未在字典中,則將 default_value 插入到字典 p 中,鍵為 key。如果 result 不為 NULL,則將 *result 設定為對 default_value (如果鍵不存在)或現有值(如果 key 已存在於字典中)的強引用。如果鍵存在且未插入 default_value,則返回 1;如果鍵不存在且已插入 default_value,則返回 0。失敗時,返回 -1,設定異常,並將 *result 設定為 NULL

為了清楚起見:如果您在呼叫此函式之前持有對 default_value 的強引用,則在函式返回後,您將持有對 default_value*result (如果它不為 NULL)的強引用。它們可能指向同一個物件:在這種情況下,您持有對它的兩個獨立引用。

在 3.13 版本加入。

int PyDict_Pop(PyObject *p, PyObject *key, PyObject **result)

從字典 p 中移除 key,並可選擇返回移除的值。如果鍵缺失,則不引發 KeyError

  • 如果鍵存在,如果 result 不為 NULL,則將 *result 設定為對移除值的新引用,並返回 1

  • 如果鍵缺失,如果 result 不為 NULL,則將 *result 設定為 NULL,並返回 0

  • 如果發生錯誤,則引發異常並返回 -1

類似於 dict.pop(),但沒有預設值,並且如果鍵缺失,則不引發 KeyError

在 3.13 版本加入。

int PyDict_PopString(PyObject *p, const char *key, PyObject **result)

類似於 PyDict_Pop(),但 key 被指定為 const char* UTF-8 編碼的位元組字串,而不是 PyObject*

在 3.13 版本加入。

PyObject *PyDict_Items(PyObject *p)
返回值: 新引用。 穩定ABI 的一部分。

返回一個包含字典中所有項的 PyListObject

PyObject *PyDict_Keys(PyObject *p)
返回值: 新引用。 穩定ABI 的一部分。

返回一個包含字典中所有鍵的 PyListObject

PyObject *PyDict_Values(PyObject *p)
返回值: 新引用。 穩定ABI 的一部分。

返回一個包含字典 p 中所有值的 PyListObject

Py_ssize_t PyDict_Size(PyObject *p)
作為 穩定 ABI 的一部分。

返回字典中的項數。這等價於對字典執行 len(p)

int PyDict_Next(PyObject *p, Py_ssize_t *ppos, PyObject **pkey, PyObject **pvalue)
作為 穩定 ABI 的一部分。

迭代字典 p 中的所有鍵值對。ppos 所指的 Py_ssize_t 在首次呼叫此函式開始迭代之前必須初始化為 0;函式對字典中的每個對返回 true,一旦所有對都被報告,則返回 false。引數 pkeypvalue 應該指向 PyObject* 變數,它們將分別填充每個鍵和值,或者可以是 NULL。透過它們返回的任何引用都是借用引用。ppos 在迭代期間不應更改。其值表示內部字典結構中的偏移量,並且由於結構是稀疏的,因此偏移量不是連續的。

例如:

PyObject *key, *value;
Py_ssize_t pos = 0;

while (PyDict_Next(self->dict, &pos, &key, &value)) {
    /* do something interesting with the values... */
    ...
}

字典 p 在迭代期間不應被修改。在迭代字典時修改鍵的值是安全的,但前提是鍵集沒有改變。例如

PyObject *key, *value;
Py_ssize_t pos = 0;

while (PyDict_Next(self->dict, &pos, &key, &value)) {
    long i = PyLong_AsLong(value);
    if (i == -1 && PyErr_Occurred()) {
        return -1;
    }
    PyObject *o = PyLong_FromLong(i + 1);
    if (o == NULL)
        return -1;
    if (PyDict_SetItem(self->dict, key, o) < 0) {
        Py_DECREF(o);
        return -1;
    }
    Py_DECREF(o);
}

自由執行緒構建中,此函式在沒有外部同步的情況下不是執行緒安全的。您可以使用 Py_BEGIN_CRITICAL_SECTION 在迭代字典時鎖定它。

Py_BEGIN_CRITICAL_SECTION(self->dict);
while (PyDict_Next(self->dict, &pos, &key, &value)) {
    ...
}
Py_END_CRITICAL_SECTION();

備註

在自由執行緒構建中,此函式可以在臨界區內安全使用。但是,為 pkeypvalue 返回的引用是借用引用,僅在持有臨界區時有效。如果您需要在臨界區外或臨界區可能被掛起時使用這些物件,請建立強引用(例如,使用 Py_NewRef())。

int PyDict_Merge(PyObject *a, PyObject *b, int override)
作為 穩定 ABI 的一部分。

迭代對映物件 b,將鍵值對新增到字典 a 中。b 可以是字典,也可以是任何支援 PyMapping_Keys()PyObject_GetItem() 的物件。如果 override 為 true,則如果 b 中找到匹配的鍵,則替換 a 中的現有對,否則只有當 a 中沒有匹配的鍵時才新增對。成功時返回 0,如果引發異常則返回 -1

int PyDict_Update(PyObject *a, PyObject *b)
作為 穩定 ABI 的一部分。

這與 C 中的 PyDict_Merge(a, b, 1) 相同,並且類似於 Python 中的 a.update(b),不同之處在於,如果第二個引數沒有“keys”屬性,PyDict_Update() 不會退回到迭代鍵值對序列。成功時返回 0,如果引發異常則返回 -1

int PyDict_MergeFromSeq2(PyObject *a, PyObject *seq2, int override)
作為 穩定 ABI 的一部分。

seq2 中的鍵值對更新或合併到字典 a 中。seq2 必須是一個可迭代物件,產生長度為 2 的可迭代物件,並將其視為鍵值對。如果存在重複鍵,如果 override 為 true,則最後一個獲勝,否則第一個獲勝。成功時返回 0,如果引發異常則返回 -1。等價的 Python 程式碼(除了返回值)

def PyDict_MergeFromSeq2(a, seq2, override):
    for key, value in seq2:
        if override or key not in a:
            a[key] = value
int PyDict_AddWatcher(PyDict_WatchCallback callback)

callback 註冊為字典觀察器。返回一個非負整數 ID,該 ID 必須傳遞給未來對 PyDict_Watch() 的呼叫。如果發生錯誤(例如,沒有可用的觀察器 ID),則返回 -1 並設定異常。

3.12 新版功能.

int PyDict_ClearWatcher(int watcher_id)

清除之前從 PyDict_AddWatcher() 返回的由 watcher_id 標識的觀察器。成功時返回 0,錯誤時返回 -1(例如,如果給定的 watcher_id 從未註冊)。

3.12 新版功能.

int PyDict_Watch(int watcher_id, PyObject *dict)

將字典 dict 標記為被監視。當 dict 被修改或解除分配時,PyDict_AddWatcher() 授予 watcher_id 的回撥將被呼叫。成功時返回 0,錯誤時返回 -1

3.12 新版功能.

int PyDict_Unwatch(int watcher_id, PyObject *dict)

將字典 dict 標記為不再被監視。PyDict_AddWatcher() 授予 watcher_id 的回撥將不再在 dict 被修改或解除分配時被呼叫。該字典必須之前已被此觀察器監視。成功時返回 0,錯誤時返回 -1

3.12 新版功能.

type PyDict_WatchEvent

字典觀察器事件的列舉:PyDict_EVENT_ADDEDPyDict_EVENT_MODIFIEDPyDict_EVENT_DELETEDPyDict_EVENT_CLONEDPyDict_EVENT_CLEAREDPyDict_EVENT_DEALLOCATED

3.12 新版功能.

typedef int (*PyDict_WatchCallback)(PyDict_WatchEvent event, PyObject *dict, PyObject *key, PyObject *new_value)

字典觀察器回撥函式的型別。

如果 eventPyDict_EVENT_CLEAREDPyDict_EVENT_DEALLOCATED,則 keynew_value 都將為 NULL。如果 eventPyDict_EVENT_ADDEDPyDict_EVENT_MODIFIED,則 new_value 將是 key 的新值。如果 eventPyDict_EVENT_DELETED,則 key 將從字典中刪除,並且 new_value 將為 NULL

dict 之前為空並且另一個字典合併到其中時,會發生 PyDict_EVENT_CLONED。為了保持此操作的效率,在這種情況下不會發出按鍵的 PyDict_EVENT_ADDED 事件;而是發出單個 PyDict_EVENT_CLONED,並且 key 將是源字典。

回撥可以檢查但不得修改 dict;這樣做可能會產生不可預測的影響,包括無限遞迴。不要在回撥中觸發 Python 程式碼執行,因為這可能會作為副作用修改字典。

如果 eventPyDict_EVENT_DEALLOCATED,在回撥中獲取對即將銷燬的字典的新引用將使其復活並阻止它在此刻被釋放。當復活的物件稍後被銷燬時,當時處於活動狀態的任何觀察器回撥將再次被呼叫。

回調發生在對 dict 的通知修改之前,因此可以檢查 dict 的先前狀態。

如果回撥設定了異常,它必須返回 -1;此異常將使用 PyErr_WriteUnraisable() 列印為無法引發的異常。否則,它應該返回 0

進入回撥時可能已經設定了掛起異常。在這種情況下,回撥應返回 0,並保持相同的異常設定。這意味著回撥不能呼叫任何其他可能設定異常的 API,除非它首先儲存並清除異常狀態,並在返回之前恢復它。

3.12 新版功能.