Let's say I have two strings, s1 = "1234" and s2 ="34567", so longest common suffix prefix between s1 and s2 is "34". I want to know if there exists any pythonic way to get this matching part ("34") real quick.
I can do it in a naive way like this one below, but I would love to know if there is an interesting library function or algorithm to get this done.
s1 = "1234"
s2 = "34567"
length1 = len(s1)
length2 = len(s2)
length = (length1 if length1<= length2 else length2)
for i in reversed(range(0, length)):
if s1[-i - 1:] == s2[:i + 1]:
print(s1[-i - 1:])
break
elif i > 0:
continue
else:
print("no common suffix prefix")
Output:
34
I want something compact and smart!
The logic in your algorithm is about as straightforward as you can get, but you can definitely compactify the notation. For example, checking a prefix of size n against a suffix of size n is simply:
s1[-n:] == s2[:n]
The ternary operator you use to check string lengths is
min(len(s1), len(s2))
A range can go backwards by itself. The reverse of range(x) is
range(x - 1, -1, -1)
You can create an iterator that checks this for each decreasing value of n and return the first non-zero result. Luckily, next accepts a second argument that represents the default if the iterator is empty:
common = next((s2[:n] for n in range(min(len(s1), len(s2)) - 1, -1, -1) if s1[-n:] == s2[:n]), '')
That's the obligatory one-liner. A more legible solution might be:
def common_fix(s1, s2):
steps = range(min(len(s1), len(s2)) - 1, -1, -1)
return next((s2[:n] for n in steps if s1[-n:] == s2[:n]), '')
As a rule, keep your functionally and printing separate. Get a value, then process it (whether by printing or something else)
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