This is well explained in the documentation :
The assignment operator evaluates the list of expressions (remember that this can be a single expression or a comma-delimited list, the last of which has a tuple), and assigns a single result object for each target list, from left to right .
(my emphasis)
If the term target_list used in the grammar as follows:
assignment_stmt ::= (target_list "=")+ (expression_list | yield_expression)
(Pay attention to the + sign after the first bracket - this allows you to assign a chain)
Thus, the resulting semantics:
target_list1 = target_list2 = expression
is equivalent to:
target_list1 = expression target_list2 = expression
It is not possible to mislead what is assigned (evaluates the list of expressions) with what the purpose of the assignment is, because assignment is an expression, not an expression. Therefore, all c = in it will not be considered as an expression - only the right side. Then all assignment operators will be processed from left to right (i.e., their target lists will have an assigned expression value).
source share