With this code, all I am trying to do is insert a dash between odd numbers and an asterisk between even ones. It does not work correctly with every input. It works with, e.g. 46879, but returns None with 468799, or does not insert * between 4 and 6 with 4546793. Why is it doing that? Thanks
def DashInsertII(num):
num_str = str(num)
flag_even=False
flag_odd=False
new_str = ''
for i in num_str:
n = int(i)
if n % 2 == 0:
flag_even = True
else:
flag_even = False
if n % 2 != 0:
flag_odd = True
else:
flag_odd = False
new_str = new_str + i
ind = num_str.index(i)
if ind < len(num_str) - 1:
m = int(num_str[ind+1])
if flag_even:
if m % 2 == 0:
new_str = new_str + '*'
else:
if m % 2 != 0:
new_str = new_str + '-'
else:
return new_str
print DashInsertII(raw_input())
3 Answers 3
Your function definition is one of the most overbuilt functions I've seen in a while; the following should do what yours was trying to do, sans the complexity.
def DashInsertII(num):
num_str = str(num)
new_str = ''
for i in num_str:
n = int(i)
if n % 2 == 0:
new_str += i + '*'
else:
new_str += i + '-'
return new_str
print DashInsertII(raw_input())
EDIT: I just re-read the question and saw that I misinterpreted what you want, which is to insert a - between two odd numbers and a * between two even numbers. For that, the best solution I can come up with uses regular expressions.
Second Edit: As per alvits's request, I'm including an explanation of the regex in this.
import re
def DashInsertII(num):
num_str = str(num)
# r'([02468])([02468])' performs capturing matches on two even numbers
# that are next to each other
# r'1円*2円' is a string consisting of the first match ([02468]) followed
# by an asterisk ('*') and the second match ([02468])
# example input: 48 [A representation of what happens inside re.sub()]
# r'([02468])([02468])' <- 48 = r'( 1円 : 4 )( 2円 : 8 )'
# r'1円*2円' <- {1円 : 4, 2円 : 8} = r'4*8'
num_str = re.sub(r'([02468])([02468])',r'1円*2円',num_str)
# This statement is much like the previous, but it matches on odd pairs
# of numbers
num_str = re.sub(r'([13579])([13579])',r'1円-2円',num_str)
return num_str
print DashInsertII(raw_input())
If this is still not what you actually want, please comment on this to let me know.
2 Comments
RevanProdigalKnight's answer is almost right but fails when 3 or more even/odd numbers come together.
The right way to do this with regex would be to use positive lookahead (use ?=).
def insert_right_way(num):
#your code here
num_str = str(num)
num_str = re.sub(r'([13579])(?=[13579])', r'1円-', num_str)
num_str = re.sub(r'([02468])(?=[02468])', r'1円*', num_str)
return num_str
def DashInsertII(num):
num_str = str(num)
num_str = re.sub(r'([02468])([02468])',r'1円*2円',num_str)
num_str = re.sub(r'([13579])([13579])',r'1円-2円',num_str)
return num_str
print insert_right_way(234467776667888)
print DashInsertII(234467776667888)
This would output:
234*4*67-7-76*6*678*8*8 ( what is desired)
234*467-776*6678*88 ( not what we wanted)
Comments
If I understand your problem - for 11223344 you need 1-12*23-34*4
def DashInsertII(num):
prev_even = ( int(num[0])%2 == 0 )
result = num[0]
for i in num[1:]:
curr_even = (int(i)%2 == 0)
if prev_even and curr_even:
result += '*'
elif not prev_even and not curr_even:
result += '-'
result += i
prev_even = curr_even
return result
print DashInsertII(raw_input())
2 Comments
raw_input() gives always string so I removed str() from version in question.
num_str.index(i)will always return the first occurrence. You can't expectind+1to point to the next number if index returned the first occurrence, instead of the succeeding occurrence.