Usage of the "==" operator for three objects - python

Is there any computational difference between these two methods of checking equality between three objects?
I have two variables: x and y. Say I do this:
>>> x = 5
>>> y = 5
>>> x == y == 5
True
Is that different from:
>>> x = 5
>>> y = 5
>>> x == y and x == 5
True
What about if they are False?
>>> x = 5
>>> y = 5
>>> x == y == 4
False
And:
>>> x = 5
>>> y = 5
>>> x == y and x == 4
False
Is there any difference in how they are calculated?
In addition, how does x == y == z work?
Thanks in advance!

Python has chained comparisons, so these two forms are equivalent:
x == y == z
x == y and y == z
except that in the first, y is only evaluated once.
This means you can also write:
0 < x < 10
10 >= z >= 2
etc. You can also write confusing things like:
a < b == c is d # Don't do this
Beginners sometimes get tripped up on this:
a < 100 is True # Definitely don't do this!
which will always be false since it is the same as:
a < 100 and 100 is True # Now we see the violence inherent in the system!

Adding a little visual demonstration to already accepted answer.
For testing equality of three values or variables. We can either use:
>>> print(1) == print(2) == print(3)
1
2
3
True
>>> print(1) == print(2) and print(2) == print(3)
1
2
2
3
True
The above statements are equivalent but not equal to, since accesses are only performed once. Python chains relational operators naturally. See this docs:
Comparisons can be chained arbitrarily, e.g., x < y <= z is equivalent to x < y and y <= z, except that y is evaluated only once (but in both cases z is not evaluated at all when x < y is found to be false).
If the functions called (and you are comparing return values) have no side-effects, then the two ways are same.
In both examples, the second comparison will not be evaluated if the first one evaluates to false. However: beware of adding parentheses. For example:
>>> 1 == 2 == 0
False
>>> (1 == 2) == 0
True
See this answer.

Related

Subselection using np.logical_and in Numpy

I plot(x,y) a chart and want to return True when for x ranging from A to B y is larger than C ("there exists x in interval such that y(x) > C). The code below does not work. How can I do it?
d_for_hours=density[np.logical_and(y>C,x>=A, x <=B)].all()
Exemplary output:
for C = 0.02 and A = 9 and B = 13, the output should be True
for C = 0.05 and A = 9 and B = 13, the output should be False
You want to use any rather than all to check if y has any value above C. Before that, you need to restrict y to the indices of x that match the condition (between A and B):
# create data
x = np.array(range(20))
y = np.array(19 * [0] + [1])
(y[np.logical_and(x>=9, x<=13)] >= 0.05).any() # False
(y[np.logical_and(x>=9, x<=20)] >= 0.05).any() # True

Check if multiple variables have the same value

I have a set of three variables x, y, z and I want to check if they all share the same value. In my case, the value will either be 1 or 0, but I only need to know if they are all the same. Currently I'm using
if 1 == x and 1 == y and 1 == z:
sameness = True
Looking for the answer I've found:
if 1 in {x, y, z}:
However, this operates as
if 1 == x or 1 == y or 1 == z:
atleastOneMatch = True
Is it possible to check if 1 is in each: x, y, and z?
Better yet, is there a more concise way of checking simply if x, y, and z are the same value?
(If it matters, I use Python 3.)
If you have an arbitrary sequence, use the all() function with a generator expression:
values = [x, y, z] # can contain any number of values
if all(v == 1 for v in values):
otherwise, just use == on all three variables:
if x == y == z == 1:
If you only needed to know if they are all the same value (regardless of what value that is), use:
if all(v == values[0] for v in values):
or
if x == y == z:
To check if they are all the same (either 1 or 2):
sameness = (x == y == z)
The parentheses are optional, but I find it improves readability
How about this?
x == y == z == 1
In my case, the value will either by 1 or 2, but I only need to know if they are all the same
Is it possible to check if 1 is in each: x, y, and z?
Better yet, is there a more concise way of checking simply if x, y, and z are the same value?
Sure:
x == y == z
which is equivalent to
(x == y) and (y == z)
If you have an arbitrary (nonzero) number of values to compare:
all(values[0] == v for v in values[1:])
You could use something similar to what you have:
sameness = (len({x, y, z}) == 1)
This allows for any number of variables. For example:
variables = {x, y, z, a, b, ...}
sameness = (len(variables) == 1)
Note: Creating a set means that each variable needs to be hashed and the hashed values need to be stored, but all() with a generator expression is short-circuiting and keeps track of only two values at a time. Therefore, besides its readability, the generator expression is more efficient.
Another way:
sameness = all(e == 1 for e in [x, y, z])
[x,y,z].count(1)
will count how many variables have 1 as value
Below all() and any() functions in python can server the purpose.
all() act as "AND": if all the values in any ittertable object is equal to given condition value, then Return True else return False.
Examples
assert all(b == True for b in [True,True,True,True]) == True
assert all(b == True for b in [False,True,True,True]) == False
any() act as "OR": if any one value in any ittertable object is equal to given condition value, then Return True else return False.
Examples
assert any(b == True for b in [False,False,False,True]) == True
assert any(b == True for b in [False,False,False,False]) == False
If you had more variables, this way might be most concise:
{x} == {y, z}
(Not as fast as x == y == z, but the question asked for concise, not for fast.)

Calling function in python 3 [closed]

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 7 years ago.
Improve this question
Adding three variables through score function
How can I call my function? Here I want to add all three variables. Why doesn´t it show the output?
def score(x,y,z):
x == 1
y == 2
z == 3
return (x+y+z)
You're not assigning values, just checking a boolean.
And, even though you assign x,y,z in your function, make sure you're including arguments when calling it. However, your result will always be 6 no matter what arguments you pass, because you're changing their values in the function.
So, to use scores it should be:
def score(x,y,z):
return (x+y+z)
or, if you want a constant one:
def score():
x = 1
y = 2
z = 3
return(x+y+z)
In python, there's to use for the = character: if you use it alone, it is an assignment:
>>> a = 8
>>> print(a)
8
The other is a test, which returns a boolean, True or False: we use it to test if a variable equals another:
>>> 1 == 2
False
>>> 1 == 1
True
>>> a = 1 # Here, it's an asignment
>>> b = 1
>>> a == b
True
>>> b = 2
>>> a == b
False
In your code, you use the test: thus, the variables x, y, and z aren't modified. You must instead write:
def score(x, y, z):
x = 1
y = 2
z = 3
return (x + y + z)
if you want to assign 1, 2 and 3 to x, y and z. But please note that in this case, the three parameters are useless: this function is simply:
def score(x, y, z):
return (1 + 2 + 3)
You should define the parameters first:
def score(x,y,z):
return (x+y+z)
print(score(1, 5, 2))
Output: 7
If you want constant scores, you shouldn't even put any parameters in the first place. You used == instead of = too.
def score():
x = 1
y = 2
z = 3
return (x+y+z)
print(score())
Output: 6
It is x = 1... not ==, == is comparison = is assignment.
def score():
x = 1
y = 2
z = 3
return (x+y+z)
Then:
print(score()) # -> 6
If you want to pass the values:
def score(x,y,z):
return (x+y+z)
print(score(1,2,3)) # -> 6
If you wanted to test the values passed in were certain numbers you would use ==:
def score(x, y, z):
if x == 1 and y == 2 and z == 3:
return x + y + z
That tests if x is equal to 1 and y is equal to 2 and z is equal to 3
A more logical reason to assign values to x y and z would be to give x,y and z default values:
def score(x=1, y=2, z=3):
return x + y + z
So calling print(score(4)) would output 9 as x would be equal to 4 and the default values for y and z are used.

Order of execution of tuples in Python during assignment [duplicate]

What is the difference between the following Python expressions:
# First:
x,y = y,x+y
# Second:
x = y
y = x+y
First gives different results than Second.
e.g.,
First:
>>> x = 1
>>> y = 2
>>> x,y = y,x+y
>>> x
2
>>> y
3
Second:
>>> x = 1
>>> y = 2
>>> x = y
>>> y = x+y
>>> x
2
>>> y
4
y is 3 in First and 4 in Second
In an assignment statement, the right-hand side is always evaluated fully before doing the actual setting of variables. So,
x, y = y, x + y
evaluates y (let's call the result ham), evaluates x + y (call that spam), then sets x to ham and y to spam. I.e., it's like
ham = y
spam = x + y
x = ham
y = spam
By contrast,
x = y
y = x + y
sets x to y, then sets y to x (which == y) plus y, so it's equivalent to
x = y
y = y + y
It is explained in the docs in the section entitled "Evaluation order":
... while evaluating an assignment, the right-hand side is evaluated
before the left-hand side.
The first expression:
Creates a temporary tuple with value y,x+y
Assigned in to another temporary tuple
Extract the tuple to variables x and y
The second statement is actually two expressions, without the tuple usage.
The surprise is, the first expression is actually:
temp=x
x=y
y=temp+y
You can learn more about the usage of comma in "Parenthesized forms".
An observation regarding the left-hand side as well: the order of assignments is guaranteed to be the order of their appearance, in other words:
a, b = c, d
is equivalent functionally to precisely (besides t creation):
t = (c, d)
a = t[0] # done before 'b' assignment
b = t[1] # done after 'a' assignment
This matters in cases like object attribute assignment, e.g.:
class dummy:
def __init__(self): self.x = 0
a = dummy(); a_save = a
a.x, a = 5, dummy()
print(a_save.x, a.x) # prints "5 0" because above is equivalent to "a = dummy(); a_save = a; t = (5, dummy()); a.x = t[0]; a = t[1]"
a = dummy(); a_save = a
a, a.x = dummy(), 5
print(a_save.x, a.x) # prints "0 5" because above is equivalent to "a = dummy(); a_save = a; t = (dummy(), 5); a = t[0]; a.x = t[1]"
This also implies that you can do things like object creation and access using one-liners, e.g.:
class dummy:
def __init__(self): self.x = 0
# Create a = dummy() and assign 5 to a.x
a, a.x = dummy(), 5
I've recently started using Python and this "feature" baffled me. Although there are many answers given, I'll post my understanding anyway.
If I want to swap the values of two variables, in JavaScipt, I'd do the following:
var a = 0;
var b = 1;
var temp = a;
a = b;
b = temp;
I'd need a third variable to temporarily hold one of the values. A very straightforward swap wouldn't work, because both of the variables would end up with the same value.
var a = 0;
var b = 1;
a = b; // b = 1 => a = 1
b = a; // a = 1 => b = 1
Imagine having two different (red and blue) buckets and having two different liquids (water and oil) in them, respectively. Now, try to swap the buckets/liquids (water in blue, and oil in red bucket). You can't do it unless you have an extra bucket.
Python deals with this with a "cleaner" way/solution: Tuple Assignment.
a = 0
b = 1
print(a, b) # 0 1
# temp = a
# a = b
# b = temp
a, b = b, a # values are swapped
print(a, b) # 1 0
I guess, this way Python is creating the "temp" variables automatically and we don't have to worry about them.
In the second case, you assign x+y to x
In the first case, the second result (x+y) is assigned to y
This is why you obtain different results.
After your edit
This happen because, in the statement
x,y = y,x+y
all variables at the right member are evaluated and, then, are stored in the left members. So first proceed with right member, and second with the left member.
In the second statement
x = y
y = x + y
yo first evaluated y and assign it to x; in that way, the sum of x+y is equivalent to a sum of y+y and not of x+x wich is the first case.
The first one is a tuple-like assignment:
x,y = y,x+y
Where x is the first element of the tuple, and y is the second element, thus what you are doing is:
x = y
y = x+y
Wheras the second is doing a straight assign:
x=y
x=x+y
Other answers have already explained how it works, but I want to add a really concrete example.
x = 1
y = 2
x, y = y, x+y
In the last line, first the names are dereferenced like this:
x, y = 2, 1+2
Then the expression is evaluated:
x, y = 2, 3
Then the tuples are expanded and then the assignment happens, equivalent to:
x = 2; y = 3
For newbies, I came across this example that can help explain this:
# Fibonacci series:
# the sum of two elements defines the next
a, b = 0, 1
while a < 10:
print(a)
a, b = b, a+b
With the multiple assignment, set initial values as a=0, b=1.
In the while loop, both elements are assigned new values (hence called 'multiple' assignment). View it as (a,b) = (b,a+b). So a = b, b = a+b at each iteration of the loop. This continues while a<10.
RESULTS:
0
1
1
2
3
5
8
Let's grok the difference.
x, y = y, x + y
It's x tuple xssignment, mexns (x, y) = (y, x + y), just like (x, y) = (y, x)
Stxrt from x quick example:
x, y = 0, 1
#equivxlent to
(x, y) = (0, 1)
#implement xs
x = 0
y = 1
When comes to (x, y) = (y, x + y)
ExFP, have x try directly
x, y = 0, 1
x = y #x=y=1
y = x + y #y=1+1
#output
In [87]: x
Out[87]: 1
In [88]: y
Out[88]: 2
However,
In [93]: x, y = y, x+y
In [94]: x
Out[94]: 3
In [95]: y
Out[95]: 5
The result is different from the first try.
Thx's because Python firstly evaluates the right-hand x+y
So it equivxlent to:
old_x = x
old_y = y
c = old_x + old_y
x = old_y
y = c
In summary, x, y = y, x+y means,
x exchanges to get old_value of y,
y exchanges to get the sum of old value x and old value y,
a, b = 0, 1
while b < 10:
print(b)
a, b = b, a+b
Output
1
1
2
3
5
8
the variables a and b simultaneously get the new values 0 and 1, the same a, b = b, a+b, a and b are assigned simultaneously.

Python Version of Perl = || (= Or)

I can't seem to find a python way of saying
x = y or 1
In Perl:
$x = $y || 1;
Is there a nice way to do this in python?
Python's or has what I believe are the semantics you're looking for. See the documentation. It's important to realize that it returns the input value(s), not True or False.
>>> "" or 12
12
>>> 27 or 9
27
>> None or "default"
'default'
This should mean that x = y or 1 should be what you're after, x will be y if y is non-False, else it will be 1.
x = y or 1 is the same as:
if y:
x = y
else:
x = 1
Isn't it what you're trying to do?
y = 2
x = y if y else 1
# x == 2
y = None
x = y if y else 1
# x == 1
All the solutions mentioned will work if y is defined (it can be None)
If y is not defined Python will throw an exception, while the Perl code will work in non-strict mode.
A simple one but not that nice:
x = y if y else 1

Categories

Resources