Update Python Dictionary with Tuple of Strings to set (key, value) fails - python

dict.update([other]) says
Update the dictionary with the key/value pairs from other, overwriting existing keys. Return None.
update() accepts either another dictionary object or an iterable of key/value pairs (as tuples or other iterables of length two). If keyword arguments are specified, the dictionary is then updated with those key/value pairs: d.update(red=1, blue=2).
But
>>> {}.update( ("key", "value") )
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: dictionary update sequence element #0 has length 3; 2 is required
So why does Python apparently try to use the first string of the tuple?

The argument needs to be an iterable of tuples (or other iterables of length two), e.g. a list
>>> d = {}
>>> d.update([("key", "value")])
>>> d
{'key': 'value'}
or a tuple, however this fails:
>>> d = {}
>>> d.update((("key", "value")))
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: dictionary update sequence element #0 has length 3; 2 is required
The Python documentation on tuple again solves this mystery:
Note that it is actually the comma which makes a tuple, not the parentheses. The parentheses are optional, except in the empty tuple case, or when they are needed to avoid syntactic ambiguity.
I.e. (None) is not a tuple at all, but (None,) is:
>>> type( (None,) )
<class 'tuple'>
So this works:
>>> d = {}
>>> d.update((("key", "value"),))
>>> d
{'key': 'value'}
>>>
You can't omit the parentheses because
>>> d = {}
>>> d.update(("key", "value"),)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: dictionary update sequence element #0 has length 3; 2 is required
that would be said syntactic ambiguity (comma is function argument separator).

Related

What does Tuple[Hashable] mean in Python?

I came across the following piece of code:
def func(self, v: Tuple[Hashable]):
...
I know v: Tuple would mean variable v must be of type Tuple, but what does Tuple[Hashable] mean? Isn't a tuple in Python always hashable?
A tuple is only hashable if the values in the tuple are hashable themselves.
>>> hash((1,2))
-3550055125485641917
>>> hash(([1],2))
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: unhashable type: 'list'

IndexError: list index out of range python 3.4

Trying to run this code :
sorted_by_name = sorted(sort_array,key=lambda x:x[0]))
I get:
IndexError: list index out of range
How do I resolve this?
Thanks
Well one of element in the sort_array should be either empty or null string. See the below examples
Example #1:
sort_array = ['abc', 'acd', 'abcd', '']
sort_array
['abc', 'acd', 'abcd', '']
sorted(sort_array, key=lambda student: student[0])
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 1, in <lambda>
IndexError: string index out of range
For example #2, i will take sort_array as list of lists, which matches more to your example of sorted_by_name
>>> student_tuples = [
... ['john', 'A', 15],
... []
... ]
>>> sorted_by_name = sorted(student_tuples,key=lambda x:x[0])
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 1, in <lambda>
IndexError: list index out of range
Hence I request you to please check your input sort_array once, if it has any empty lists
That means that at least one thing in your list is empty so doesn't have a first element. The fix is simple, don't pass a key:
sorted_by_name = sorted(sort_array)
The default implementation of sorted already tries the first item, then the second item, the third item, etc. When you pass it a key, it first tries your key, the first item. If it finds that two are the same, it does its own check. It checks the first item (again), the second item, the third item, etc. In other words, both are the same except that supplying a key might mean that the first item is checked twice, and of course the default implementation doesn't error on an empty list.

Python how to combine a string and list to a tuple

I have a string and a list
a=100
b=["abc","def"]
How do I combine these to a tuple, that looks like (abc, 100), (def, 100)? I tried
>>> for i in file:
... tuple(file, uid)
...
Traceback (most recent call last):
File "<stdin>", line 2, in <module>
TypeError: tuple() takes at most 1 argument (2 given)
a=100
b=["abc","def"]
print [(i,a) for i in b]
You can do this through simple list comprehension
as the traceback said, tuple takes 1 argument, in your code, just change tuple(file, uid) to tuple([file, uid]). That is to say, tuple takes one argument which is iterable

Combine single and multi argument variables in a function call for Python

I wrote the following function to return a subset of a dictionary but want to insist on having at least one key provided in the input arguments.
def getProperty(self,x, *key):
key = [k for k in key]
key.insert(0,x)
return {k:self.__properties[k] for k in key if k in self.__properties}
The code works.
I know the insert is not really necessary since dictionary elements aren't ordered. What I really wish I could do is to get rid of the first for-loop that creates a list by extracting elements from the multi-argument tuple.
Something like
key = [x] + [key]
but it does not work.
This should do what you need:
def getProperty(self,x, *key):
key = (x,)+key
return {k:self.__properties[k] for k in key if k in self.__properties}
If you want to insist on there being at least one argument then you should assert that the args tuple is not empty
>>> def get_property(*args):
... assert (args != ()), "There must be at least one argument"
... print(args)
...
>>> get_property('a')
('a',)
>>> get_property('a', 'b')
('a', 'b')
>>> get_property()
Traceback (most recent call last):
File "<stdin>", line 1, in ?
File "<stdin>", line 2, in get_property
AssertionError: There must be at least one argument
>>>
There's no need, then, to do anything fancy to provide one separate argument when you call the method and you can catch the AssertionError in the calling statement if required.

TypeError: zip argument #1 must support iteration

for k,v in targets.iteritems():
price= str(v['stockprice'])
Bids = str(u''.join(v['OtherBids']))
Bids = Bids.split(',')
# create a list of unique bids by ranking
for a, b in zip(float(price), Bids):
try:
del b[next(i for i, e in enumerate(b) if format(e, '.4f') == a)]
except StopIteration:
pass
I am extracting data from my dictionary but it seems that all of them are in unicode. How may I get rid of the unicode nonsense?
I take it your code is giving you the error message, TypeError: zip argument #1 must support iteration. You are getting this error due to the expression zip(float(price), Bids). This simplified code demonstrates the error:
>>> price = str(u'12.3456')
>>> bids = ['1.0', '2.0']
>>> zip(float(price), bids)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: zip argument #1 must support iteration
The Python 2.x zip() built-in library function requires all its arguments to be iterables. float(price) is not an iterable.
If you want to make tuples combining float(price) with each element of the array Bids, you can use itertools.repeat() in the first argument expression.
>>> import itertools
>>> price = str(u'12.3456')
>>> bids = ['1.0', '2.0']
>>> zip(itertools.repeat(float(price),len(bids)), bids)
[(12.345599999999999, '1.0'), (12.345599999999999, '2.0')]
I don't see that your use of Unicode data types has anything to do with the TypeError.

Categories

Resources