Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to convert a string of arbitrary base back to decimal?

Tags:

python

I'm trying to convert a decimal number to an arbitrary base and back to decimal. I found this code below from another question:

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

When I convert a decimal to hex:

in_base16 = int2base(number, 16)

it works, but when I try to convert that result back to decimal (base 10):

back_to_10 = int2base(in_base16, 10)

... it gives me the error:

    if x<=0:
    TypeError: '<=' not supported between instances of 'str' and 'int'

It can't convert a string back to a number for some reason. I don't understand why. How would I convert a number of an arbitrary base back to decimal?

like image 642
Un1 Avatar asked Oct 12 '25 11:10

Un1


2 Answers

If base-n is up to 36, you can use the built-in int(str,base).

>>> int('AA', 32)
330
like image 98
Vinícius Figueiredo Avatar answered Oct 15 '25 04:10

Vinícius Figueiredo


You'll need one function for converting from int to base (returning a string that represents a number in that base -- here up to base 36):

digits = '0123456789abcdefghijklmnopqrstuvwxyz'

def int2base(n, b=2, digits=digits):
    "convert integer n to base b"
    if n < 0:
        raise ValueError("no negative numbers")
    if n < b:
        return digits[n]
    res = []
    q = n
    while q:
        q, r = divmod(q, b)
        res.append(digits[r])
    return ''.join(reversed(res))

and another function for converting back from base to int:

def base2int(s, base=2, digits=digits):
    "convert string s representing a number in base to int (base 10)"
    if not (2 <= base <= len(digits)):
        raise ValueError("base must be >= 2 and <= %d" % len(digits))
    res = 0
    for i, v in enumerate(reversed(s)):
        digit = digits.index(v)
        res += digit * (base ** i)
    return res
like image 22
thebjorn Avatar answered Oct 15 '25 04:10

thebjorn