strings are immutable (unchangeable). But you can index and join items.
mystring = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'
mystring = 'ABCDE'.join([mystring[:20],mystring[24:]])
'XXXXXXXXXXXXXXXXXXXXABCDEXXXXXXXXXXXXXX'
Do be careful as the string length "ABCDE" and the number of items you omit between mystring[:20], mystring[24:] need to be the same length.
Answer from Back2Basics on Stack Overflowstrings are immutable (unchangeable). But you can index and join items.
mystring = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'
mystring = 'ABCDE'.join([mystring[:20],mystring[24:]])
'XXXXXXXXXXXXXXXXXXXXABCDEXXXXXXXXXXXXXX'
Do be careful as the string length "ABCDE" and the number of items you omit between mystring[:20], mystring[24:] need to be the same length.
Strings are immutable in python! You'll have to split the string into three pieces and concatenate them together :)
mystring = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'
new_str = "ABCDE"
first_piece = mystring[0:20]
third_piece = mystring[24:len(mystring)]
final_string = first_piece + new_str + third_piece
how to substitute part of a string in python? - Stack Overflow
python - how do i replace a character in a string by range? - Stack Overflow
python - Replacing a character from a certain index - Stack Overflow
python - Remove characters in ranges from a string - Stack Overflow
For a simpler solution you could instead use rjust on the last 4 characters of the string, and fill it with # up to its original length:
s = 'TestName'
s[-4:].rjust(len(s), '#')
'####Name'
The problem with your function, is that you have to repeat the elements you want to use to replace as many times as replacements there will be. So you should do:
def maskify(cc):
c2 = cc.replace(cc[:-4], '#'*len(cc[:-4]))
return c2
yatu's solution using rjust() looks good, but str.replace() is a false friend. It works for a reasonably varied string, but if elements are repeated in the string it can fail (this is yatu's 2nd solution):
def maskify(cc):
c2 = cc.replace(cc[:-4], '#'*len(cc[:-4]))
return c2
print(maskify('12121212'))
gives,
########
I suggest 'building' the new string like this instead,
def maskify(cc):
mask = '#' * (len(cc)-4)
return mask+cc[-4:]
which gives the desired result,
####1212
If it's always the same position you're replacing, you could do something like:
>>> s = s[0:-2] + "A" + s[-1:]
>>> print s
abcdefghijAl
In the general case, you could do:
>>> rindex = -2 #Second to the last letter
>>> s = s[0:rindex] + "A" + s[rindex+1:]
>>> print s
abcdefghijAl
Edit: The very general case, if you just want to repeat a single letter in the replacement:
>>> s = "abcdefghijkl"
>>> repl_str = "A"
>>> rindex = -4 #Start at 4th character from the end
>>> repl = 3 #Replace 3 characters
>>> s = s[0:rindex] + (repl_str * repl) + s[rindex+repl:]
>>> print s
abcdefghAAAl
TypeError: 'str' object does not support item assignment
This is to be expected - python strings are immutable.
One way is to do some slicing and dicing. Like this:
>>> aa = 'abcdefghijkl'
>>> changed = aa[0:-2] + 'A' + aa[-1]
>>> print changed
abcdefghijAl
The result of the concatenation, changed will be another immutable string. Mind you, this is not a generic solution that fits all substitution scenarios.
A more generic approach would be to split the URL, replace the dot and then join:
In [1]: url = 'www.google.com/bla.bla'
In [2]: s = url.split("/")
In [3]: s[1] = s[1].replace(".", "")
In [4]: "/".join(s)
Out[4]: 'www.google.com/blabla'
In one line:
url = url[:-7] + (url[-7:].replace('.', ''))
As strings are immutable in Python, just create a new string which includes the value at the desired index.
Assuming you have a string s, perhaps s = "mystring"
You can quickly (and obviously) replace a portion at a desired index by placing it between "slices" of the original.
s = s[:index] + newstring + s[index + 1:]
You can find the middle by dividing your string length by 2 len(s)/2
If you're getting mystery inputs, you should take care to handle indices outside the expected range
def replacer(s, newstring, index, nofail=False):
# raise an error if index is outside of the string
if not nofail and index not in range(len(s)):
raise ValueError("index outside given string")
# if not erroring, but the index is still not in the correct range..
if index < 0: # add it to the beginning
return newstring + s
if index > len(s): # add it to the end
return s + newstring
# insert the new string between "slices" of the original
return s[:index] + newstring + s[index + 1:]
This will work as
replacer("mystring", "12", 4)
'myst12ing'
You can't replace a letter in a string. Convert the string to a list, replace the letter, and convert it back to a string.
>>> s = list("Hello world")
>>> s
['H', 'e', 'l', 'l', 'o', ' ', 'W', 'o', 'r', 'l', 'd']
>>> s[int(len(s) / 2)] = '-'
>>> s
['H', 'e', 'l', 'l', 'o', '-', 'W', 'o', 'r', 'l', 'd']
>>> "".join(s)
'Hello-World'
This might be faster. It's basically your solution but with list instead of strings. Since lists are mutable and doesn't need to be created every loop, it should be faster by quite much (maybe not for such few matches though).
sentence = "This is some example sentence where we remove parts"
matches = [(5, 10), (13, 18), (22, 27), (38, 42)]
def remove_matches(sentence, matches):
result = []
i = 0
for x, y in matches:
result.append(sentence[i:x])
i = y
result.append(sentence[i:])
return "".join(result)
This method might be quicker otherwise:
def remove_matches(sentence, matches):
return "".join(
[sentence[0:matches[i][0]] if i == 0 else
sentence[matches[i - 1][1]:matches[i][0]] if i != len(matches) else
sentence[matches[i - 1][1]::] for i in range(len(matches) + 1)
])
shorthend =sentence[:matches[0][0]]+ "".join([sentence[matches[i-1][1]:matches[0][0] for i in range(1, len(matches)]) + sentence[matches[len(matches)]:]
Since I' on my phone right now, I cannot debug but it should work :D