I'm trying to split the following code into a separate if statement.
def second_half(s):
return s[len(s)//2 if len(s)%2 == 0 else ((len(s)//2)+1):]
I've already tried doing the following:
def second_half(s):
if len(s) % 2 == 0:
return s[len(s)//2]
else:
return s[((len(s)//2)+1):]
and receive the following output in my doctest (although majority of my other tests passed):
Failed example:
second_half("abcdef")
Expected:
'def'
Got:
'd'
Would appreciate any help. Cheers.
In your original list-comprehension code, the start index of the slice is calculated and the last index is taken as (len(s)
But when you translate this into two if-statements, You forgot the slice operator : in the the first if condition, which caused only one element to be returned, but what you want is the whole slice in both if conditions, which will happen when you do return s[len(s)//2:] instead of return s[len(s)//2] in the first if condition
So the updated code will be
def second_half(s):
if len(s) % 2 == 0:
#Added the missing slice
return s[len(s)//2:]
else:
return s[((len(s)//2)+1):]
And the code will work as expected
print(second_half('abcde'))
#de
print(second_half('abcdef'))
#def
As commented, your first return is missing the colon.
This is called list slicing, see here for more info.
def second_half_original(s):
return s[len(s)//2 if len(s)%2 == 0 else ((len(s)//2)+1):]
def second_half_split(s):
if len(s) % 2 == 0:
return s[len(s) // 2:]
else:
return s[len(s)//2 + 1:]
Result:
>>> def second_half_original(s):
... return s[len(s)//2 if len(s)%2 == 0 else ((len(s)//2)+1):]
...
>>> def second_half_split(s):
... if len(s) % 2 == 0:
... return s[len(s) // 2:]
... else:
... return s[len(s)//2 + 1:]
...
>>> s = 'abcdef'
>>> print('Old\t{old}\nNew\t{new}'.format(
... old=second_half_original(s),
... new=second_half_split(s)
... )
... )
Old def
New def
whats happening here:
len(s)//2 if len(s)%2 == 0 else ((len(s)//2)+1)
Ternary operator expression:
syntax:
value_when_true if condition else value_when_false
this part of code will return integer (some_integer)
and then you will have:
s[some_integer:] # a[start:] items start through the rest of the array
Slicing strings:
Syntax:
substring = original_string[first_pos:last_pos]
def second_half(s):
if len(s) % 2 == 0:
n=len(s) // 2
else:
n=(len(s)//2)+1
return s[n:]
print (second_half("abcdef"))
def second_half(s):
if len(s) % 2 == 0:
return s[len(s)//2:]
else:
return s[len(s)//2)+1]
output:
def
Related
I wrote a regex code which compares two strings. It recognises a special character '?' that allows zero or more instances of previous character. It works fine until there are two or more occasions of '?' in the string. And I can't make out why.
def single_character_string(a, b) -> "return True if characters match":
"""check if two characters match"""
if len(a) == 0:
return True
elif len(b) == 0:
return False
else:
if a == '.':
return True
else:
if a == b:
return True
else:
return False
def meta_question_result(temp):
if len(temp) >= 2:
if temp[1] == '?':
k_1 = temp.replace(temp[0: 2], '') # no char
k_2 = temp.replace(temp[1], '') # char
return k_1, k_2
def check_pair_by_pair(template, check_string) -> "Strings are of Equal length! " \
"return True if lines are identical":
"""check if two strings match symbol by symbol. template may be less than string, the opposite
is False"""
if not template: # exit from recursion
return True
if not check_string: # exit from recursion
return False
if meta_question_result(template):
t_1, t_2 = meta_question_result(template)
if single_character_string(t_1[0], check_string[0]):
return check_pair_by_pair(t_1[1:], check_string[1:])
if single_character_string(t_2[0], check_string[0]):
return check_pair_by_pair(t_2[1:], check_string[1:])
else:
return False
elif single_character_string(template[0], check_string[0]):
return check_pair_by_pair(template[1:], check_string[1:])
else:
return False
reg, st = input().split("|")
print(check_pair_by_pair(reg, st))
reg = "co?lou?r"
st = "colour"
gives True as expected,
reg = "co?lou?r"
st = "clor"
gives True as expected,
but...
reg = "co?lou?r"
st = "color"
gives False. I expected True.
Found the bag.
Replace method replaces all instances of '?'. So the second '?' was replaced also and program didn't see it.
I should add an argument 'count' to replace method that is equal to 1.
k_1 = temp.replace(temp[0: 2], '', 1) # no char
I'm looking to write a function definition named has_evens that takes in sequence of numbers and returns True if there are any even numbers in the sequence and returns False otherwise.
My code is correct, except when it receives something empty, like "([])". I need to account for that. Here's my code:
def has_evens(s):
for num in s:
if num % 2 == 0:
return True
elif num % 2 != 0:
return False
if ([]):
return False
The final part is a desperate attempt to account for blank lists. More formally, it needs to pass this assertion:
assert has_evens([]) == False
You should only return True when an even is found:
def has_evens(s):
for num in s:
if num % 2 == 0:
return True
return False
Python has an any function to make this simpler:
def has_evens(s):
return any(num % 2 == 0 for num in s)
I answered my own question. I just needed to un-indent my lines
def has_evens(s):
for num in s:
if num % 2 == 0:
return True
else:
return False
I want to use recursion here but my code is wrong. Help me where I'm wrong. It is only return True. I have to return recursive statement as well as the condition in which the function return False. Basically, I want to expand my code.
def mypalindrome(l):
if l==[] or len(l) == 1:
return(True)
else:
return(mypalindrome(l[1:-1]))
You seem to have most of it right. You just need to call the arguments properly and fix the return value. Additionally, you are missing the check that checks the first and the last character, here's an example:
string = "reallear"
def mypalindrome(string):
if len(string) <= 1:
return True
elif string[0] == string[-1]:
return mypalindrome(string[1:-1])
else:
return False
print mypalindrome(string)
Few ways to check word palindrome
def mypalindrome(l):
if len(l) < 2:
return True
if l[0] != l[-1]:
return False
return mypalindrome(l[1:-1])
or more elegant way
def mypalindrome(l):
return l == l[::-1]
def mypalindrome(l):
if l==[] or len(l) == 1:
return(True)
else:
return(mypalindrome(l[1:-1]) and l[0] == l[-1])
The given template is:
def total(lst):
return (
#### YOUR CODE HERE ####
#### DO NOT WRITE CODE OUTSIDE OF THIS ####
#### RETURN STATEMENT ####
)
def getValue():
try:
return int(input())
except:
return None
v = getValue()
myLst = [v]
while v != None:
v = getValue()
if v != None:
myLst.append(v)
print(total(myLst))
I have gotten this:
def total(lst):
return (
if lst ==1:
lst[0]
else:
lst[0]+total(lst[0:])
)
def getValue():
try:
return int(input())
except:
return None
v = getValue()
myLst = [v]
while v != None:
v = getValue()
if v != None:
myLst.append(v)
print(total(myLst))
The input is:
1
2
3
4
5
It should print the sum of all the numbers.
But this gives me an error:
File "main.py", line 3
if lst ==1:
^
SyntaxError: invalid syntax
Please help me figure out what I did wrong! Thanks!
You put an if statement inside a return expression. Putting a statement inside an expression is a syntax error. Use an if expression instead, such as
return (
lst[0] if lst == 1 else lst[0] + total(lst[0:])
)
Since you're only allowed to write code inside an expression, you need to use a slightly different syntax for if-statements.
if len(lst) == 1:
lst[0]
else:
lst[0]+total(lst[0:])
can be written as a single statement as:
lst[0] if len(lst) == 1 else lst[0]+total(lst[0:])
(assuming you wanted to check the length of the list, rather than doing a compare against an int, which is always going to be false)
I want to check if the string user entered has a balanced amount of ( and )'s
ex. ()( is not balanced
(()) is balanced
def check(string):
counter=0
string=string.replace(" ","")
if string[0] is "(":
for x in string:
if x is "(":
counter=counter+1
elif x is ")":
counter=counter-1
if counter1 is 0:
print("Balanced")
else:
print("Unbalanced")
else:
print ("Unbalanced")
so this works, but how do I solve this problem with recursion? I am trying to think how I can make a variable decrease each time i call it recursively and once it's 0, stop.s
>>> def check(mystr, barometer=0):
... if not mystr:
... return barometer
... elif mystr[0] == "(":
... return check(mystr[1:], barometer+1)
... elif mystr[0] == ")":
... return check(mystr[1:], barometer-1)
... else:
... return check(mystr[1:], barometer)
...
>>> for s in ["()", "(()", "(())", "()()"]: print(s, check(s))
...
() 0
(() 1
(()) 0
()() 0
0 means you're properly balanced. Anything else means you're not balanced
A direct, equivalent conversion of the algorithm would look like this:
def check(string, counter=0):
if not string:
return "Balanced" if counter == 0 else "Unbalanced"
elif counter < 0:
return "Unbalanced"
elif string[0] == "(":
return check(string[1:], counter+1)
elif string[0] == ")":
return check(string[1:], counter-1)
else:
return check(string[1:], counter)
Use it like this:
check("(())")
=> "Balanced"
check(")(")
=> "Unbalanced"
Notice that the above algorithm takes into account cases where the closing parenthesis appears before the corresponding opening parenthesis, thanks to the elif counter < 0 condition - hence fixing a problem that was present in the original code.