This is what it should return
Returns True if all items are truthy.
Examples:
>>> all_true([1, True, 'oregonstate'])
True
>>> all_true([0, 1, 2])
False
"""
This is what I have written
def all_true(items):
for i in items:
if i == True:
return True
else:
return False
pass
Not sure why it is not working, can someone help?
Your function just returns the truthiness of the first item in the list, since it always returns on the first iteration.
You want to do something like this:
def all_true(items):
for i in items:
if not i:
return False
return True
Note that this all_true function already exists in Python. It is the the built-in all function.
Two problems. First, you are returning on the first True thing. In fact, you are returning either True or False on the first thing, regardless. Since you return on both the if and its else clauses, the loop will always return on the first iteration. A bit more subtle, but if there aren't any values in the list, it will return None.
Second, if you want "truthy", don't compare specifically to True. foo == True is False. Instead, just let the if do the boolean test
def all_true(items):
for i in items:
if not i:
return False
return True
all and any are builtin functions that do the same thing. It would generally be preferable to use them.
"All items are truthy" is logically equivalent to "no items are falsy."
def all_true(items):
for i in items:
if not i:
return False
return True
Because 0 is falsy. Also there's no need to implement your own function for that, use Python's built–in all() function instead!
Related
Hey Stackoverflow community,
I am a python newbie.
So, I am trying to build the function any() from scratch. However the output I get is not what I expected. My code is working fine without the second if statement:
def anys(lst):
for i in range(0,len(lst)):
if bool(lst[i])==True:
return True
anys([False,True,False]) executes True as expected.
However, when I am adding a second if statement I get a different outcome:
def anys(lst):
for i in range(0,len(lst)):
if bool(lst[i])==True:
return True
if bool(lst[i])==False or len(lst)==0:
return False
anys([False,True,False]) executes False.
Can anyone help me what I am doing wrong? Any help would be greatly appreciated.
When you are using a return statement, the function will stop executing and, as instructed, return to the place where the function was called from. This means that the function will return at the first elemt in the list since it was False. If you want the function to return false if all of the elemts are false, I would recomend that you put the return False statement after the for loop.
To clearify, the loop starts with the first elemnt in the list, which in this case is False. The element satisfies the condition:
if bool(lst[i])==False or len(lst)==0:
And the function will then return False.
To answer the comment, if you loop through the entire list, and none of the elements are true (in other words "any"), you then want to return false instead.
def anys(lst):
for i in range(0,len(lst)):
if bool(lst[i])==True:
return True
return False
The code now goes through the list, if it ever encounters a True value, it returns True, however if none of the elements are True, it instead returns False.
The basic answer is that with both conditional return statements, you were always returning on the first iteration and ignoring the rest of the values from the list (or other iterable).
But aside from that, a few other hints that could be useful:
You do not need to loop by index number - just loop over the elements in the list directly.
To test whether an expression (here x) would be True if converted into a boolean, all you need to do is if x:
In the correct form with a single conditional return in the loop, it was returning None if no true values were found and the end of the function was reached. But the builtin any returns False in that situation, so an explicit return False is needed if you want to emulate this behaviour.
def anys(lst):
for x in lst:
if x:
return True
return False
Let us execute your second any() function line by line.
First element of input argument is False.
When you check first if condition, if bool(False) == True, it fails.
It reaches to your second if condition.
if bool(False) == False or len(lst) == 0, bool(False) == False is true hence this if condition is executed and your method returns False.
why does this not work?
It works for False palindrome; however, for anything True it never returns True..
I don't understand why this function does not return True?
And how I should improve this same answer so that it returns True.
My logic was that after the function completes iterating through the entire string, it will return True.
def isPalindrome(string, i = 0):
if i == len(string):
return True
if string[i] != string[len(string)-1-i]:
return False
isPalindrome(string,i+1)
Problem is with your last line:
isPalindrome(string,i+1)
That last line will eventually resolve to either True or False -- but how is that value being returned? (It isn't.)
Try:
return isPalindrome(string,i+1)
Check out the visualization here
My hint would be check what you are returning (i.e. what does isPalindrome return).
If you want just the answer, it is here
I need to check if a function written by another team returns True or None.
I want to check for identity, not equality.
I'm unclear what type of check happens when using in. Which of the following does if result in (True, None): behave like?
if result is True or result is None:
if result or result == None:
No, they are not the same, because identity testing is a subset of what the in operator does.
if result in (True, None):
Is the same as this:
if result == True or result is True or result == None or result is None:
# notice that this is both #1 and #2 OR'd together
From the docs:
For container types such as list, tuple, set, frozenset, dict, or collections.deque, the expression x in y is equivalent to any(x is e or x == e for e in y)
The in operator tests for both equality and identity, and either one being true will return True. I got the impression that you're only working with boolean values and None. In that limited case, the in operator will behave the same as both of your other snippets.
However, you said you want identity checking. So I would suggest you use that explicitly so your code's intention and what it is expecting is clear. Furthermore, if there is a bug in the called function and it returns something other than boolean or None, using the in operator can hide that bug.
I would suggest your first alternative:
if result is True or result is None:
# do stuff
else:
# do other stuff
Or if you're feeling defensive:
if result is True or result is None:
# do stuff
elif result is False:
# do other stuff
else:
# raise exception or halt and catch fire
You want to use the identity operator (is) and not the membership operator (in):
> 1 == True
True
> 1 is True
False
> 1 in (True, None)
True
This is a "TL;DR" complement to #skrrgwasme answer :)
I'm working with this exercise:
Write a function is_member() that takes a value (i.e. a number, string, etc) x and a list of values a, and returns True if x is a member of a, False otherwise. (Note that this is exactly what the in operator does, but for the sake of the exercise you should pretend Python did not have this operator.)
I wrote this function:
def isMember(value, list):
for element in list:
if(element == value):
return True
else:
return False
myList = ["a","b","c",1,2,3]
print(isMember("a",myList)) #Returns True; correct
print(isMember(3,myList)) #Returns False; why the heck?
You need to take the return False out of the loop:
def isMember(value, list):
for element in list:
if(element == value):
return True
return False
The way you have it currently, isMember will return False if the value is not the first item in the list. Also, you should change the name of your list variable to something other than list, which is a built-in function in Python.
The problem is that your return False is within the loop, directly as the else case of your membership test. So as you loop through the list, you get to the first element and check if it is in the list or not. If it is in the list, you return true—that’s fine. If it’s not in the list, you return false, aborting the loop process and ending the function. So you never look at the other values inside the loop.
So to fix this, move the return False outside of the loop, at the end of the function. That way, only when all elements have been looked at, you return false.
def isMember (value, list):
for element in list:
if element == value:
return True
return False
Another way would be to simplify this using the any function to perform the check for every element in the list. any takes an iterable and looks at the values. As soon as it finds a true value, it returns true. Otherwise it keeps iterating until it finds a false value or hits the end of the iterator, both cases yielding a false. So you could rewrite it like this:
def isMember (value, list):
return any(value == element for element in list)
Can anybody explain why in python builtin buinction all return True in this case all([])?
In [33]: all([])
Out[33]: True
In [34]: all([0])
Out[34]: False
In [35]: __builtins__.all([])
Out[35]: True
I'm not convinced that any of the other answers have really address the question of why this should be the case.
The definition for Python's all() comes from boolean logic. If for example we say that "all swans are white" then a single black swan disproves the statement. However, if we say that "all unicorns are pink" logicians would take that as a true statement simply because there are no non-pink unicorns. Or in other words "all " is vacuously true.
Practically it gives us a useful invariant. If all(A) and all(B) are both true then the combination of all(A + B) is also true. If all({}) was false we should have a less useful situation because combining two expressions one of which is false suddenly gives an unexpected true result.
So Python takes all([]) == True from boolean logic, and for consistency with other languages with a similar construct.
Taking that back into Python, in many cases the vacuous truth makes algorithms simpler. For example, if we have a tree and want to validate all of the nodes we might say a node is valid if it meets some conditions and all of its children are valid. With the alternative definition of all() this becomes more complex as we have to say it is valid if it meets the conditions and either has no children or all its children are valid.
class Node:
def isValid(self):
return some_condition(self) and all(child.isValid for child in self.children)
From the docs:
Return True if all elements of the iterable are true (or if the iterable is empty).
So, roughly, it's simply defined this way.
You can get around that by using
list = []
if list and all(list):
pass
As the docs say, all is equivalent to:
def all(iterable):
for element in iterable:
if not element:
return False
return True
For an empty iterable the loop body is never executed, so True is immediately returned.
Another explanation for this is that all and any are generalisations of the binary operators and and or for arbitrarily long numbers of parameters. Thus, all and any can be defined as:
def all(xs):
return reduce(lambda x,y: x and y, xs, True)
def any(xs):
return reduce(lambda x,y: x or y, xs, False)
The True and False parameters show that all([]) == True and any([]) == False.
Any expression with all can be rewritten by any and vice versa:
not all(iterable)
# is the same as:
any(not x for x in iterable)
and symmetrically
not any(iterable)
# is the same as:
all(not x for x in iterable)
These rules require that all([]) == True.
The function all is very useful for readable asserts:
assert all(required_condition(x) for x in some_results_being_verified)
(It is not so bad if a task has no results, but something is very broken if any result is incorrect.)