Reputation: 17007
It seems to me that the default behavior for replacement of matched strings with a larger string is to begin replacement at the starting position of the matched string ie.
import re
string = "Parameter Value: 0.12345"
new = re.sub(r'(\d|\.)+', '%0.5f' % 100.123, string)
print string+'\n'+new
Gives the output:
Parameter Value: 0.12345
Parameter Value: 100.12300
Which appears to be the default behavior, but is there a way to get:
Parameter Value: 0.12345
Parameter Value: 100.12300
Instead so that the decimal place is lined up with where it was before replacement?
Upvotes: 1
Views: 590
Reputation: 180461
You will have to add more logic deciding whether to ljust or rjust etc.. but this should get you started. Might pay to move '{:.5f}'.format(100.123)
outside the regex and use the length of that as a deciding factor
import re
s = "Parameter Value: 0.12345"
new = re.sub(r'(\d|\.)+', '{:.5f}'.format(100.123), s)
s = s.split(" ")
new = new.split(" ")
a, b = s[-1], new[-1]
ln = len(max(a, b, key=len))
print("{}{:>{ln}}\n{}{}".format(" ".join(s[:-1]), a, " ".join(new[:-1]), b, ln=ln)))
Parameter Value: 0.12345
Parameter Value: 100.12300
Another way is getting the start and end index of the string that is going to be replaced, it is pretty easy adjust the string once you know exactly where the string is and how long the string to be replaced is in comparison to rep:
import re
f = 100.123
rep = '{:.5f}'.format(f)
s = "Parameter Value: 0.12345"
inds = next(re.finditer(r'(\d|\.)+', s))
start, end = inds.span()
print(start,end)
(21, 28)
ln = end - start
Upvotes: 2
Reputation: 52141
Taking a clue from Padraic's comment I tried this and it's working
>>> string = "Parameter Value: 0.12345"
>>> s = string.split(":")
>>> num = 100.123
>>> ":".join([s[0],("%0.5f"%(num)).rjust(len(s[1]))])
'Parameter Value: 100.12300'
>>> string
'Parameter Value: 0.12345'
Upvotes: 1