bpo-36144: Dictionary Union (PEP 584) (#12088) · python/cpython@eb8ac57 (original) (raw)
`@@ -2320,6 +2320,25 @@ dict_fromkeys_impl(PyTypeObject *type, PyObject *iterable, PyObject *value)
`
2320
2320
`return _PyDict_FromKeys((PyObject *)type, iterable, value);
`
2321
2321
`}
`
2322
2322
``
``
2323
`+
/* Single-arg dict update; used by dict_update_common and operators. */
`
``
2324
`+
static int
`
``
2325
`+
dict_update_arg(PyObject *self, PyObject *arg)
`
``
2326
`+
{
`
``
2327
`+
if (PyDict_CheckExact(arg)) {
`
``
2328
`+
return PyDict_Merge(self, arg, 1);
`
``
2329
`+
}
`
``
2330
`+
_Py_IDENTIFIER(keys);
`
``
2331
`+
PyObject *func;
`
``
2332
`+
if (_PyObject_LookupAttrId(arg, &PyId_keys, &func) < 0) {
`
``
2333
`+
return -1;
`
``
2334
`+
}
`
``
2335
`+
if (func != NULL) {
`
``
2336
`+
Py_DECREF(func);
`
``
2337
`+
return PyDict_Merge(self, arg, 1);
`
``
2338
`+
}
`
``
2339
`+
return PyDict_MergeFromSeq2(self, arg, 1);
`
``
2340
`+
}
`
``
2341
+
2323
2342
`static int
`
2324
2343
`dict_update_common(PyObject *self, PyObject *args, PyObject *kwds,
`
2325
2344
`const char *methname)
`
`@@ -2331,23 +2350,7 @@ dict_update_common(PyObject *self, PyObject *args, PyObject *kwds,
`
2331
2350
`result = -1;
`
2332
2351
` }
`
2333
2352
`else if (arg != NULL) {
`
2334
``
`-
if (PyDict_CheckExact(arg)) {
`
2335
``
`-
result = PyDict_Merge(self, arg, 1);
`
2336
``
`-
}
`
2337
``
`-
else {
`
2338
``
`-
_Py_IDENTIFIER(keys);
`
2339
``
`-
PyObject *func;
`
2340
``
`-
if (_PyObject_LookupAttrId(arg, &PyId_keys, &func) < 0) {
`
2341
``
`-
result = -1;
`
2342
``
`-
}
`
2343
``
`-
else if (func != NULL) {
`
2344
``
`-
Py_DECREF(func);
`
2345
``
`-
result = PyDict_Merge(self, arg, 1);
`
2346
``
`-
}
`
2347
``
`-
else {
`
2348
``
`-
result = PyDict_MergeFromSeq2(self, arg, 1);
`
2349
``
`-
}
`
2350
``
`-
}
`
``
2353
`+
result = dict_update_arg(self, arg);
`
2351
2354
` }
`
2352
2355
``
2353
2356
`if (result == 0 && kwds != NULL) {
`
`@@ -3169,6 +3172,33 @@ dict_sizeof(PyDictObject *mp, PyObject *Py_UNUSED(ignored))
`
3169
3172
`return PyLong_FromSsize_t(_PyDict_SizeOf(mp));
`
3170
3173
`}
`
3171
3174
``
``
3175
`+
static PyObject *
`
``
3176
`+
dict_or(PyObject *self, PyObject *other)
`
``
3177
`+
{
`
``
3178
`+
if (!PyDict_Check(self) || !PyDict_Check(other)) {
`
``
3179
`+
Py_RETURN_NOTIMPLEMENTED;
`
``
3180
`+
}
`
``
3181
`+
PyObject *new = PyDict_Copy(self);
`
``
3182
`+
if (new == NULL) {
`
``
3183
`+
return NULL;
`
``
3184
`+
}
`
``
3185
`+
if (dict_update_arg(new, other)) {
`
``
3186
`+
Py_DECREF(new);
`
``
3187
`+
return NULL;
`
``
3188
`+
}
`
``
3189
`+
return new;
`
``
3190
`+
}
`
``
3191
+
``
3192
`+
static PyObject *
`
``
3193
`+
dict_ior(PyObject *self, PyObject *other)
`
``
3194
`+
{
`
``
3195
`+
if (dict_update_arg(self, other)) {
`
``
3196
`+
return NULL;
`
``
3197
`+
}
`
``
3198
`+
Py_INCREF(self);
`
``
3199
`+
return self;
`
``
3200
`+
}
`
``
3201
+
3172
3202
`PyDoc_STRVAR(getitem__doc__, "x.getitem(y) <==> x[y]");
`
3173
3203
``
3174
3204
`PyDoc_STRVAR(sizeof__doc__,
`
`@@ -3274,6 +3304,11 @@ static PySequenceMethods dict_as_sequence = {
`
3274
3304
`0, /* sq_inplace_repeat */
`
3275
3305
`};
`
3276
3306
``
``
3307
`+
static PyNumberMethods dict_as_number = {
`
``
3308
`+
.nb_or = dict_or,
`
``
3309
`+
.nb_inplace_or = dict_ior,
`
``
3310
`+
};
`
``
3311
+
3277
3312
`static PyObject *
`
3278
3313
`dict_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
`
3279
3314
`{
`
`@@ -3335,7 +3370,7 @@ PyTypeObject PyDict_Type = {
`
3335
3370
`0, /* tp_setattr */
`
3336
3371
`0, /* tp_as_async */
`
3337
3372
` (reprfunc)dict_repr, /* tp_repr */
`
3338
``
`-
0, /* tp_as_number */
`
``
3373
`+
&dict_as_number, /* tp_as_number */
`
3339
3374
`&dict_as_sequence, /* tp_as_sequence */
`
3340
3375
`&dict_as_mapping, /* tp_as_mapping */
`
3341
3376
`PyObject_HashNotImplemented, /* tp_hash */
`