Problem with comparing two items in a list of lists - python

I have this list
zipped_values = [(3.0, 4.242640687119285), (3.605551275463989, 3.1622776601683795), (5.0, 3.1622776601683795), (4.123105625617661, 4.47213595499958), (5.0, 4.0), (5.830951894845301, 7.810249675906654), (5.0990195135927845, 5.385164807134504), (7.0710678118654755, 8.06225774829855), (7.0710678118654755, 7.280109889280518), (8.06225774829855, 8.246211251235321)]
what I am trying to do is compare each item within the lists to each other (within the same list), to find out what the minimum is. In the first case, it would be 3.0, in the second, it would be 3.1.
Now what I am trying to do is, if the minimum is the first element, assign that element (3.0) to a dictionary key named M1, and if the minimum is the second element, assign that element to a dictionary key named M2.
This is what I've come up with:
for jk in zipped_value:
for n in jk:
if zipped_value[0][n] < zipped_value[0][n+1]:
dictionary["M1"].append(zipped_value[0][n])
But it gives me this error: TypeError: tuple indices must be integers or slices, not float
What do I do?

You don't need the inner loop. jk is the tuple, you just need to compare jk[0] with jk[1]. You can simplify this by unpacking to two variables when looping.
for a, b in zipped_values:
if a < b:
dictionary["M1"].append(a)
else:
dictionary["M2"].append(b)

Your inner for loop is iterating over the tuple, so the value of n is actually the floats in your tuple. Additionally, you will have problems with the append statement since it does not seem like you are initializing the dictionary values to be list type. Lastly, python allows you to unpack your tuples as you are iterative over them, making the code easier to read and comprehend rather than needing to use indices.
Try this:
from collections import defaultdict
dictionary = defaultdict(list)
for item1, item2 in zipped_value:
if item1 < item2:
dictionary["M1"].append(item1)
else:
dictionary["M2"].append(item2)

You are getting this error "TypeError: tuple indices must be integers or slices, not float" because in the
"for n in jk" the 'n' here is actually representing the float values in tuples and is not the index of tuple.
So,
if zipped_value[0][n] < zipped_value[0][n+1]:
dictionary["M1"].append(zipped_value[0][n])
is not correct indexing to access elements of tuples in a list.
You can modify your code to something below to get correct results:
for jk in zipped_values:
if jk[0] < jk[1]:
dictionary["M1"].append(jk[0])
else:
dictionary["M2"].append(jk[1])

Related

Summing using Inline for loop vs normal for loop

I'm trying to sum a list named mpg with the entry 'cty' (converted from a dictionary).
Sample data:
[{'': '1', 'trans': 'auto(l5)', 'drv': 'f', 'cty': '18'}, {'': '2', 'trans': 'manual(m5)', 'drv': 'f', 'cty': '21'}]
I tried 2 ways of doing this:
This gives the error that float object is not iterable.
for d in mpg:
sum(float(d['cty']))
No problem with this one.
sum(float(d['cty']) for d in mpg)
I understand that float objects are not iterable but isn't the 2nd method just an example of list comprehension of the 1st one?
Why does the second option work but not the first?
sum() takes an iterable as an argument and sums all items of that iterable. A simple float or integer is not a list and therefore not iterable.
In example 1, you iterate through each item of your list of dictionaries, but then only pass a single float (the float value of the current dictionary) to your function, resulting in sum(123), which then returns an error.
In example 2, you first iterate through your whole list of dictionaries and extract the values you need into a new list. If you stored float(d['cty']) for d in mpg in a new variable, it would create a list. If you now pass that list, the function results in sum([123, 456, 789]), which returns the desired value.
The second one works because the list comprehension constructs a list prior to trying to evaluate the sum, but the first way tries to pass float(d['cty']) to the sum. But that's just a float rather than an iterable (which is what sum needs). See this modification of the first way:
lst = []
for d in mpg:
lst.append(float(d['cty']))
sum(lst)
Two ways to solve the problem:
1.
i = 0
for d in mpg:
i += float(d['cty'])
x = sum([float(d['cty']) for d in mpg])

Nested tuples within lists

I have a list of lists of tuples and am having trouble accessing the values within the tuples.
Note: apologies for the basic nature of this query, but I'm a beginner and it takes me a long time to access simple variables.
E.g:
[[('foo', '-1')],[('bar', '-5'),('baz', '+7')], [('qux', '+9')]]
I want to 1) remove the second value of each tuple i.e. the numbers and 2) remove the tuple type and just convert it a list of strings.
As you can see, it is a list of tuples so it can be one tuple or a number of tuples based on the content of extraction - but it is always 2 values within each tuple and I want to remove the second value.
I am having trouble 1) converting each tuple to a string, to be able to 2) remove the second value (preferably I want to remove that before making it into a string) - any ideas?
Just get 0 index of each tuple by iterating in list
ll_tuple = [[('foo', '-1')],[('bar', '-5'),('baz', '+7')], [('qux', '+9')]]
print(
[
[tuple_[0] for tuple_ in l_tuple]
for l_tuple in ll_tuple
]
)
I don't understand very well the question but two points:
Your values in tuple are already string.
To access tuple, you can iterate over your list and access first value of tuple by doing this:
tuple[0]
I don't understand if you have a list of list of tuple, or a list of tuple
First of all your list of lists of tubles is incorrectly formatted I assume what you mean:
data = [
[('foo', '-1')],
[('bar', '-5')],
[('baz', '+7'), ('qux', '+9')]
]
When create a nested for loop and append the first element in each tuble to new list output.
output = []
for lst in data:
for tub in lst:
output.append(tub[0])
print(output)
Prints:
['foo', 'bar', 'baz', 'qux']

How to use hashed values as an Index in Python

I want to use three lists as a index for a table in Python. To do so I decided to hash the lists to a int, because you can not use lists as an index.
The Problem is that the hashed vaule is a number like: -103692953590217654
This can not be used as an index as well.
How can I turn this high int into a smaller number, so that it is usabel for a index of a table?
I need this solution to fill a q-table for a reinforcement learning framework. My state is definded with three lists.
IndexError: list index out of range
Tuples are hashable, and sounds like you should be using them for your case.
As an arbitrary example:
a = (1,2)
b = (3,4)
q_learning_dict = {}
q_learning_dict[(a, b)] = 0.1
To convert your lists to tuples, you can simply pass them to the tuple() function like tuple([1,2,3]).
Warning: Tuples are IMMUTABLE. This means that you cannot change their content after you initialize them (which is also what makes them hashable).
Hashing a list doesn't make sense because you can change the contents of the list or append/remove values to/from it, which would render your previous hash invalid.

summing dict value of list to single integer

I am trying to do something pretty simple but cant seem to get it. I have a dictionary where the value is a list. I am trying to just sum the list and assign the value back to the same key as an int. Using the code below the first line doesn't do anything, the second as it says puts the value back but in a list. All other things ive tried has given me an error can only assign iterable. As far as i know iterables are anything that can be iterated on such as list and not int. Why can I only use iterable and how can i fix this issue ? The dict im using is here (https://gist.github.com/ishikawa-rei/53c100449605e370ef66f1c06f15b62e)
for i in dict.values():
i = sum(i)
#i[:] = [sum(i) / 3600] # puts answer into dict but as a list
You can use simple dictionary comprehension if your dict values are all lists
{k:sum(v) for k, v in dict.items()}
for i in dikt.keys():
dickt[i] = sum(dict[i]))
btw, dict is a type. best not to use it as a variable name

Loop through a list in Python using enumerate and openpyxl

New Python convert here. Simply, trying to loop through a list in Python using openpyxl. Of course, my list has about 100 items and my code has more conditions.
lst = ['1','2','a','a12']
for value in enumerate(lst):
row = ws1.iter_rows(min_row=value,max_row=value)
When I try without enumerate I get error "must be str, not int" and when I try with enumerate I get error "Can only concatenate tuple (not "int") to tuple".
I believe it has something to do with min_row and max_row requiring an int, but even then I get "'int' object is not iterable". Also, tried making value str() and int()
Any advice much appreciated, thank you.
When you wrap an iterable with enumerate, you get two values:
the index of enumeration
the value of the iterable at that index
That pair is emitted from enumerate() as a tuple.
You're only identifying one variable name, though, so value contains the whole tuple,
i.e. value = (i, current_val_of_lst).
Instead, try:
lst = ['1','2','a','a12']
for i, value in enumerate(lst):
# i is the enumeration index
# value is the entry in list
...

Categories

Resources