I have a tuple, In this tuple, I have two values first-one is a dictionary and the second is list.
so I want all values in the dictionary only.
I have:
data_tuple = ({'student':['raaj','rohan','rahul'],'teacher':['teacher1','teacher2']},[3,2])
But the correct output I needed:
data_dictionary = {'student':[('raaj','rohan','rahul'),(3)],'teacher':[('teacher1','teacher2'),(2)]}
This might help you
Assumes that len of data_tuple[1] == length of data_tuple [0] or else you need to handle that.
data_tuple = ({'student':['raaj','rohan','rahul'],'teacher':['teacher1','teacher2']},[3,2])
keys = data_tuple[0].keys()
count = 0
ans = {}
for i in keys:
ans[i] = [ tuple(data_tuple[0][i]), (data_tuple[1][count])]
count = count+1
print(ans)
Output
{'student': [('raaj', 'rohan', 'rahul'), 3], 'teacher': [('teacher1', 'teacher2'), 2]}
Or else change the following if you want other output as follows
for i in keys:
ans[i] = [ tuple(data_tuple[0][i]), (data_tuple[1][count], )]
count=count+1
Output
{'student': [('raaj', 'rohan', 'rahul'), (3,)], 'teacher': [('teacher1', 'teacher2'), (2,)]}
Though I have same question - How do you know which key to pair with which item from the list? The dictionary has no inherent order.
Related
I was making a program where first parameter is a list and second parameter is a list of dictionaries. I want to return a list of lists like this:
As an example, if this were a function call:
make_lists(['Example'],
[{'Example': 'Made-up', 'Extra Keys' : 'Possible'}]
)
the expected return value would be:
[ ['Made-up'] ]
As an second example, if this were a function call:
make_lists(['Hint', 'Num'],
[{'Hint': 'Length 2 Not Required', 'Num' : 8675309},
{'Num': 1, 'Hint' : 'Use 1st param order'}]
)
the expected return value would be:
[ ['Length 2 Not Required', 8675309],
['Use 1st param order', 1]
]
I have written a code for this but my code does not return a list of lists, it just returns a single list. Please can someone explain?
def make_lists(s,lod):
a = []
lol =[]
i = 0
for x in lod:
for y in x:
for k in s:
if(y==k):
lol.append(x.get(y))
i = i+1
return lol
Expected Output:
[ ['Length 2 Not Required', 8675309],['Use 1st param order', 1] ]
Output:
['Length 2 Not Required', 8675309, 1, 'Use 1st param order']
The whole point of dictionaries, is that you can access them by key:
def make_lists(keys, dicts):
result = []
for d in dicts:
vals = [d[k] for k in keys if k in d]
if len(vals) > 0:
result.append(vals)
return result
Let's have a look what happens here:
We still have the result array, which accumulates the answers, but now it's called result instead of lol
Next we iterate through every dictionary:
for d in dicts:
For each dictionary d, we create a list, which is a lookup in that dictionary for the keys in keys, if the key k is in the dictionary d:
vals = [d[k] for k in keys if k in d]
The specs don't detail this, but I assume if none of the keys are in the dictionary, you don't want it added to the array. For that, we have a check if vals have any results, and only then we add it to the results:
if len(vals) > 0:
result.append(vals)
Try this code - I've managed to modify your existing code slighty, and added explanation in the comments. Essentially, you just need to use a sub-list and add that to the master list lol, and then in each loop iteration over elements in lod, append to the sub-list instead of the outermost list.
def make_lists(s,lod):
a = []
lol =[]
i = 0
for x in lod:
## Added
# Here we want to create a new list, and add it as a sub-list
# within 'lol'
lols = []
lol.append(lols)
## Done
for y in x:
for k in s:
if(y==k):
# Changed 'lol' to 'lols' here
lols.append(x.get(y))
i = i+1
return lol
print(make_lists(['Example'], [{'Example': 'Made-up', 'Extra Keys' : 'Possible'}]))
print(make_lists(['Hint', 'Num'], [{'Hint': 'Length 2 Not Required', 'Num' : 8675309}, {'Num': 1, 'Hint' : 'Use 1st param order'}]))
Prints:
[['Made-up']]
[['Length 2 Not Required', 8675309], [1, 'Use 1st param order']]
A simpler solution
For a cleaner (and potentially more efficient approach), I'd suggest using builtins like map and using a list comprehension to tackle this problem:
def make_lists(s, lod):
return [[*map(dict_obj.get, s)] for dict_obj in lod]
But note, that this approach includes elements as None in cases where the desired keys in s are not present in the dictionary objects within the list lod.
To work around that, you can pass the result of map to the filter builtin function so that None values (which represent missing keys in dictionaries) are then stripped out in the result:
def make_lists(s, lod):
return [[*filter(None, map(dict_obj.get, s))] for dict_obj in lod]
print(make_lists(['Example'], [{'Extra Keys' : 'Possible'}]))
print(make_lists(['Hint', 'Num'], [{'Num' : 8675309}, {'Num': 1, 'Hint' : 'Use 1st param order'}]))
Output:
[[]]
[[8675309], ['Use 1st param order', 1]]
I wanna achieve this without any libraries or special functions just loops. I wanna have a main program that takes in 2 inputs which are the 2 lists and returns the dictionary like shown below.
Please enter the item names: Cans, bottles, boxes, jugs
please enter quantities : 20,34,10
output : {'Cans':'20','bottles':'34','boxes':'10','jugs':'0'}
If the list of items is longer than the quantities then the quantity becomes automatically 0 as it did with the jugs above.
If the List of Quantity is longer than the items list then the item should automatically become 'unknown object_1' with the number changing accordingly.
Split with comma as delimiter. Fill values with zero for a number of iterations equal to the difference in length between keys and values.
Then use dict comprehension to build your dict. This with the zip built-in function.
keys = 'a,b,c,d'
values = '1,2,3'
keys = keys.split(',')
values = values.split(',')
for i in range(len(keys) - len(values)):
values.append('0')
dct = {}
for i in range(len(keys)):
dct[keys[i]] = values[i]
print(dct)
Output:
{'a': '1', 'b': '2', 'c': '3', 'd': '0'}
This uses only built-in calls so it fits your requirements at best. At the OP requirements it is not using the zip function.
item_names = ['Cans', 'Bottles', 'boxes', 'jugs']
quantities = [20, 34, 10]
output_dict = {}
for i, item in enumerate(item_names):
if i > len(quantities) - 1:
output_dict.update({item : 0})
else:
output_dict.update({item : quantities[i]})
a = list(input().split(','))
b = list(map(int, input().split(',')))
res = {}
for i in range(len(a)):
res[a[i]] = b[i] if i < len(b) else 0
print(res)
list1 = ['cans','Bottles','Boxes','Jugs']
list2 = [1,2,3]
res = {}
for i, element in enumerate(list1):
try:
res[element] = list2[i]
except IndexError:
res[element] = 0
print(res)
Edited code without enumerate or zip:
list1 = ['cans','Bottles','Boxes','Jugs']
list2 = [1,2,3]
res = {}
i=0
for element in list1:
try:
res[element] = list2[i]
except IndexError:
res[element] = 0
i+=1
print(res)
```
I am trying to sort a large json file with Steam games in descending order based on the value of key: positive_ratings, without using the built in sort() function.
small_example = [
{'id':10,'game':'Counterstrike','positive_ratings':150},
{'id':20,'game':'Bioshock Infinite','positive_ratings':50},
{'id':30,'game':'Rust','positive_ratings':300},
{'id':40,'game':'Portal','positive_ratings':200}
]
The output in descending order would be the following list:
['Rust', 'Portal', 'Counterstrike', 'Bioshock Infinite']
For school we had to make a quick sort function that sorts lists like below. Now i would like to rewrite it so it sorts a list of dictionaries.
def quick_sort(sequence):
length = len(sequence)
if length <= 1:
return sequence
else:
centre = sequence.pop()
items_bigger = []
items_smaller = []
for item in sequence:
if item > centre:
items_bigger.append(item)
else: items_smaller.append(item)
return quick_sort(items_smaller) + [centre] + quick_sort(items_bigger)
print(quick_sort([1,2,5,6,2,10,34,54,23,1]))
In your code, you sort the list based on the element's value. But what you want is sorting list based on element['positive_ratings']. You just need to alter code a little bit:
def quick_sort(sequence):
length = len(sequence)
if length <= 1:
return sequence
else:
centre = sequence.pop()
items_bigger = []
items_smaller = []
for item in sequence:
if item['positive_ratings'] > centre['positive_ratings']: # I changed only this line
items_bigger.append(item)
else: items_smaller.append(item)
return quick_sort(items_smaller) + [centre] + quick_sort(items_bigger)
sort function also works like that, you just specify the key:
some_list.sort(key= lambda x: x['positive_ratings'])
We can adjust your code to look similar to sort function:
def quick_sort(sequence, key = lambda x: x):
length = len(sequence)
if length <= 1:
return sequence
else:
centre = sequence.pop()
items_bigger = []
items_smaller = []
for item in sequence:
if key(item> key(centre): # I changed only this line
items_bigger.append(item)
else: items_smaller.append(item)
return quick_sort(items_smaller, key) + [centre] + quick_sort(items_bigger, key)
You can call it like this:
quick_sort(small_example, key = lambda x: x['positive_ratings'])
Edit: I forgot to add key in the last line. Thanks to #DarrylG I fixed that
you can sort the example, by sorting the data based, based on the key positive_ratings ie sort the postive_ratings values first and then based on that return the output
small_example = [
{'id':10,'game':'Counterstrike','positive_ratings':150},
{'id':20,'game':'Bioshock Infinite','positive_ratings':50},
{'id':30,'game':'Rust','positive_ratings':300},
{'id':40,'game':'Portal','positive_ratings':200}
]
def func(data, key: int):
dic = {}
for i in data:
if i[key] not in dic:
dic[i[key]] = [i]
else:
dic[i[key]].append(i)
dic_key = list(dic.keys())
# sorting the dic_key, sorting data based on postive_raing values, you can
# use any sort algo here
for i in range(len(dic_key)):
for j in range(i+1, len(dic_key)):
if dic_key[i]>dic_key[j]:
dic_key[i], dic_key[j] = dic_key[j], dic_key[i]
result = []
for i in dic_key:
result.extend(dic[i])
return result
sol = func(small_example, 'positive_ratings')
print(solution)
output
[{'id': 20, 'game': 'Bioshock Infinite', 'positive_ratings': 50},
{'id': 10, 'game': 'Counterstrike', 'positive_ratings': 150},
{'id': 40, 'game': 'Portal', 'positive_ratings': 200},
{'id': 30, 'game': 'Rust', 'positive_ratings': 300}]
I'm calculating the average score of people in a dictionary with two-dimensional array and I want to know how to return two people with the same score connected by "and"; EX: name and name
My code:
def bestAverage(inputDict):
dic = {}
for i in inputDict:
if i[0] in dic.keys():
dic[i[0]].append(int(i[1]))
else:
dic[i[0]] = [int(i[1])]
totle_score = 0
print(dic)
for key, value, in dic.items():
for c in value:
totle_score += int(c)
Q = len(value)
avrage = totle_score / Q
dic[key]= [avrage]
print(dic)
My input:
inputDict = [ ["Diane", 20],["Bion",25],["Jack","30"],["Diane","50"] ]
result = bestAverage(inputDict)
OUTCOME:
{'Diane': [35.0], 'Bion': [95.0], 'Jack': [125.0]}
Using the sorted dictionary, you can get the dictionary you want.
Sorry, I think my code is a bit complicated.
dic = {'Diane': [35.0],
'Bion': [95.0],
'Jack': [125.0],
'Diane_2': [35.0],
'Bion_2':[95],
'Diane_3':[35.0],
'John':[10]}
import operator
sorted_dic = sorted(dic.items(), key=operator.itemgetter(0))
new_dic = dict()
preKey = sorted_dic[0][0]
preValue = sorted_dic[0][1]
nms = preKey
for key,value in sorted_dic[1:]:
if(value == preValue):
nms += ' and ' + key
else:
new_dic[nms] = preValue
preKey = key
preValue = value
nms = preKey
new_dic[nms] = preValue
print(new_dic)
OUTCOME:
{'Jack': [125.0], 'John': [10], 'Diane and Diane_2 and Diane_3':
[35.0], 'Bion and Bion_2': [95.0]}
Per the OPs question in the comments, this example now produces a final structure containing entries for only those scores that had multiple people with that same score.
data = {'Diane': [35.0], 'Bion': [95.0], 'Jack': [125.0], 'Sam': [95.0]}
# Here, we create a dict of lists, where the keys are the scores, and the values
# are the names of each person who has that score. This will produce:
#
# {
# 35.0: ['Diane'],
# 95.0: ['Bion', 'Sam'],
# 125.0: ['Jack']
# }
collected = {}
# For each key (name) in the input dict...
for name in data:
# Get the score value out of the array for this name
val = data[name][0]
# If we don't have an entry in our new dict for this score (no key in the dict of that
# score value) then add that entry as the score for the key and an empty array for the value
if val not in collected:
collected[val] = []
# Now that we're sure we have an entry for the score of the name we're processing, add
# the name to the array for that score in the new dict
collected[val].append(name)
# Now we just "flip" each entry in the 'collected' map to create a new dict. We create
# one entry in this dict for each entry in the 'collected' map, where each key is a
# single string where we've combined all of the names with the same score, separated
# by 'and', and each value is the score that those names had.
result = {}
# Now iterate over each of our keys, the unique scores, in our new 'collected' dict...
for val in collected:
# We only want to create an entry in the new dict if the entry we're processing has more than
# just one name in the list of names. So here, we check for that, and skip adding an entry to
# the new dict if there is only one name in the list
if len(collected[val]) == 1:
continue
# Combine the value of this entry, the list of names with a particular score, into a single string
combinedNames = " and ".join(collected[val])
# Add an entry to our 'result' dict with this combined name as the key and the score as the value
result[combinedNames] = val
# Print each combined name string from the resulting structure
for names in result:
print(names)
Output:
Bion and Sam
While iterating in a for loop, I am trying to append a dictionary item's key to a list if the item has a value of 1.
What I have is:
peeps = {'scoobydoo':0, 'shaggy':0, 'scrappydoo':0, 'velma':1, 'freddy':0, 'daphne':1}
ignore_list = []
for peep in peeps:
if peep == 1:
ignore_list.append(peep)
print(ignore_list)
This however does not give me what I would expect:
['velma', 'daphne']
It prints an empty list:
[]
You didn't check for the value, only for the key itself.
Check the value by accessing it:
for peep in peeps:
if peeps[peep] == 1:
ignore_list.append(peep)
or loop over both keys and values together:
for peep, peep_value in peeps.items():
if peep_value == 1:
ignore_list.append(peep)
You can build the list in one step using a list comprehension here:
ignore_list = [peep for peep, peep_value in peeps.items() if peep_value == 1]
You're iterating over keys not values. So you need to combine the key with the actual dictionary to check if the value of that corresponding key is equal to 1 or not.
peeps = {'scoobydoo':0, 'shaggy':0, 'scrappydoo':0, 'velma':1, 'freddy':0, 'daphne':1}
ignore_list = []
for peep in peeps:
if peeps[peep] == 1:
ignore_list.append(peep)
print(ignore_list)
OR
peeps = {'scoobydoo':0, 'shaggy':0, 'scrappydoo':0, 'velma':1, 'freddy':0, 'daphne':1}
print([key for key,value in peeps.items() if value == 1])
You can iterate through the keys and values of the dictionary to accomplish what you want:
peeps = {'scoobydoo':0, 'shaggy':0, 'scrappydoo':0, 'velma':1, 'freddy':0, 'daphne':1}
ignore_list = []
for key, value in peeps.items():
if value == 1:
ignore_list.append(key)
print(ignore_list)