断言一个数字是二进制的

Asserting that a number is in binary

我正在做作业,遇到了问题。我不得不将二进制数字串接起来。 假设我们加入了 (1, 3) - 1 是起始数字,3 表示我将使用另外 2 个数字(如果我加入了 (5, 4),id 将使用 5、6、7 和 8) 1 1 2 10 3 11 结果 11011

def num_to_2(number):
    num2 = 0
    exp = 0
    while number >= 1:
        num2 += (number % 2) * (10 ** exp)
        number = number // 2
        exp += 1
    return num2


def num_lenght(number):
    if number == 0:
        return 0
    lenght = 0
    while number >= 1:
        number /= 10
        lenght += 1
    return lenght


def joined(start, count):
    result = 0
    end = start + count - 1
    for i in range(end, start - 1, -1):
        number = num_to_2(i)
        res_lenght = num_lenght(result)
        result += number * (10 ** res_lenght)
    return result


def main():
    assert joined(1, 3) == 0b11011
    assert joined(10, 4) == 0b1010101111001101
    assert joined(8, 5) == 0b10001001101010111100
    assert joined(99, 2) == 0b11000111100100
    assert joined(999, 3) == 0b111110011111111010001111101001
    assert joined(1111, 1) == 0b10001010111

该函数工作正常,但它给我的结果没有 0b 前缀,我需要它来传递断言。我如何在那里添加它?还有:我不能使用字符串。

提前致谢!

编辑:我添加了其余代码,这样更有意义

嗯,不清楚你的老师所说的“不要使用字符串”是什么意思。我觉得这是一个很奇怪的作业,所以我做了,没有任何条件。

我不确定你应该从中学到什么,但它是:

def to_binary(number):
    b = 0
    while number >= 2**(b+1):
        b += 1
        
    while True:
        if number >= 2**b:
            yield 1
            number -= 2**b
        else:
            yield 0
        b -= 1
        if b < 0:
            return


def joined(start, count):
    result = 0
    for i in range(start, start + count):
        for digit in to_binary(i):
            result = (result << 1) + digit
    return result
    

def main():
    assert joined(1, 3) == 0b11011
    assert joined(10, 4) == 0b1010101111001101
    assert joined(8, 5) == 0b10001001101010111100
    assert joined(99, 2) == 0b11000111100100
    assert joined(999, 3) == 0b111110011111111010001111101001
    assert joined(1111, 1) == 0b10001010111

它实现了一个 to_binary() 函数,该函数将产生一个整数序列。然后 join 函数将结果二进制左移,并加上 1 或 0。

没有附加条件...

我已经解决了我的问题,我所要做的就是“手动”将伪二进制数转换为以 10 为基数的数字。这是我的代码:

def convert_to_2(number):
    num2 = 0
    exp = 0
    while number >= 1:
        num2 += (number % 2) * (10 ** exp)
        number = number // 2
        exp += 1
    return num2


def num_lenght(number):
    if number == 0:
        return 0
    lenght = 0
    while number >= 1:
        number /= 10
        lenght += 1
    return lenght


def joined(start, count):
    result = 0
    end = start + count - 1
    for i in range(end, start - 1, -1):
        number = convert_to_2(i)
        res_lenght = num_lenght(result)
        result += number * (10 ** res_lenght)
    result = convert_to_10(result)
    return result


def convert_to_10(number):
    num10 = 0
    exp = 0
    while number >= 1:
        num10 += (number % 10) * (2 ** exp)
        number = number // 10
        exp += 1
    return num10


def main():
    assert joined(1, 3) == 0b11011
    assert joined(10, 4) == 0b1010101111001101
    assert joined(8, 5) == 0b10001001101010111100
    assert joined(99, 2) == 0b11000111100100
    assert joined(999, 3) == 0b111110011111111010001111101001
    assert joined(1111, 1) == 0b10001010111


if __name__ == "__main__":
    main()

非常感谢你的帮助(:

这是一个通过所有断言的移位版本:

from math import ceil, log2
from functools import reduce

def join2(a,b):
    n = ceil(log2(b+1))
    return (a<<n) | b

def joined(start, count):
    return reduce(join2,range(start,start+count))

def main():
    assert joined(1, 3) == 0b11011
    assert joined(10, 4) == 0b1010101111001101
    assert joined(8, 5) == 0b10001001101010111100
    assert joined(99, 2) == 0b11000111100100
    assert joined(999, 3) == 0b111110011111111010001111101001
    assert joined(1111, 1) == 0b10001010111

您不必担心 0b 前缀,它只是 Python 源代码中表达数字文字的一种方式。他们本可以写 270x1b 而不是 0b11011,但二进制形式使 joined().

返回的整数值中预期的位模式更清楚

您可以使用整数的 .bit_length() 方法来了解用多少位来表示一个数字。这应该会使函数更简单一些。

def joined(start,count):
    result = 0
    for n in range(start,start+count):
        result <<= n.bit_length()       # offset by the number of bits
        result  |= n                    # add the number's bits
    return result

如果您不允许使用该方法,您可以编写自己的函数来执行此操作:

def bitLength(N): return 0 if not N else bitLength(N//2)+1

如果您也不允许使用按位运算符,则可以使用乘法和加法来实现:

def joined(start,count):
    result = 0
    for n in range(start,start+count):
        result  *= 2**bitLength(n)      # offset by the number of bits
        result  += n                    # add the number's bits
    return result