Reputation: 5972
Imagin I have three lists like:
l = ['2g_', '3k', '3p']
p = ['3f', '2y_', '4k', 'p']
s = ['12g', 'k_', '3p']
So:
>>> ''.join(i[1]*int(i[0])+i[2:] if i[0].isdigit() else i for i in l)
'gg_kkkppp'
>>> ''.join(i[1]*int(i[0])+i[2:] if i[0].isdigit() else i for i in p)
'fffyy_kkkkp'
>>> ''.join(i[1]*int(i[0])+i[2:] if i[0].isdigit() else i for i in s)
'2gk_ppp'
But what in list s:
2gk_ppp
must be ggggggggggggk_ppp
Upvotes: 1
Views: 437
Reputation: 82949
You can use a nested list comprehension / generator expression with regular expressions.
def join(lst):
return ''.join((int(n or 1) * c + r
for (n, c, r)
in (re.search(r"(\d*)(\w)(.*)", x).groups() for x in lst)))
First, use re.search
with (\d*)(\w)(.*)
to get the (optional) number, the character, and the (optional) rest for each string.
[re.search(r"(\d*)(\w)(.*)", x).groups() for x in lst]
For your second example, this gives [('3', 'f', ''), ('2', 'y', '_'), ('4', 'k', ''), ('', 'p', '')]
. Now, in the outer generator, you can use or
to provide a "default-value" in case the number is ''
(or use a ternary expression if you prefer: int(n) if n else 1
):
[int(n or '1') * c + r
for (n, c, r)
in (re.search(r"(\d*)(\w)(.*)", x).groups() for x in lst)]
This gives ['fff', 'yy_', 'kkkk', 'p']
. Finally, join to get fffyy_kkkkp
.
Upvotes: 4
Reputation: 1825
This variant is a little bit more imperative and simple to follow:
import re as regex
def process_template(template):
result = regex.match('(\d*)(.)(.*)', template)
if (result.group(1)):
return int(result.group(1)) * result.group(2) + result.group(3)
else:
return result.group(2) + result.group(3)
''.join([process_template(template) for template in ['3f', '2y_', '4k', 'p']])
Upvotes: 0