Hướng dẫn chaining operators in python

Checking more than two conditions is very common in Programming Languages. Let’s say we want to check the below condition:

a < b < c

The most common syntax to do it is as follows:

if a < b and b < c :
   {...}

In Python, there is a better way to write this using Comparison operator Chaining. The chaining of operators can be written as follows:

if a < b < c :
    {.....}

According to associativity and precedence in Python, all comparison operations in Python have the same priority, which is lower than that of any arithmetic, shifting, or bitwise operation. Also unlike C, expressions like a < b < c have the interpretation that is conventional in mathematics. List of comparison operators in Python:

">" | "=" | ">> def f[a, b]:
...     print[a, b]
...
>>> f[b=1, *[2,]]
2 1
>>> f[a=1, *[2,]]
Traceback [most recent call last]:
  File "", line 1, in 
TypeError: f[] got multiple values for keyword argument 'a'
>>> f[1, *[2,]]
1 2

It is unusual for both keyword arguments and the *expression syntax to be used in the same call, so in practice this confusion does not arise.

If the syntax **expression appears in the function call, expression must evaluate to a mapping, the contents of which are treated as additional keyword arguments. If a keyword is already present [as an explicit keyword argument, or from another unpacking], a TypeError exception is raised.

Formal parameters using the syntax *identifier or **identifier cannot be used as positional argument slots or as keyword argument names.

Changed in version 3.5: Function calls accept any number of * and ** unpackings, positional arguments may follow iterable unpackings [*], and keyword arguments may follow dictionary unpackings [**]. Originally proposed by PEP 448.

A call always returns some value, possibly None, unless it raises an exception. How this value is computed depends on the type of the callable object.

If it is—

a user-defined function:

The code block for the function is executed, passing it the argument list. The first thing the code block will do is bind the formal parameters to the arguments; this is described in section Function definitions. When the code block executes a return statement, this specifies the return value of the function call.

a built-in function or method:

The result is up to the interpreter; see Built-in Functions for the descriptions of built-in functions and methods.

a class object:

A new instance of that class is returned.

a class instance method:

The corresponding user-defined function is called, with an argument list that is one longer than the argument list of the call: the instance becomes the first argument.

a class instance:

The class must define a __call__[] method; the effect is then the same as if that method was called.

6.4. Await expression¶

Suspend the execution of coroutine on an awaitable object. Can only be used inside a coroutine function.

await_expr ::=  "await" primary

New in version 3.5.

6.5. The power operator¶

The power operator binds more tightly than unary operators on its left; it binds less tightly than unary operators on its right. The syntax is:

power ::=  [await_expr | primary] ["**" u_expr]

Thus, in an unparenthesized sequence of power and unary operators, the operators are evaluated from right to left [this does not constrain the evaluation order for the operands]: -1**2 results in -1.

The power operator has the same semantics as the built-in pow[] function, when called with two arguments: it yields its left argument raised to the power of its right argument. The numeric arguments are first converted to a common type, and the result is of that type.

For int operands, the result has the same type as the operands unless the second argument is negative; in that case, all arguments are converted to float and a float result is delivered. For example, 10**2 returns 100, but 10**-2 returns 0.01.

Raising 0.0 to a negative power results in a ZeroDivisionError. Raising a negative number to a fractional power results in a complex number. [In earlier versions it raised a ValueError.]

This operation can be customized using the special __pow__[] method.

6.6. Unary arithmetic and bitwise operations¶

All unary arithmetic and bitwise operations have the same priority:

u_expr ::=  power | "-" u_expr | "+" u_expr | "~" u_expr

The unary - [minus] operator yields the negation of its numeric argument; the operation can be overridden with the __neg__[] special method.

The unary + [plus] operator yields its numeric argument unchanged; the operation can be overridden with the __pos__[] special method.

The unary ~ [invert] operator yields the bitwise inversion of its integer argument. The bitwise inversion of x is defined as -[x+1]. It only applies to integral numbers or to custom objects that override the __invert__[] special method.

In all three cases, if the argument does not have the proper type, a TypeError exception is raised.

6.7. Binary arithmetic operations¶

The binary arithmetic operations have the conventional priority levels. Note that some of these operations also apply to certain non-numeric types. Apart from the power operator, there are only two levels, one for multiplicative operators and one for additive operators:

m_expr ::=  u_expr | m_expr "*" u_expr | m_expr "@" m_expr |
            m_expr "//" u_expr | m_expr "/" u_expr |
            m_expr "%" u_expr
a_expr ::=  m_expr | a_expr "+" m_expr | a_expr "-" m_expr

The * [multiplication] operator yields the product of its arguments. The arguments must either both be numbers, or one argument must be an integer and the other must be a sequence. In the former case, the numbers are converted to a common type and then multiplied together. In the latter case, sequence repetition is performed; a negative repetition factor yields an empty sequence.

This operation can be customized using the special __mul__[] and __rmul__[] methods.

The @ [at] operator is intended to be used for matrix multiplication. No builtin Python types implement this operator.

New in version 3.5.

The / [division] and // [floor division] operators yield the quotient of their arguments. The numeric arguments are first converted to a common type. Division of integers yields a float, while floor division of integers results in an integer; the result is that of mathematical division with the ‘floor’ function applied to the result. Division by zero raises the ZeroDivisionError exception.

This operation can be customized using the special __truediv__[] and __floordiv__[] methods.

The % [modulo] operator yields the remainder from the division of the first argument by the second. The numeric arguments are first converted to a common type. A zero right argument raises the ZeroDivisionError exception. The arguments may be floating point numbers, e.g., 3.14%0.7 equals 0.34 [since 3.14 equals 4*0.7 + 0.34.] The modulo operator always yields a result with the same sign as its second operand [or zero]; the absolute value of the result is strictly smaller than the absolute value of the second operand 1.

The floor division and modulo operators are connected by the following identity: x == [x//y]*y + [x%y]. Floor division and modulo are also connected with the built-in function divmod[]: divmod[x, y] == [x//y, x%y]. 2.

In addition to performing the modulo operation on numbers, the % operator is also overloaded by string objects to perform old-style string formatting [also known as interpolation]. The syntax for string formatting is described in the Python Library Reference, section printf-style String Formatting.

The modulo operation can be customized using the special __mod__[] method.

The floor division operator, the modulo operator, and the divmod[] function are not defined for complex numbers. Instead, convert to a floating point number using the abs[] function if appropriate.

The + [addition] operator yields the sum of its arguments. The arguments must either both be numbers or both be sequences of the same type. In the former case, the numbers are converted to a common type and then added together. In the latter case, the sequences are concatenated.

This operation can be customized using the special __add__[] and __radd__[] methods.

The - [subtraction] operator yields the difference of its arguments. The numeric arguments are first converted to a common type.

This operation can be customized using the special __sub__[] method.

6.8. Shifting operations¶

The shifting operations have lower priority than the arithmetic operations:

shift_expr ::=  a_expr | shift_expr [""] a_expr

These operators accept integers as arguments. They shift the first argument to the left or right by the number of bits given by the second argument.

This operation can be customized using the special __lshift__[] and __rshift__[] methods.

A right shift by n bits is defined as floor division by pow[2,n]. A left shift by n bits is defined as multiplication with pow[2,n].

6.9. Binary bitwise operations¶

Each of the three bitwise operations has a different priority level:

and_expr ::=  shift_expr | and_expr "&" shift_expr
xor_expr ::=  and_expr | xor_expr "^" and_expr
or_expr  ::=  xor_expr | or_expr "|" xor_expr

The & operator yields the bitwise AND of its arguments, which must be integers or one of them must be a custom object overriding __and__[] or __rand__[] special methods.

The ^ operator yields the bitwise XOR [exclusive OR] of its arguments, which must be integers or one of them must be a custom object overriding __xor__[] or __rxor__[] special methods.

The | operator yields the bitwise [inclusive] OR of its arguments, which must be integers or one of them must be a custom object overriding __or__[] or __ror__[] special methods.

6.10. Comparisons¶

Unlike C, all comparison operations in Python have the same priority, which is lower than that of any arithmetic, shifting or bitwise operation. Also unlike C, expressions like a

Chủ Đề