Как преобразовать целое число в основе к строке?

Python позволяет легкое создание целого числа от строки данной основы через

int(str, base). 

Я хочу выполнить инверсию: создание строки от целого числа, т.е. Я хочу некоторую функцию int2base(num, base), таким образом, что:

int(int2base(x, b), b) == x

Имя функции / порядок аргументов неважно.

Для любого числа x и основа b это int() примет.

Это - легкая функция для записи: на самом деле это легче, чем описание его в этом вопросе. Однако я чувствую, что должен пропускать что-то.

Я знаю о функциях bin, oct, hex, но я не могу использовать их по нескольким причинам:

  • Те функции не доступны на более старых версиях Python, с которым мне нужна совместимость с (2,2)

  • Я хочу общее решение, которое можно назвать тем же путем к различным основаниям

  • Я хочу позволить основания кроме 2, 8, 16

Похожие страницы

185
задан Community 23 May 2017 в 02:34
поделиться

6 ответов

Если вам нужна совместимость с древними версиями Python, вы можете либо использовать gmpy (который действительно включает быструю, совершенно общую функцию преобразования int-to-string, и может быть построен для таких древних версий - возможно, вам придется попробовать более старые версии, так как последние не тестировались для старых версий Python и GMP, только для несколько более новых), либо, для меньшей скорости, но большего удобства, использовать код Python - например, наиболее просто:

import string
digs = string.digits + string.ascii_letters


def int2base(x, base):
    if x < 0:
        sign = -1
    elif x == 0:
        return digs[0]
    else:
        sign = 1

    x *= sign
    digits = []

    while x:
        digits.append(digs[int(x % base)])
        x = int(x / base)

    if sign < 0:
        digits.append('-')

    digits.reverse()

    return ''.join(digits)
90
ответ дан 23 November 2019 в 05:52
поделиться

Отличные ответы! Думаю, ответ на мой вопрос был "нет". Я не упустил какое-то очевидное решение. Вот функция, которую я буду использовать, чтобы обобщить хорошие идеи, выраженные в ответах.

  • разрешает отображение символов вызывающим абонентом (позволяет кодировать base64)
  • проверяет наличие отрицательных и нулевых значений
  • отображает комплексные числа в кортежи строк


def int2base(x,b,alphabet='0123456789abcdefghijklmnopqrstuvwxyz'):
    'convert an integer to its string representation in a given base'
    if b<2 or b>len(alphabet):
        if b==64: # assume base64 rather than raise error
            alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
        else:
            raise AssertionError("int2base base out of range")
    if isinstance(x,complex): # return a tuple
        return ( int2base(x.real,b,alphabet) , int2base(x.imag,b,alphabet) )
    if x<=0:
        if x==0:
            return alphabet[0]
        else:
            return  '-' + int2base(-x,b,alphabet)
    # else x is non-negative real
    rets=''
    while x>0:
        x,idx = divmod(x,b)
        rets = alphabet[idx] + rets
    return rets

20
ответ дан 23 November 2019 в 05:52
поделиться
>>> import string
>>> def int2base(integer, base):
        if not integer: return '0'
        sign = 1 if integer > 0 else -1
        alphanum = string.digits + string.ascii_lowercase
        nums = alphanum[:base]
        res = ''
        integer *= sign
        while integer:
                integer, mod = divmod(integer, base)
                res += nums[mod]
        return ('' if sign == 1 else '-') + res[::-1]


>>> int2base(-15645, 23)
'-16d5'
>>> int2base(213, 21)
'a3'
1
ответ дан 23 November 2019 в 05:52
поделиться

Python не имеет встроенной функции для печати целого числа с произвольной базой. Если хотите, вам придется написать свой собственный.

16
ответ дан 23 November 2019 в 05:52
поделиться
def baseN(num,b,numerals="0123456789abcdefghijklmnopqrstuvwxyz"):
    return ((num == 0) and numerals[0]) or (baseN(num // b, b, numerals).lstrip(numerals[0]) + numerals[num % b])

ref: http://code.activestate.com/recipes/65212/

Имейте в виду, что это может привести к

RuntimeError: maximum recursion depth exceeded in cmp

для очень больших целых чисел.

87
ответ дан 23 November 2019 в 05:52
поделиться

http://code.activestate.com/recipes/65212/

def base10toN(num,n):
    """Change a  to a base-n number.
    Up to base-36 is supported without special notation."""
    num_rep={10:'a',
         11:'b',
         12:'c',
         13:'d',
         14:'e',
         15:'f',
         16:'g',
         17:'h',
         18:'i',
         19:'j',
         20:'k',
         21:'l',
         22:'m',
         23:'n',
         24:'o',
         25:'p',
         26:'q',
         27:'r',
         28:'s',
         29:'t',
         30:'u',
         31:'v',
         32:'w',
         33:'x',
         34:'y',
         35:'z'}
    new_num_string=''
    current=num
    while current!=0:
        remainder=current%n
        if 36>remainder>9:
            remainder_string=num_rep[remainder]
        elif remainder>=36:
            remainder_string='('+str(remainder)+')'
        else:
            remainder_string=str(remainder)
        new_num_string=remainder_string+new_num_string
        current=current/n
    return new_num_string

Вот еще один по той же ссылке

def baseconvert(n, base):
    """convert positive decimal integer n to equivalent in another base (2-36)"""

    digits = "0123456789abcdefghijklmnopqrstuvwxyz"

    try:
        n = int(n)
        base = int(base)
    except:
        return ""

    if n < 0 or base < 2 or base > 36:
        return ""

    s = ""
    while 1:
        r = n % base
        s = digits[r] + s
        n = n / base
        if n == 0:
            break

    return s
4
ответ дан 23 November 2019 в 05:52
поделиться
Другие вопросы по тегам:

Похожие вопросы: