I'm trying to use a for
loop in order to formulate this:
expand('*+123456')
should return '1*2+3*4+5*6'
expand('++123')
should return '1+2+3'
expand('+*1234')
should return '1+2*3+4'
A symbol is chosen from the first two characters of the given string in an alternating fashion and placed between the proceeding digits.
Here is what I've been working with:
def expand(original):
var = ""
symbols = original[0:2]
for i in range(len(original)):
var = var + symbols + original[i]
return var
I realize that there also must be a original[2:]
but I don't know where I can fit this into in here.
I'm an amateur and I've been trying to figure out this question for a long time.
Yes, your function would be improved by adding [2:]
in there, but it could also do with losing the range(len(original))
. Whenever you find yourself writing range(len(something))
, you should step back and think about what you're actually trying to do.
In this case, you're looking for the characters in the string, and you can get those more straightforwardly with for x in string
. Here's a slightly improved version, taking those ideas into account:
def expand(original):
var = ""
symbols = original[:2]
for digit in original[2:]:
var += (digit + symbols)
return var
This stops you from getting the weird mixture of symbols at the beginning of the output, but it's still not perfect:
>>> expand('+*1234')
'1+*2+*3+*4+*'
We need to find a way of
We can use itertools.cycle to handle the first of these, and string slicing for the second:
from itertools import cycle
def expand(original):
var = ""
symbols = cycle(original[:2])
for digit in original[2:]:
var += (digit + next(symbols))
return var[:-1]
That works, but at some point, someone's going to pipe up and tell you you shouldn't use +
or +=
to build strings, because it's inefficient. If we build a list instead, and then use str.join()
to turn that into a string, we can improve things slightly:
from itertools import cycle
def expand(original):
chars = []
symbols = cycle(original[:2])
for digit in original[2:]:
chars.extend([digit, next(symbols)])
return "".join(chars[:-1])
However, we can do better than that. Rather than having to call next(symbols)
every time, we can use zip()
to get the next symbol and next digit a pair at a time:
from itertools import cycle
def expand(original):
chars = []
for symbol, digit in zip(cycle(original[:2]), original[2:]):
chars.extend([digit, symbol])
return "".join(chars[:-1])
... and that's probably enough :-)
EDIT: Since in a comment to another answer, you've said you're not allowed to import anything from the standard library (a rather silly restriction IMO, but there it is), you can use the Python implementation of cycle()
described at the link earlier in this answer:
def cycle(iterable):
# cycle('ABCD') --> A B C D A B C D A B C D ...
saved = []
for element in iterable:
yield element
saved.append(element)
while saved:
for element in saved:
yield element
... but you'll probably have to be prepared to convince your teacher that you understand it, which means you need to understand the yield keyword.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With