Updating a single value in a list of dictionaries - python

I have a webpage where I display a list of passenger information as a table. This is the usual stuff: arrival_time, flight number etc.
I've made the table editable so when the user clicks a certain column with information he can edit this column. When he finally clicks confirm I send only the columns that were edited along with value and row number to the view which is suppose to locate the row of the list from the data I sent, find the key and update the original value.
The json values I get from editing a column look like this:
[{u'classname': u'flight', u'column': 6, u'value': u'F1521', u'row': 0}, {u'classname': u'flight', u'column': 6, u'value': u'FI521', u'row': 1}]
The code I have so far to update the value looks like this:
# Original data
query = UploadOrderModel.objects.filter(hashId = receiptNr)
# Gives me a list of dictionaries containing these keys
data = query.values("office", "reserv", "title","surname","firstN",
"arrival", "flight", "transferF", "hotelD", "tour")
# Update
json_dump = json.loads(request.body)
if json_dump:
for d in json_dump:
# get row number
row = int(d['row'])
# updates dictionary value at row
data[row][d['classname']] = d['value']
But this does not update the value. I have checked if is getting the correct values to update and it is, so that's not the case, row is correct and if I print out:
data[row][d['classname']]
I get the element I want to update. Is there anything really obvious I'm missing here.
Should I be making updates to the entire row instead? so update the entire dictionary at
the current location?
EDIT:
I'm still having problems. First off, i misread your good answer lyschoening. I thought you meant that values() does not return a writeable list, silly me. The saving of the model is done later in the code and works as expected. However I still have the problem of the dictionary at the location I'm trying to update does not update at all :/

Ok I found out what was the problem.
django values() does not return a list of dictionaries as it looks but a ValuesQuerySet.
It is therefor not possible to do updates on this list as one would do with a regular list.
All I had to do was turning it into a list of dictionaries:
updates = [item for item in data]

Related

Using Dictionary in Python

I am trying to read data from an excel sheet and form a dictionary in a loop as below.
for row in range(2,sheet.max_row+1):
temp_list.clear()
for col in range (2,sheet.max_column):
temp_list.append(sheet.cell(row,col).value)
dict_key = sheet.cell(row,1).value
Create a dictionary
MyDataDictionary.update( {dict_key : temp_list})
Assuming my excel have two rows of data I am reading, my dictionary value always gets overwritten with the value from second row always
(Create a dictionary) if this is part of your code what i think is your dictionary is getting created each time you run the loop therefore you should create dictionary before running loop and then update it
Try something like this below:
if MyDataDictionary.get(dict_key, []):
#updates the existing key assuming that temp_list is always a list
MyDataDictionary.get(dict_key).extend(temp_list)
else:
#creates a new key
MyDataDictionary.update({dict_key : temp_list})

How to insert multiple values into specific treeview columns?

I have a database returning the total of several column and I am trying to display it in a treeview. If I do
for i in backend2.calc_total()[0]:
treeviewtotal.insert("", END, values=i)
I get
which is not what i want as i want everything to start from "food" column onwards. I cant make date a iid as i already have an iid that I am referencing to my database.
If I do
list2 = ['Date', 'Food', 'Transport', 'Insurance', 'Installments', 'Others']
for i in range(len(backend2.calc_total()[0][0])):
treeviewtotal.insert("", 0, list2[i+1], values=backend2.calc_total()[0][0][i])
I get this
instead, all the totals get stacked into 1 column (which is scrollable).
Any way to achieve my aim of allocating the respective totals to the respective column in a same row? Thanks!
With reference to the first attempt, the following solves the problem:
for i in backend2.calc_total()[0]:
treeviewtotal.insert("", END, values=([], *i))
values= takes in a list. Therefore we add an empty space by using [], but since i itself is already a list, we need to "flatten out" the list by doing *i.
Please correct me if I used any parts of the code wrongly. Still trying to learn =)

how to edit records in the database using Tryton code

I want to edit (add or delete) records in the database using Tryton code.
Which function or method should I use to modify records in Tryton?
Example:
status=fields.Char("status")
How can I delete all records of field status and add a new one which has the value status1?
You just need to use the ORM methods in order to search for the values you want and then delete them. So for example:
pool = Pool()
Model = pool.get('your.model.name')
records = Model.search([('status', '=', 'search_value')])
Model.delete(records)
In order to create new ones just use a the create method with a list of dictionaries. Each dictionary key must be the name of the field, and their value the value you want yo set. So for example:
values = [{'state': 'one'}, {'state': 'two'}]
Model.create(values)
Will create two records, one with state == 'one' and the other with state == 'two'

Change List of Tuples into Dictionary (pythonic way)

This is more of a best practice question. What I have created is working perfectly, but I am curious if there is a shorter method for creating a dictionary out of my current data structure.
I am reading tables out of a SQLite database, the data is returned as a list of tuples.
eg
[(49, u'mRec49', u'mLabel49', 1053, 1405406806822606L, u'1405406906822606'),
(48, u'mRec48', u'mLabel48', 1330, 1405405806822606L, u'1405405906822606'),
(47, u'mRec47', u'mLabel47', 1220, 1405404806822606L, u'1405404906822606')...
]
I want to take each column of the list-tuple structure, make it into a list, get the column name from the database and use that as the key holding the list. Later I turn my dictionary into JSON.
Here is my function I scratched up, it does the job, I just can't help wondering if there is a better way to do this.
def make_dict(columns, list_o_tuples):
anary = {}
for j, column in enumerate(columns):
place = []
for row in list_o_tuples:
place.append(row[j])
anary[column] = place
return anary
make_dict(mDBTable.columns, mDBTable.get_table())
Note:the function shouldn't care about the table its presented, or the number or rows & columns in table.
It seems that you want to transpose the list_o_tuples:
transpose = zip(*list_o_tuples)
And then zip that up with the column names:
return dict(zip(columns, transpose))
You can simply unzip the list_o_tuples and then using a dictionary comprehension create a new dictionary with the corresponding column data and the column header
columns = ["num1", "str1", "num2", "num3", "str2", "str3"]
print {columns[idx]:row for idx, row in enumerate(zip(*list_o_tuples))}

Adding Keys and Values to Python Dictionary in Reverse Order

I have written a simple script that prints out and adds the name of a table and it's associated column headings to a python list:
for table in arcpy.ListTables():
for field in arcpy.ListFields(table):
b.append(field.name + "," + fc)
print b
In each table there are a number of column headings. There are many instances where one or more tables contain the same column headings. I want to do a bit of a reverse python dictionary instead of a list, where keys are the column headings and the values are the table names. My idea is, to find the all the tables that each column heading lies within.
I've been playing around all afternoon and I think I am over thinking this so I came here for some help. If anyone can suggest how I can accomplish this, i would appreciate it.
Thanks,
Mike
Try this:
result = {}
for table in arcpy.ListTables():
for field in arcpy.ListFields(table):
result.setdefault(field.name, []).append(table)
If I understand correctly, you want to map from a column name to a list of tables that contain that have columns with that name. That should be easy enough to do with a defaultdict:
from collections import defaultdict
header_to_table_dict = defaultdict(list)
for table in arcpy.ListTables():
for field in arcpy.ListFields(table):
header_to_table_dict[field.name].append(table.name)
I'm not sure if table.name is what you want to save, exactly, but this should get you on the right track.
You want to create a dictionary in which each key is a field name, and each value is a list of table names:
# initialize the dictionary
col_index = {}
for table in arcpy.ListTables():
for field in arcpy.ListFields(table):
if field.name not in col_index:
# this is a field name we haven't seen before,
# so initialize a dictionary entry with an empty list
# as the corresponding value
col_index[field.name] = []
# add the table name to the list of tables for this field name
col_index[field.name].append(table.name)
And then, if you want want a list of tables that contain the field LastName:
list_of_tables = col_index['LastName']
If you're using a database that is case-insensitive with respect to column names, you might want to convert field.name to upper case before testing the dictionary.

Categories