Returning something other than -1 index - python

Hi I would like to know how I can have my code below return the following given the input
split_sentence("doghellomeyayahell")
return
["dog","hellomeyayahell",""]
instead of
['dog', 'hellomeyayahel', 'l']
I know the problem is that since the thing cannot find the 'hello' string it returns the -1 index. If possible how would I make it so the above would work?
def split_sentence(s):
lst = []
first = s.find('hello')
firsts = s[0:first]
third = s.find('hello', first +2, len(s))
thirds = s[third:len(s)]
second = s[first:third]
lst.append(firsts)
lst.append(second)
lst.append(thirds)
return lst

You can't make it return something else, so you have to test the return value.
if third == -1:
third = len(s)
thirds = s[third:]
You can also use try/except with index:
try:
third = s.index('hello', first + 2)
except:
third = len(s)

Related

How can I assign positives and negatives to a string?

I'm trying to create this code so that when variable J is present, it is a positive number, but if H is present, it is a negative number. Here is my code.
record = ['1J2H']
def robot_location(record: str):
if J in record:
sum()
if H in record:
** I dont know how to subtract them**
print(robot_location(record)
So if record = [1J2H] then the output should be ((+1)+(-2)) = -1 should be the output... how can I do that?? Somebody pls help explain this.
You need to iterate over string inside list, check char by char and asume thats always length of string will be odd
record = ['1J2H']
def robot_location(record: str):
total = 0
aux_n = 0
for a in record:
if a.isnumeric():
aux_n = int(a)
else:
if a == 'H':
total = total + aux_n*-1
else:
total = total + aux_n
aux_n = 0
return total
print(robot_location(record[0]))
Here is a concise way to do this via a list comprehension:
record = '1J2H'
nums = re.findall(r'\d+[JH]', record) # ['1J', '2H']
output = sum([int(x[:-1]) if x[-1] == 'J' else -1*int(x[:-1]) for x in nums])
print(output) # -1
One way to do that is by using iter and converting the string into an iterable, that allows to use next which moves the iteration to the next item meaning that if one simply iterates over it it will get moved to the next item and then if one uses next it will return the current value where the "pointer"? is and move it to the next value so the next iteration with a for loop (list comprehension in this case) will get the next value, meaning that the loop will return only the numbers while next will return only the letters:
lst = ['1J2H']
def robot_location(record: str):
record = iter(record)
numbers = [int(i) if next(record) == 'J' else -int(i) for i in record]
return sum(numbers)
print(robot_location(lst[0]))
You could modify a string like s = '1J2H' to '1+2*-1+0' and let Python evaluate it:
result = eval(s.replace('J', '+').replace('H', '*-1+') + '0')

How to find elements in a list is consecutive

Hi I have a list [tag1 tag2], I would like to find out whether the number following tag is incremental.
match_atr_value = re.search('(.+)\~(\w+)',each_line)
tags = match_atr_value.group(1).split('.')
print tag
Input:
[tag1 tag2]
[tag1 tag3]
[tag1 tag2 tag4]
Output:
Incremental
Not
Not
"Consecutive integers are integers that follow each other in order"
Is there a simpler way to do it? All I have to do is check if its incremental and if yes I should use them else I should throw an exception.
Thanks
You can extract all the digits followed by tag via re.findall() and then use enumerate() and all() to check if the numbers are consecutive:
import re
l = [
"[tag1 tag2]",
"[tag1 tag3]",
"[tag1 tag2 tag4]"
]
pattern = re.compile(r"tag(\d+)")
for item in l:
numbers = map(int, pattern.findall(item)) # if Python 3: call list() on that
result = all(index == item for index, item in enumerate(numbers, start=numbers[0]))
print(result)
Prints:
True
False
False
tag1val = int(re.search(r'\D*(\d+)', tag1).group(1))
tag2val = int(re.search(r'\D*(\d+)', tag2).group(1))
(tag1val - tag2val) == -1
True
tag3val = int(re.search(r'\D*(\d+)', tag3).group(1))
(tag1val - tag3val) == -1
False
(tag2val - tag3val) == -1
True
If you wanted to stick with regular expressions, you can go this route. If the difference is -1 then the one on the right is 1 greater than the one on the left.
If I were you, I would avoid a regex and do something like below. I get the number from the string, whether it's beginning, end, etc. and then compare it to the previous value and return False if it's not increasing
def isIncreasing( listy ):
prev = 0
for w in listy:
val = [''.join(s) for s in w if s.isdigit()]
cur = int(val[0])
if cur != prev+1:
return False
prev = cur
return True

Funny behaviour of my recursive function

t = 8
string = "1 2 3 4 3 3 2 1"
string.replace(" ","")
string2 = [x for x in string]
print string2
for n in range(t-1):
string2.remove(' ')
print string2
def remover(ca):
newca = []
print len(ca)
if len(ca) == 1:
return ca
else:
for i in ca:
newca.append(int(i) - int(min(ca)))
for x in newca:
if x == 0:
newca.remove(0)
print newca
return remover(newca)
print (remover(string2))
It's supposed to be a program that takes in a list of numbers, and for every number in the list it subtracts from it, the min(list). It works fine for the first few iterations but not towards the end. I've added print statements here and there to help out.
EDIT:
t = 8
string = "1 2 3 4 3 3 2 1"
string = string.replace(" ","")
string2 = [x for x in string]
print len(string2)
def remover(ca):
newca = []
if len(ca) == 1: return()
else:
for i in ca:
newca.append(int(i) - int(min(ca)))
while 0 in newca:
newca.remove(0)
print len(newca)
return remover(newca)
print (remover(string2))
for x in newca:
if x == 0:
newca.remove(0)
Iterating over a list and removing things from it at the same time can lead to strange and unexpected behvaior. Try using a while loop instead.
while 0 in newca:
newca.remove(0)
Or a list comprehension:
newca = [item for item in newca if item != 0]
Or create yet another temporary list:
newnewca = []
for x in newca:
if x != 0:
newnewca.append(x)
print newnewca
return remover(newnewca)
(Not a real answer, JFYI:)
Your program can be waaay shorter if you decompose it into proper parts.
def aboveMin(items):
min_value = min(items) # only calculate it once
return differenceWith(min_value, items)
def differenceWith(min_value, items):
result = []
for value in items:
result.append(value - min_value)
return result
The above pattern can, as usual, be replaced with a comprehension:
def differenceWith(min_value, items):
return [value - min_value for value in items]
Try it:
>>> print aboveMin([1, 2, 3, 4, 5])
[0, 1, 2, 3, 4]
Note how no item is ever removed, and that data are generally not mutated at all. This approach helps reason about programs a lot; try it.
So IF I've understood the description of what you expect,
I believe the script below would result in something closer to your goal.
Logic:
split will return an array composed of each "number" provided to raw_input, while even if you used the output of replace, you'd end up with a very long number (you took out the spaces that separated each number from one another), and your actual split of string splits it in single digits number, which does not match your described intent
you should test that each input provided is an integer
as you already do a print in your function, no need for it to return anything
avoid adding zeros to your new array, just test first
string = raw_input()
array = string.split()
intarray = []
for x in array:
try:
intarray.append(int(x))
except:
pass
def remover(arrayofint):
newarray = []
minimum = min(arrayofint)
for i in array:
if i > minimum:
newarray.append(i - minimum)
if len(newarray) > 0:
print newarray
remover(newarray)
remover(intarray)

formatting list to convert into string

Here is my question
count += 1
num = 0
num = num + 1
obs = obs_%d%(count)
mag = mag_%d%(count)
while num < 4:
obsforsim = obs + mag
mylist.append(obsforsim)
for index in mylist:
print index
The above code gives the following results
obs1 = mag1
obs2 = mag2
obs3 = mag3
and so on.
obsforrbd = parentV = {0},format(index)
cmds.dynExpression(nPartilce1,s = obsforrbd,c = 1)
However when i run the code above it only gives me
parentV = obs3 = mag3
not the whole list,it only gives me the last element of the list why is that..??
Thanks.
I'm having difficulty interpreting your question, so I'm just going to base this on the question title.
Let's say you have a list of items (they could be anything, numbers, strings, characters, etc)
myList = [1,2,3,4,"abcd"]
If you do something like:
for i in myList:
print(i)
you will get:
1
2
3
4
"abcd"
If you want to convert this to a string:
myString = ' '.join(myList)
should have:
print(myString)
>"1 2 3 4 abcd"
Now for some explanation:
' ' is a string in python, and strings have certain methods associated with them (functions that can be applied to strings). In this instance, we're calling the .join() method. This method takes a list as an argument, and extracts each element of the list, converts it to a string representation and 'joins' it based on ' ' as a separator. If you wanted a comma separated list representation, just replace ' ' with ','.
I think your indentations wrong ... it should be
while num < 4:
obsforsim = obs + mag
mylist.append(obsforsim)
for index in mylist:
but Im not sure if thats your problem or not
the reason it did not work before is
while num < 4:
obsforsim = obs + mag
#does all loops before here
mylist.append(obsforsim) #appends only last
The usual pythonic way to spit out a list of numbered items would be either the range function:
results = []
for item in range(1, 4):
results.append("obs%i = mag_%i" % (item, item))
> ['obs1 = mag_1', 'obs2 = mag_2', 'ob3= mag_3']
and so on (note in this example you have to pass in the item variable twice to get it to register twice.
If that's to be formatted into something like an expression you could use
'\n'.join(results)
as in the other example to create a single string with the obs = mag pairs on their own lines.
Finally, you can do all that in one line with a list comprehension.
'\n'.join([ "obs%i = mag_%i" % (item, item) for item in range (1, 4)])
As other people have pointed out, while loops are dangerous - its easier to use range

why the output is not good in some cases?

i feel stupid and don't know why the output is not good in some cases.
here is the output (at the end)
it sould find the first sub string in given string for example:
sim('banan','na') -> 'na'
def rev (str):
rev_str=''
i = len(str)-1;
while (i >= 0):
rev_str += str[i];
i = i-1;
return rev_str;
######################################
def sim (str,sub):
sub_len = len (sub);
start = str.index(sub);
rev_str = rev(str)
rev_sub = rev(sub)
if (start ==0):
start =1;
end = start + rev_str.index(rev_sub,start-1);
ret_val = ''
print start , end
for n in range (start,end):
ret_val += str[n];
return ret_val;
print sim('abcdef', 'abc')
print sim('abcdef', 'bc')
print sim('banana', 'na')
the output :
1 4
bcd
1 4
bcd
2 4
na
def sim(haystack, needle):
if needle in haystack:
return needle
If you want indices:
def sim(haystack, needle):
index = haystack.index(needle) # throws ValueError when not found
return (index, index + len(needle))
I agree with Cat's solution. FWIW, you probably want to study a bit about slice syntax. If you're doing string manipulation, slices are a basic tool. I don't see from your code why you wanted to reverse your string, but if you must, try this:
my_string = "abcdefg"
reversed = my_string[::-1] # here's the slice magic
print(reversed)

Categories