11 ms·
INADA Naoki's argument [1] is succinct and insightful. I feel zero value of non abelian group should not mean False in bool context. () + () == () ""
by clarkevans 13y ago
INADA Naoki's argument [1] is succinct and insightful.
I feel zero value of non abelian group should not mean
False in bool context.
() + () == ()
"" + "" == ""
0 + 0 == 0
timedelta() + timedelta() == timedelta()
time() + time() => TypeError
[1] https://mail.python.org/pipermail/python-ideas/2014-March/026674.html https://mail.python.org/pipermail/python-ideas/2014-March/02...
- barakm 13y agoCame here to say this. It's the most useful statement in the entire thread of "you're wrong!" "no, you're wrong!" and nobody noticed.
- deleted 13y ago[deleted]
- dalke 13y agoPerhaps people ignored it because it isn't true? {}+{} fails, because addition of dictionaries is non-abelian and Python refuses to choose a preferred result. But bool({}) is perfectly reasonable.
- maxiepoo 13y agoAbelian group is a sort of stringent requirement, they probably just mean a plain monoid? After all it works for python lists, which form a non-commutative monoid: [] + [] == [] [1,2] + [3] != [3] + [1,2]
- jessaustin 13y agoThe additional property which makes a monoid a group is the existence of inverse elements. So list is a good example for your point, because there are no "inverse lists".
- raverbashing 13y agoAnd this is why programmers who know math are better programmers.
- pekk 13y agoAdding times is semantic nonsense. It's irrelevant how this relates to Abelian monoids. Mathematically beautiful form is not a virtue if it just creates bizarre and confusing interfaces. edit: last Tuesday, 5:00pm + Christmas two years ago at noon = ???
- baddox 13y agoAn ironic comment, considering that appears to me to be a misuse of "abelian group." Abelian groups are those whose group operation is commutative, which has nothing to do with the code examples provided.
- StefanKarpinski 13y agoThis is a nice clean criterion, but it's still pretty unclear to me why the zero element of a monoid should be considered falsey at all.
- chrismonsanto 13y agoBecause when writing a recursive function, the zero element is generally the base case. if x: <destructure x, recurse on subparts> else: return <something> This applies to (natural) numbers as well--'destructuring' usually means decrementing the number.
- dalke 13y agoIf that were true, it would mean that dict should not support bool: >>> {} + {} Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: unsupported operand type(s) for +: 'dict' and 'dict' >>> bool({}) False Since I find bool(a_dict) to be very useful, and the lack of a_dict+b_dict to be reasonable (precisely because it's non-abelian!), I conclude that logic is cute, but not that relevant. Those who think it this argument is pursuasive, should bool({}) raise an exception? Or should {1:"A"}+{1:"B"} not raise an exception and instead return ... what? Or do I misunderstand something?
- mctx 13y ago{1: ["A", "B"]}?
- cuttle 13y agoVery little code that expects "A" or "B" would be equipped to handle ["A","B"].
- dalke 13y agoOkay, then what about {1: "A"} + {} Should that return {1: ["A"]}? In which case {} is no longer a zero value. What about {1: "A"} + {} + {1: "B", 2: "Z"} + {1: "C"} + {} In any case, your suggestion would break all existing code. Based on all the StackOverflow and python-list questions, most people expect one or the other value, and few want the two-element list containing both. (And why a list instead of a tuple?) Guido chose the current behavior because there is no clear-cut winner. "Refuse the temptation to guess."
- aiiane 13y agoHow does {1:"A"}+{} = {1:"A"} imply that {} is no longer a zero value? 1+0=1 makes total sense...
- dalke 13y agoIt's not just that one expression, but when done in addition to the previous suggested answer. That is, what is the type of the values in the summed dictionaries? If {1:"A"}+{} == {1:"A"} then the type of each value is unchanged from the input list. If {1:"A"}+{1:"B"} == {1:["A","B"]} then the type of each value (or at least each shared value) is a 2-element list. If both are true, then no one can write sane code which knows how deal with the sum of two dictionaries. That is, the insane code has to have checks for if one of the dictionaries is empty, and if so, do one thing, otherwise do another thing. In which case, why is this definition useful? Therefore, either {} is the zero value, or dictionary summation produces lists for the resulting values, but not both.
- davidcuddeback 13y agoI just tried this: $ python >>> import time, datetime >>> () + () () >>> "" + "" '' >>> 0 + 0 0 >>> datetime.timedelta() + datetime.timedelta() datetime.timedelta(0) >>> time.time() + time.time() 27848327051.323207 Seems like time() + time() is not a TypeError in Python.
- Aramgutang 13y agoWrong time(), you want datetime.time(). time.time() returns the seconds elapsed since the epoch.
- pekk 13y agoIt doesn't make sense that times should be added at all.
- baddox 13y agoWhat do those code samples have anything to do with abelian groups? Abelian groups are those whose group operator is commutative, i.e. a + b = b + a for all a and b. The code examples seem to be referring to the existence of an identity element, which is necessary for all groups.
- moomin 13y agoI think what he was saying was: * You should use + only for operations that form an abelian group across the domain * In those cases, it makes sense for the identity to be false. The truth is, time doesn't have a sensible addition/combination operator, never mind an identity and inverse, so it isn't even a group.
- baddox 13y agoOkay, I definitely buy that. It makes sense to add a duration (timedelta in Python) to a time, but not to add times to one another. This is venturing off topic, but if you really wanted to, you could define addition for times in terms of timedeltas. It makes sense to subtract times and get a timedelta, so you could define addition as the subtraction with signed times and signed timedeltas. So, since `time(today) - time(yesterday) = timedelta(1 day)`, we could say that `time(today) + time(yesterday) = -timedelta(1 day)` and `time(today) - -time(yesterday) = timedelta(1 day)`. It's a bit strange to define the notion of a signed time object, but it could work.
- k2enemy 13y agoYeah, I was trying to figure that out too. They seem to care about closure and identity, but most of the examples have operators that trivially break an Abelian group's commutative requirement.
- bjourne 13y agoBut you can make an equally succinct argument in the opposite direction, namely to treat time values as polar coordinates. Then they indeed form an abelian group: a + 0:00 = a 15:00 + 13:00 = 02:00 12:00 + 12:00 = 00:00 The examples are for hours only, but you can extend it for minutes too. Showing that time values on a clock forms an abelian group under addition is a textbook example everyone uses when introducing group theory.
- mooism2 13y agoBut it's wrong. I'll assume the times you gave were in the UK's timezone. Here they are rewritten to use Germany's timezone. a + 1:00 = a 16:00 + 14:00 = 03:00 13:00 + 13:00 = 01:00 Still think this makes sense? Time deltas? Then you don't have the timezone or epoch problem. Works fine. But time stamps? You can't add two time stamps and get a sensible answer. Time stamps form a torsor, not a group: http://math.ucr.edu/home/baez/torsors.html http://math.ucr.edu/home/baez/torsors.html
- bjourne 13y agoYou're right, but time values with timezones are completely different types from time values without. They follow different rules and need to be treated differently.