Struggling with python Comparison question [closed] - python

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 1 year ago.
Improve this question
Am learning python and one of the questions in our study guide asks to evaluate RNA sequences. I do not get the expected outputs as suggested by the question, I get 17.
Here is the code:
####START FUNCTION
def rna_length(mrna);
start_rna = 'AUG';
end_rna1 = 'UGA';
end_rna2 = 'UAA';
end_rna3 = 'UAG';
if (mrna[0:3]==start_rna) and (mrna [-3:]==end_rna1 or end_rna2 or end_rna3):
length = len(mrna[3:-3])
return length
else: ((mrna[0:3]!=start_rna) or (mrna [-3:]!=end_rna1 or end_rna2 or end_rna3))
return "Not readable RNA code"
####END FUNCTION
A link to a screenshot of the question here

The issue is you using the boolean operator or to compare strings. You can think of the comparisons like this:
(mrna [-3:]==end_rna1 or end_rna2 or end_rna3)
(((mrna [-3:]==end_rna1) or end_rna2) or end_rna3)
Because or is a boolean operator, it needs to work on booleans. You can convert strings to booleans using bool(<str>)
(((mrna [-3:]==end_rna1) or bool(end_rna2)) or bool(end_rna3))
Any string that is not empty (ie. any string that is not "") is "truthy." What that means is that bool(non_empty_str) == True and bool('') == False.
(((mrna [-3:]==end_rna1) or True) or True)
((True) or True)
(True or True)
True
Now, how should you fix it? There are a few approaches to this.
Properly use or.
if (mrna[0:3]==start_rna) and (mrna[-3:]==end_rna1 or mrna[-3:]==end_rna2 or mrna[-3:]==end_rna3):
length = len(mrna[3:-3])
return length
else:
((mrna[0:3]!=start_rna) or (mrna[-3:]!=end_rna1 or mrna[-3:]!=end_rna2 or mrna[-3:]!=end_rna3))
return "Not readable RNA code"
Use a collection. Note that it is standard to use tuples instead of lists whenever you don't want to modify the collection. I used lists here because the brackets look different. You can also use sets for quicker in, but that's overkill for 3.
if mrna[0:3] == start_rna and mrna[-3:] in [end_rna1, end_rna2, end_rna3]:
length = len(mrna[3:-3])
return length
else:
(mrna[0:3] != start_rna or mrna[-3:] not in [end_rna1, end_rna2, end_rna3])
return "Not readable RNA code"
Heck, you can even use the string methods str.startswith and str.endswith.
if mrna.startswith(start_rna) and mrna.endswith([end_rna1, end_rna2, end_rna3]):
length = len(mrna[3:-3])
return length
else:
...

Related

Organizing a list of values in ascending order with only slicing [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 10 days ago.
Improve this question
I am attempting to organize a list in Python without using sort(), mutable default arguments, loops or variables outside of the function.
The only basic option I have is slices, but I am unsure how to set up a slice to compare each value to the preceding value.
def ascending_nums(numbahs):
if len(numbahs) == 1:
return False #set a base case where if only one numbah is entered we return false
else:
ascending = ascending_nums(numbahs[::1])
if numbahs[0:] < ascending:
return True
print(ascending_nums([1,2,3,4,5,6]))
an attempt
This is what I have so far, unfortunately it exceeds the recursion limit because of how the base case is set up.
The code is not supposed to sort, just return whether or not the list is sorted. I was able to submit a solution that I will upload later.
Here is what I came up with
def list_min(numbahs):
if len(numbahs) == 0
return True #set up a base case to be true, and eliminate numbers as we move through the list
else:
overall_list = list_min(numbahs[1:]) #this makes it so the 2nd and every following member is run through the list
if numbahs[0] < overall_list: #if the first numbah in the list is less than the second
overall_list = numbahs[0] #set the second to the first value
return overall_list
Is there a specific reason why you can't use sort()? You can get pretty creative with the key= kwarg.
The standard bubble sort looks something like this:
def bubbleSort(arr):
n = len(arr)
# Traverse through all array elements
for i in range(n):
swapped = False
# Last i elements are already in place
for j in range(0, n-i-1):
# traverse the array from 0 to n-i-1
# Swap if the element found is greater
# than the next element
if arr[j] > arr[j+1]:
arr[j], arr[j+1] = arr[j+1], arr[j]
swapped = True
if (swapped == False):
break
Taken from Geeks for Geeks.
Info on sort can be found here, and info on sorted can be found here
Also, I'm sure that someone else has asked your question before. Please refer to other answers or Google before asking your question here. Stackoverflow has a LOT of questions that have already been answered.

Most pythonic way to split string into integers [closed]

Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 21 days ago.
Improve this question
I have a string that needs to be validated that it is of the form of ‘#-#’ where the #s should be unsigned integers. What is the most pythonic way to split this into two integers, lo and hi, possibly including type-checking/validation that lo < hi, unsigned ints, and so on?
I’ve thought about various solutions, but I have varying criteria and it must make sure that # and # are unsigned ints with only the one hyphen in between.
I'm not sure if this is absolutely the most pythong way, but I'd split on the - character and use a list comprehension to generate lo and hi:
[lo, hi] = [int(x) for x in s.split('-')]
You can try something like this:
string = "43-3" #example data
num = string.split("-") #split the string
lo = int(num[0])
hi = int(num[1])
if(lo<hi):
print("ok")
else:
print("ko")
this will work as long your string is exactly as you told us and there are only unsigned ints in the string.
Best I can think of is using a regular expression to match the exact pattern and assert that everything is correct. Note however that doing it this way will crash the program as soon as an invalid input appears, unless you do some extra error handling.
import re
input_strings = [
"123-321",
"92646-278364",
# "12345-123", # error: low > high
# "123.45-98765", # error: not integers
]
def get_num_pair(num_str: str):
m = re.match(r'(\d+)-(\d+)', num_str)
assert m and len(m.groups()) == 2
lo, hi = int(m.group(1)), int(m.group(2))
assert 0 <= lo <= hi
return lo, hi
for input_str in input_strings:
print(get_num_pair(input_str))
Expanding on Mureinik's answer - I'd suggest you do the following:
use a list comprehension to split the list on '-' and turn each bit into ints
carry out validation on the resulting list to ensure it meets your requirements - exactly two elements and the first one is lower
wrap this in a try, except block in case the list comprehension gives an error
wrap that in a function that encapsulates the concept of splitting #-# strings
e.g.
def parse_twoval_str(twoval_str):
try:
vals = [int(s) for s in twoval_str.split("-")]
except ValueError:
raise ValueError("Could not parse input - must be of form '123-234'")
if len(vals) != 2:
raise ValueError("Input must contain two values")
a, b = vals
if a > b:
raise ValueError("First value must be less than second value")
return a, b

Should i always use 'else:' even it is not necessary? [closed]

Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 3 years ago.
Improve this question
Am i must to use here else: or i have opportunity to remove it and just type return True
def some_function(x):
if another_function(x) == -1:
return False
else:
return True
EDIT: I know how to make this code compact with just one return. The main question is about else:.
Should i always use 'else:' even it is not necessary?
I myself believe that they are not necessary. Returning at the beginning of the function in case of edge cases is something that allows you to skip sometimes lots of indentations caused by elses:
def some_function(x):
if edge_case_1:
return []
if edge_case_2:
return None
#a
#lot
#of
#code
#here
return result
looks better than
def some_function(x):
if edge_case_1:
return []
elif edge_case_2:
return None
else:
#a
#lot
#of
#code
#here
return result
right?
But it's not only about the looks:
Elses like that make you easily confuse the indentation levels.
The line width becomes smaller because the indentation takes those few character, you might need to format your code more to fit PEP8.
Sometimes you write the main part of the code first, only to discover the edge cases later. Version control systems such as git would mark all indented lines as changed (depending on the configuration), while the only thing you did was add those ifs at the beginning!
you can remove else and do like this:
def some_function(x):
if another_function(x) == -1:
return False
return True
Logically you can write
def some_function(x):
return another_function(x) != -1
else is not mandatory syntactically but there are few cases where you will get error
declare default value:-
var1 = some_value
if condition:
var1 = "something"
return var1
For the general case: since the return exits the function at this point and return control to the caller, the prefered idiom is :
def foo(x):
if <some_expression>:
return <something>
# we'll only ever get here if `<some_expression>`'s value is false
return <something_else>
As to why it's the prefered idiom (in python at least): the general consensus is that it makes the code more readable by 1/ flattening it (less indentation levels) and 2/ getting rid of all corner cases right from the start so the nominal case code is not polluted by such considerations. As a general rule, the simpler the code (and "flat" code is simpler than nested one, at least for the human brain) the easiest it is to understand.
Now for your own case where you are returning the boolean value of an expression, you don't even need a if statement at all - you can just directly return the result of evaluating the expression:
def foo(x):
return some_test(x) != some_value

Iterate through string of characters and look for int? [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 3 years ago.
Improve this question
I need to iterate through a string with a mixture of letters and numbers. If it finds at least one number, it returns True, else, it returns false. How can I do this?
You can write a function that returns True when find at least one digit using the isdigit() method.
def has_digit(str):
for letter in str:
if letter.isdigit():
return True
return False
if __name__ == '__main__':
print(has_digit('abcdef'))
print(has_digit('abd5e'))
The output is:
False
True
You can write a function or not as you like. You can also write a ready string or you can use input function:
x = 'Jack77'
for i in x:
if i.isdigit():
print(True)
else:
print(False)
#==================
def checking_digits(x):
for i in x:
if i.isdigit():
return True
return False
print(checking_digits(x))
This will create a list of bool values for each character in the string. isdigit return True if the character is a digit, False otherwise. So if any of the bool values (or any the characters is a digit), it will return True
has_digits = any(i.isdigit() for i in text)

Is there a way in python to compare strings for unique character [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 8 years ago.
Improve this question
Suppose I have a list of strings
['elvis','elo','eels','acdc']
Is there a function that accept this string and returns a unique character for each of the strings? For example, in this case, I expect to get
['e','l','s','a']
Edit: To clarify my meaning.
I want a function that will return an identifier character or string that is based on the input list members. jme answer and bonit's one are a good example.
I think I see your point. There is no built-in for this.
Correct me if I am wrong, but it seems like you want to take the first not already taken character in each string and take one only.
Here is some code to do that
def get_first_not_know(l):
chars = []
for word in l:
for letter in word:
if letter not in chars:
chars.append(letter)
break
return chars
If you don't care about order of letters you take, you can do something quicker using sets.
Assuming Benoît Latinier's interpretation of your question is right (which, it looks like it is), then there will be some cases where a unique letter can't be found, and in these cases you might throw an exception:
def unique_chars(words):
taken = set()
uniques = []
for word in words:
for char in word:
if char not in taken:
taken.add(char)
uniques.append(char)
break
else:
raise ValueError("There are no unique letters left!")
return uniques

Categories