Как я могу получить следующую строку в алфавитно-цифровом порядке в Python?
Вопрос
Мне нужна простая программа, которая по заданной строке возвращает мне следующую в буквенно-цифровом порядке (или просто в алфавитном порядке).
f("aaa")="aab"
f("aaZ")="aba"
И так далее.
Есть ли уже такая функция в одном из модулей?
Решение
Я не думаю, что есть встроенная функция для этого.Должно работать следующее:
def next_string(s):
strip_zs = s.rstrip('z')
if strip_zs:
return strip_zs[:-1] + chr(ord(strip_zs[-1]) + 1) + 'a' * (len(s) - len(strip_zs))
else:
return 'a' * (len(s) + 1)
Объяснение:вы найдете последний символ, который не является z
, увеличьте его и замените все символы после него на a
х.Если вся строка z
s, затем верните строку всех a
это на один длиннее.
Другие советы
Есть ли ответы на Как бы вы перевели это с Perl на Python? достаточный?Не 100% то, что вы спрашиваете, но близко...
Другое, более длинное, но, возможно, более читаемое и гибкое решение:
def toval(s):
"""Converts an 'azz' string into a number"""
v = 0
for c in s.lower():
v = v * 26 + ord(c) - ord('a')
return v
def tostr(v, minlen=0):
"""Converts a number into 'azz' string"""
s = ''
while v or len(s) < minlen:
s = chr(ord('a') + v % 26) + s
v /= 26
return s
def next(s, minlen=0):
return tostr(toval(s) + 1, minlen)
s = ""
for i in range(100):
s = next(s, 5)
print s
Вы преобразуете строку в число, где каждая буква представляет цифру по основанию 26, увеличиваете число на единицу и преобразуете число обратно в строку.Таким образом, вы можете выполнять произвольные математические операции со значениями, представленными в виде строк букв.
Параметр minlen определяет, сколько цифр будет в результате (поскольку 0 == a == aaaaa).
Отстой, что у Python нет того, что есть у Ruby: String#next
Итак, вот дерьмовое решение для работы с буквенно-цифровыми строками:
def next_string(s):
a1 = range(65, 91) # capital letters
a2 = range(97, 123) # letters
a3 = range(48, 58) # numbers
char = ord(s[-1])
for a in [a1, a2, a3]:
if char in a:
if char + 1 in a:
return s[:-1] + chr(char + 1)
else:
ns = next_string(s[:-1]) if s[:-1] else chr(a[0])
return ns + chr(a[0])
print next_string('abc') # abd
print next_string('123') # 124
print next_string('ABC') # ABD
# all together now
print next_string('a0') # a1
print next_string('1a') # 1b
print next_string('9A') # 9B
# with carry-over
print next_string('9') # 00
print next_string('z') # aa
print next_string('Z') # AA
# cascading carry-over
print next_string('a9') # b0
print next_string('0z') # 1a
print next_string('Z9') # AA0
print next_string('199') # 200
print next_string('azz') # baa
print next_string('Zz9') # AAa0
print next_string('$a') # $b
print next_string('$_') # None... fix it yourself
Не хорошо.У меня вроде работает.