@@ -4162,17 +4162,34 @@ static PySequenceMethods dictkeys_as_sequence = {
4162
4162
(objobjproc )dictkeys_contains , /* sq_contains */
4163
4163
};
4164
4164
4165
+ // Create an set object from dictviews object.
4166
+ // Returns a new reference.
4167
+ // This utility function is used by set operations.
4165
4168
static PyObject *
4166
- dictviews_sub (PyObject * self , PyObject * other )
4169
+ dictviews_to_set (PyObject * self )
4167
4170
{
4168
- PyObject * result = PySet_New (self );
4169
- PyObject * tmp ;
4170
- _Py_IDENTIFIER (difference_update );
4171
+ PyObject * left = self ;
4172
+ if (PyDictKeys_Check (self )) {
4173
+ // PySet_New() has fast path for the dict object.
4174
+ PyObject * dict = (PyObject * )((_PyDictViewObject * )self )-> dv_dict ;
4175
+ if (PyDict_CheckExact (dict )) {
4176
+ left = dict ;
4177
+ }
4178
+ }
4179
+ return PySet_New (left );
4180
+ }
4171
4181
4172
- if (result == NULL )
4182
+ static PyObject *
4183
+ dictviews_sub (PyObject * self , PyObject * other )
4184
+ {
4185
+ PyObject * result = dictviews_to_set (self );
4186
+ if (result == NULL ) {
4173
4187
return NULL ;
4188
+ }
4174
4189
4175
- tmp = _PyObject_CallMethodIdOneArg (result , & PyId_difference_update , other );
4190
+ _Py_IDENTIFIER (difference_update );
4191
+ PyObject * tmp = _PyObject_CallMethodIdOneArg (
4192
+ result , & PyId_difference_update , other );
4176
4193
if (tmp == NULL ) {
4177
4194
Py_DECREF (result );
4178
4195
return NULL ;
@@ -4273,34 +4290,29 @@ _PyDictView_Intersect(PyObject* self, PyObject *other)
4273
4290
static PyObject *
4274
4291
dictviews_or (PyObject * self , PyObject * other )
4275
4292
{
4276
- PyObject * result = PySet_New (self );
4277
- PyObject * tmp ;
4278
- _Py_IDENTIFIER (update );
4279
-
4280
- if (result == NULL )
4293
+ PyObject * result = dictviews_to_set (self );
4294
+ if (result == NULL ) {
4281
4295
return NULL ;
4296
+ }
4282
4297
4283
- tmp = _PyObject_CallMethodIdOneArg (result , & PyId_update , other );
4284
- if (tmp == NULL ) {
4298
+ if (_PySet_Update (result , other ) < 0 ) {
4285
4299
Py_DECREF (result );
4286
4300
return NULL ;
4287
4301
}
4288
-
4289
- Py_DECREF (tmp );
4290
4302
return result ;
4291
4303
}
4292
4304
4293
4305
static PyObject *
4294
4306
dictviews_xor (PyObject * self , PyObject * other )
4295
4307
{
4296
- PyObject * result = PySet_New (self );
4297
- PyObject * tmp ;
4298
- _Py_IDENTIFIER (symmetric_difference_update );
4299
-
4300
- if (result == NULL )
4308
+ PyObject * result = dictviews_to_set (self );
4309
+ if (result == NULL ) {
4301
4310
return NULL ;
4311
+ }
4302
4312
4303
- tmp = _PyObject_CallMethodIdOneArg (result , & PyId_symmetric_difference_update , other );
4313
+ _Py_IDENTIFIER (symmetric_difference_update );
4314
+ PyObject * tmp = _PyObject_CallMethodIdOneArg (
4315
+ result , & PyId_symmetric_difference_update , other );
4304
4316
if (tmp == NULL ) {
4305
4317
Py_DECREF (result );
4306
4318
return NULL ;
0 commit comments