16

I was doing django project about processing request.data and from.cleaned_data issues. When user only inputs specify fields, it will send request to my server. Next, the form class process the request, except processing inputed fields and return no inputted fields from form built-in fields.

This is request data:

<QueryDict: {u'is_public': [u'True']}>

This is cleaned data from from class:

{'name': u'', 'devie_type': u'', 'is_public': True, 'serial_num': u'', 'is_online': False, 'operation_system': u''}

I know these are dictionary type. I hope getting their union keys of them and values of cleaned data. I expect that it returns:

{u'is_public': True}

This is my attempt:

a = {}
for k in request.data:
    if k in the_form.cleaned_data:
        a[k] = the_form.cleaned_data[k]
print a

Is it readable? or is there any built-in functions about processing union dictionary in python?

0

3 Answers 3

8

You can use intersection operations (which sounds like what you really want, not union) to efficiently limit iteration to keys common to both dicts, then use a dict comprehension to achieve this fairly efficiently:

a = {k: the_form.cleaned_data[k]
     for k in request.data.viewkeys() & the_form.cleaned_data.viewkeys()}

So when a key exists in both the request and the cleaned data, you'll have a mapping from that key to the cleaned data. All other keys that appear in only one input dict or the other are dropped. In Python 3, you'd replace .viewkeys() with just .keys() (and this won't work before Python 2.7, which is where .viewkeys() was introduced).

6
  • Let me edit my problem. My environment is python-2.7 Commented Oct 28, 2015 at 3:11
  • @BurgerKing: I assumed it was. This will work just fine with .viewkeys() on Python 2.7, I just included the Python 3 differences for completeness. Commented Oct 28, 2015 at 3:12
  • list and list can do union? or is it available on python3? Commented Oct 28, 2015 at 3:15
  • .viewkeys() is not a list, it's a special "keys view" object, that is set-like live view of the dict's keys. In Python 3, .keys() is the same as Py 2.7's .viewkeys() (.iterkeys() and the Py2-style .keys() returning list are removed; the views already iterate, and you can just wrap .keys() calls in the list constructor if you need an actual list). Commented Oct 28, 2015 at 3:19
  • @BurgerKing: You can see more details at What's new in Python 3.0: Views and iterators instead of lists, which describes how many built-ins went from producing lists to producing views or iterator/generator objects, to reduce the creation of unnecessary intermediate data copies. Commented Oct 28, 2015 at 3:21
3

There's nothing inherently wrong with what you're doing, all totally fine. However, the more pythonic way to do this would be to use a dictionary comprehension:

a = {
   k: the_form.cleaned_data[k]
   for k in request.data
   if k in the_form.cleaned_data
}
2
  • Great! It's my wanted. Commented Oct 28, 2015 at 3:09
  • 1
    This is the same basic concept as my answer, though it won't allow Python to optimize for cases where the request.data dict is large and the cleaned_data is small (because it must loop and check them all, where intersection operations can choose to iterate the smaller input and membership test the larger input, to reduce the work to the lesser of the two inputs' lengths). Commented Oct 28, 2015 at 3:11
0

just do: request_data.update(form.cleaned_data)

5
  • Sorry, the return is not my expect: <QueryDict: {u'name': [u''], u'devie_type': [u''], u'serial_num': [u''], u'opera tion_system': [u''], u'is_online': [False], u'is_public': [u'True', True]}> Commented Oct 28, 2015 at 3:01
  • i modified my answer a couple of times..which one did you try out?
    – labheshr
    Commented Oct 28, 2015 at 3:03
  • Please check your code before posting your answer. My expectation is {u'is_public': True} Commented Oct 28, 2015 at 3:06
  • your question's title is misleading...my answer correctly posts the union of two dicts with request_data getting the right value of public in addition to contents of cleaned_data - which is what union means...also this question is closed in favor of a question that allows for union of two dicts, not exactly what you want ....
    – labheshr
    Commented Oct 28, 2015 at 3:10
  • run this as is and you'll see what i mean : request_data = {u'is_public': [u'True']} cleaned_data = {'name': u'', 'devie_type': u'', 'is_public': True, 'serial_num': u'', 'is_online': False, 'operation_system': u''} request_data.update(cleaned_data) print request_data
    – labheshr
    Commented Oct 28, 2015 at 3:11

Not the answer you're looking for? Browse other questions tagged or ask your own question.