Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit a797d81

Browse files
committed
Patch #642500 with slight modifications: allow keyword arguments in
dict() constructor. Example: >>> dict(a=1, b=2) {'a': 1, 'b': 2} >>>
1 parent e17af7b commit a797d81

4 files changed

Lines changed: 46 additions & 30 deletions

File tree

Doc/lib/libfuncs.tex

Lines changed: 21 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -189,27 +189,34 @@ \section{Built-in Functions \label{built-in-funcs}}
189189
\end{funcdesc}
190190

191191
\begin{funcdesc}{dict}{\optional{mapping-or-sequence}}
192-
Return a new dictionary initialized from the optional argument.
193-
If an argument is not specified, return a new empty dictionary.
194-
If the argument is a mapping object, return a dictionary mapping the
195-
same keys to the same values as does the mapping object.
196-
Else the argument must be a sequence, a container that supports
197-
iteration, or an iterator object. The elements of the argument must
198-
each also be of one of those kinds, and each must in turn contain
192+
Return a new dictionary initialized from an optional positional
193+
argument or from a set of keyword arguments.
194+
If no arguments are given, return a new empty dictionary.
195+
If the positional argument is a mapping object, return a dictionary
196+
mapping the same keys to the same values as does the mapping object.
197+
Otherwise the positional argument must be a sequence, a container that
198+
supports iteration, or an iterator object. The elements of the argument
199+
must each also be of one of those kinds, and each must in turn contain
199200
exactly two objects. The first is used as a key in the new dictionary,
200201
and the second as the key's value. If a given key is seen more than
201202
once, the last value associated with it is retained in the new
202203
dictionary.
204+
205+
If keyword arguments are given, the keywords themselves with their
206+
associated values are added as items to the dictionary. If a key
207+
is specified both in the positional argument and as a keyword argument,
208+
the value associated with the keyword is retained in the dictionary.
203209
For example, these all return a dictionary equal to
204-
\code{\{1: 2, 2: 3\}}:
210+
\code{\{"one": 2, "two": 3\}}:
205211

206212
\begin{itemize}
207-
\item \code{dict(\{1: 2, 2: 3\})}
208-
\item \code{dict(\{1: 2, 2: 3\}.items())}
209-
\item \code{dict(\{1: 2, 2: 3\}.iteritems())}
210-
\item \code{dict(zip((1, 2), (2, 3)))}
211-
\item \code{dict([[2, 3], [1, 2]])}
212-
\item \code{dict([(i-1, i) for i in (2, 3)])}
213+
\item \code{dict(\{'one': 2, 'two': 3\})}
214+
\item \code{dict(\{'one': 2, 'two': 3\}.items())}
215+
\item \code{dict(\{'one': 2, 'two': 3\}.iteritems())}
216+
\item \code{dict(zip(('one', 'two'), (2, 3)))}
217+
\item \code{dict([['two', 3], ['one', 2]])}
218+
\item \code{dict(one=2, two=3)}
219+
\item \code{dict([(['one', 'two'][i-2], i) for i in (2, 3)])}
213220
\end{itemize}
214221

215222
\versionadded{2.2}

Lib/test/test_descr.py

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -184,12 +184,19 @@ def dict_constructor():
184184
vereq(d, {})
185185
d = dict({})
186186
vereq(d, {})
187-
d = dict(items={})
187+
d = dict({})
188188
vereq(d, {})
189189
d = dict({1: 2, 'a': 'b'})
190190
vereq(d, {1: 2, 'a': 'b'})
191191
vereq(d, dict(d.items()))
192-
vereq(d, dict(items=d.iteritems()))
192+
vereq(d, dict(d.iteritems()))
193+
d = dict({'one':1, 'two':2})
194+
vereq(d, dict(one=1, two=2))
195+
vereq(d, dict(**d))
196+
vereq(d, dict({"one": 1}, two=2))
197+
vereq(d, dict([("two", 2)], one=1))
198+
vereq(d, dict([("one", 100), ("two", 200)], **d))
199+
verify(d is not dict(**d))
193200
for badarg in 0, 0L, 0j, "0", [0], (0,):
194201
try:
195202
dict(badarg)
@@ -205,12 +212,6 @@ def dict_constructor():
205212
raise TestFailed("no TypeError from dict(%r)" % badarg)
206213
else:
207214
raise TestFailed("no TypeError from dict(%r)" % badarg)
208-
try:
209-
dict(senseless={})
210-
except TypeError:
211-
pass
212-
else:
213-
raise TestFailed("no TypeError from dict(senseless={})")
214215

215216
try:
216217
dict({}, {})
@@ -232,7 +233,7 @@ class Mapping:
232233

233234
Mapping.keys = lambda self: self.dict.keys()
234235
Mapping.__getitem__ = lambda self, i: self.dict[i]
235-
d = dict(items=Mapping())
236+
d = dict(Mapping())
236237
vereq(d, Mapping.dict)
237238

238239
# Init from sequence of iterable objects, each producing a 2-sequence.
@@ -2332,10 +2333,10 @@ def keywords():
23322333
vereq(unicode(string='abc', errors='strict'), u'abc')
23332334
vereq(tuple(sequence=range(3)), (0, 1, 2))
23342335
vereq(list(sequence=(0, 1, 2)), range(3))
2335-
vereq(dict(items={1: 2}), {1: 2})
2336+
# note: as of Python 2.3, dict() no longer has an "items" keyword arg
23362337

23372338
for constructor in (int, float, long, complex, str, unicode,
2338-
tuple, list, dict, file):
2339+
tuple, list, file):
23392340
try:
23402341
constructor(bogus_keyword_arg=1)
23412342
except TypeError:

Misc/NEWS

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,12 @@ What's New in Python 2.3 alpha 1?
1111

1212
Type/class unification and new-style classes
1313
--------------------------------------------
14+
- dict() now accepts keyword arguments so that dict(one=1,two=2)
15+
is the equivalent of dict([('one',1),('two',2)]). Accordingly,
16+
the existing (but undocumented) 'items' keyword argument has
17+
been eliminated. This means that dict(items=someMapping) now has
18+
a different meaning than before.
19+
1420
- int() now returns a long object if the argument is outside the
1521
integer range, so int("4"*1000), int(1e200) and int(1L<<1000) will
1622
all return long objects instead of raising an OverflowError.

Objects/dictobject.c

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1705,7 +1705,7 @@ static PyMethodDef mapp_methods[] = {
17051705
{"setdefault", (PyCFunction)dict_setdefault, METH_VARARGS,
17061706
setdefault_doc__},
17071707
{"pop", (PyCFunction)dict_pop, METH_O,
1708-
pop__doc__},
1708+
pop__doc__},
17091709
{"popitem", (PyCFunction)dict_popitem, METH_NOARGS,
17101710
popitem__doc__},
17111711
{"keys", (PyCFunction)dict_keys, METH_NOARGS,
@@ -1781,11 +1781,9 @@ static int
17811781
dict_init(PyObject *self, PyObject *args, PyObject *kwds)
17821782
{
17831783
PyObject *arg = NULL;
1784-
static char *kwlist[] = {"items", 0};
17851784
int result = 0;
17861785

1787-
if (!PyArg_ParseTupleAndKeywords(args, kwds, "|O:dict",
1788-
kwlist, &arg))
1786+
if (!PyArg_ParseTuple(args, "|O:dict", &arg))
17891787
result = -1;
17901788

17911789
else if (arg != NULL) {
@@ -1794,6 +1792,8 @@ dict_init(PyObject *self, PyObject *args, PyObject *kwds)
17941792
else
17951793
result = PyDict_MergeFromSeq2(self, arg, 1);
17961794
}
1795+
if (result == 0 && kwds != NULL)
1796+
result = PyDict_Merge(self, kwds, 1);
17971797
return result;
17981798
}
17991799

@@ -1817,7 +1817,9 @@ PyDoc_STRVAR(dictionary_doc,
18171817
"dict(seq) -> new dictionary initialized as if via:\n"
18181818
" d = {}\n"
18191819
" for k, v in seq:\n"
1820-
" d[k] = v");
1820+
" d[k] = v\n"
1821+
"dict(**kwargs) -> new dictionary initialized with the name=value pairs\n"
1822+
" in the keyword argument list. For example: dict(one=1, two=2)");
18211823

18221824
PyTypeObject PyDict_Type = {
18231825
PyObject_HEAD_INIT(&PyType_Type)

0 commit comments

Comments
 (0)