[Python-3000] Iterables and scalars was: sets in P3K?
Raymond Hettinger
rhettinger at ewtllc.com
Wed Apr 26 20:07:39 CEST 2006
Edward Loper wrote:
>I think that a significant motivation for people that propose set
>literals is that the following is just plain ugly:
>
> s = set([1,2,3])
>
>It seems much more natural to write:
>
> s = set(1, 2, 3)
>
>However, it is fairly common to want to build a set from a collection,
>an iterator, or a genexp. With the current notation, all three of these
>are easy. But with this "more natural" notation, they're no longer
>possible without resorting to varargs (which would create an unnecessary
>imtermediary tuple). I.e., we don't want to lose the ability to do any
>of the following:
>
> s = set(my_list)
> s = set(enumerate(my_list))
> s = set(x for x in collection if x>10)
>
>One way around this conflict might be to define a new factory function,
>that generates a set from an iterable. I.e., something like:
>
> s = set.from_iter(my_list)
> s = set.from_iter(enumerate(my_list))
> s = set.from_iter(x for x in collection if x>10)
>
>
We're no longer talking about an issue unique to the set and frozenset
datatypes. Many elements of the language are challenged by conflicting
desires for a function or type choose between taking an iterable
argument or to have them already unwound.
IMO, the worst solution is trying to accommodate both within a single
callable. The problematic %-formatting operator is one example. The
min() and max() functions are another:
>>> min(3,4,5)
3
>>> min([3,4,5])
3
The current solution for sets is to provide only the iterable form and
to require the user to create a list when he/she wants to write-out a
literal: set([1,2,3]). The advantage of this approach is that it has a
small footprint in terms of human memory because it takes advantage of
pre-existing knowledge about how to write list literals and because it
doesn't double the number of forms for every function and type.
Edward's solution is to provide an alternate classmethod or factory
function. IMO, this doesn't solve the general problem unless it is
applied throughout the language:
list(1)
list.from_iter([1])
tuple(1)
tuple.from_iter([1])
set(1)
set.from_iter([1])
If those examples make your stomach churn, then let's not go down the
path of adding all these classmethods and factory functions. The
existing approach using list literals is dirt simple and universally
applicable. While writing set([1,2,3]) is not a perfect solution, it is
much less complex than non-generalizable alternatives involving
classmethods, factory functions, or punctuation.
Raymond
More information about the Python-3000
mailing list