Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Concatenation using the + and += operators in Python [duplicate]

Recently, I have noticed an inconsistency while concatenating lists.

So if I use the + operator, it doesn't concatenates list with any object of different type. For example,

l = [1,2,3]
l = l + (4,5)        #TypeError: can only concatenate list (not "tuple") to list

But, if I use the += operator, it neglects the type of the object. For example,

l = [1,2,3]
l += "he"            #Here, l becomes [1, 2, 3,"h", "e"]

l += (56, 67)        #Here, l becomes [1, 2, 3,"h", "e", 56, 67]

So, is it just the semantics of the language or some other reason?

like image 476
Perspicacious Avatar asked Jul 14 '19 08:07

Perspicacious


People also ask

What is concatenation and replication in Python?

In python, concatenations and repetitions are supported by sequence data types both mutable(list) and immutable(tuple, strings). Sequence types like range objects do not support concatenation and repetition.

What operators are used for string concatenation and repetition?

Again, as with strings, the + operator concatenates lists. Similarly, the * operator repeats the items in a list a given number of times. It is important to see that these operators create new lists from the elements of the operand lists.

Which operator is used for concatenation in Python?

Using '+' operator Two strings can be concatenated in Python by simply using the '+' operator between them. More than two strings can be concatenated using '+' operator.

What are concatenation and replication operators?

The concatenation operator "{ , }" combines (concatenates) the bits of two or more data objects. The objects may be scalar (single bit) or vectored (muliple bit). Mutiple concatenations may be performed with a constant prefix and is known as replication.


1 Answers

The basic idea is that the + and the += operators are not necessarily the same operation in Python, and they are indeed different for lists. The + operation is carried out by the __add__ magic method while the += operation is carried out by the __iadd__ (in-place add) magic method. These magic methods come from the type on the left of the operator.

The in-place adding for a list does not require a list on the right-hand side, just an iterable. The items are then taken one-by-one from the iterable and appended to the list. This is similar to the list's extend method. So the += operator does not neglect the type of the object on the right, it just extends the possible types that can be used.

This behavior is somewhat confusing--it must be since you are the second person in two days I have seen ask a similar (but not duplicate) question on this issue. However, this behavior is convenient--we now have an easy way to combine a list with any iterable.

For more on this, see Why do Python lists let you += a tuple, when you can’t + a tuple?.


As @khelwood's comment states, the resulting type for a += b is obvious: the type of a. So the type of b can be flexible. The resulting type of a + b is not obvious. Python is a strictly-typed language and hates such ambiguity. The Zen of Python states

Explicit is better than implicit.

and

In the face of ambiguity, refuse the temptation to guess.

and

Although practicality beats purity.

So the current behavior fits Python's Zen pretty well. I note that there is nothing in the Zen about consistency.

like image 155
Rory Daulton Avatar answered Sep 20 '22 07:09

Rory Daulton