On 20/02/2021 20.25, Wolfgang Stöcher wrote: > Having a dict like > d = {'one': 1, 'two': 2} > the representation of its keys > repr(d.keys()) > gives > "dict_keys(['one', 'two'])" > > But since the keys are unique, wouldn't a representation using the set > notation > be more intuitive, i.e. what about changing the output of > dict_keys.__repr__ to > "dict_keys({'one', 'two'})" > (using curly braces instead of brackets)
When considering the data-returned, the logic of formatting as a set makes sense. So, why did the Python-gods decide otherwise? Let's start by asking what it actually is: >>> d = {'one': 1, 'two': 2} >>> repr(d.keys()) "dict_keys(['one', 'two'])" >>> k = d.keys() >>> type( k ) <class 'dict_keys'> So, the output is not a set (as you say) but nor (as apparently-indicated by the square-brackets) is it actually a list! Not much help there, then. So, let's use help() to see if that helps, hah! (long listing, so not reproduced here). No joy there either. Is it actually one of our 'standard' collections at all? >>> k is dict False >>> k is list False >>> k is set False >>> k is tuple False OK, that makes reasonable sense. Perhaps dict_keys are a sub-class then? >>> isinstance( k, dict ) False >>> isinstance( k, list ) False >>> isinstance( k, set ) False >>> isinstance( k, tuple ) False Still going 'nowhere' fast! It is (apparently) reported as a list, and we'd like to think of it as a set. So, compare help() output with the attributes of list and set (and/or other collections). There are considerable differences (again, not reproduced here due to length). However, still not revealing any answers! If we de-construct the data contained in a dictionary, then as well as the keys, we should consider the values: >>> d {'one': 1, 'two': 2} >>> k = d.keys() >>> k dict_keys(['one', 'two']) >>> v = d.values() >>> v dict_values([1, 2]) Hah, they are (apparently) considered a list as well, but have another distinct type/are another custom-object. Still not making progress though! We've looked at the data/the output and found nothing much! Now, let's totally invert our view of the matter: Instead of deconstructing the original dictionary, consider the purpose of repr()? <<<built-in function to compute the “official” string representation of an object.>>> #repr Thus, we should be able to take the output of repr() and re-create the original object. Because a dictionary consists of key-value pairs, we will need both 'sets' of components: >>> new_d = dict( zip( k, v ) ) >>> new_d {'one': 1, 'two': 2} Ahah! Now, we realise that whereas a list-like #list data structure maintains the sequence of its elements, a set #set is not required to do so. Thus, if "k" were a set, what is produced on your machine may be different to what happens on mine/no guarantees: Possibly @Wolfgang's machine = >>> k { 'one', 'two' } Possibly @dn's machine = >>> k { 'two', 'one' } Thus no guarantee that when we try to re-combine keys and values they would correspond correctly! - and if we applied the same to data - even worse: combinatorial issue! Web.Refs: #repr: https://docs.python.org/3/reference/datamodel.html#basic-customization #list: and #set: https://docs.python.org/3/reference/datamodel.html#the-standard-type-hierarchy -- Regards, =dn -- https://mail.python.org/mailman/listinfo/python-list