【问题标题】:How can I find out how much storage it would take to store every number between 1 and 2^100?如何找出存储 1 到 2^100 之间的每个数字需要多少存储空间?
【发布时间】:2021-11-06 15:51:07
【问题描述】:

在代码中处理大量数字时,我完全是初学者,我知道这绝对是错误的方法,但这是我开始的。

import tqdm

try:
    total = 0
    for num in tqdm.tqdm(range(2**100), total=2**100):
        total += len(bin(num)) - 2
finally:
    with open('results.txt', 'w') as file:
        file.write(f'{total=}')

我得到的结果是:

0%|                  | 87580807/1267650600228229401496703205376 [00:39<159887459362604133471:34:24, 2202331.37it/s]

显然这种方法会花费太长的时间。我知道我可以尝试制作这种多核,但我认为这不会对速度产生太大影响。

我有什么选择?

使用像 C 这样的另一种语言会显着提高速度,从而需要数天或数小时而不是数小时吗?我可以使用其他方法/算法吗?

【问题讨论】:

  • 为什么要存储小于 2^100 的每个数字?
  • 这是一个编程测验问题吗?通常,您不应该实际存储它,而只是计算需要多少。
  • @rv.kvetch - tqdm 是 python 的进度条。而不是for num in range(..),你通过 tqdm 运行它,你会得到显示进度的 ascii 艺术。
  • 2**99(包括)到2**100(不包括)的数字都占用100位。显式循环所有这些数字来计算它们的位数简直是荒谬的,只需将 100 乘以范围的大小(对于所有先前的 2 次幂范围也是如此)。
  • @tdelaney 抓紧时间,现在就开始吧

标签: python large-data largenumber


【解决方案1】:

好的,我想通了。我用@jasonharper's approach

所以代码如下:

total = 0
for power in range(1, 101):
    total += ((int('1' * power, base=2) - int('1' + '0' * (power - 1), base=2)) + 1) * power

total 等于 125497409422594710748173617332225,表示存储 1 到 2^100 之间的每个数字所需的字节数。

在某些情况下,存储 1 到 2^100 之间的所有数字需要 ≈425414947195.2363 倍的地球总存储容量。

参考:https://www.zdnet.com/article/what-is-the-worlds-data-storage-capacity/

【讨论】:

    【解决方案2】:

    有趣的问题,但不是所有的问题都应该用蛮力解决,算法的一部分。查看您的问题,您似乎想计算直到某个n 所需的操作系统位数。现在,如果我们仔细观察,

    number of bits    total number of numbers we can represent
    1                  2**1 = 2
    2                  2**2 = 4
    3                  2**3 = 8
    4                  2**4 = 16
    5                  2**5 = 32
    ...
    

    所以总和是这样的

    1*2 + 2*2 + 3*2^2 + 4*2^3 + ...
    = 1 + 1*2^0 + 2*2^1 + 3*2^2 + 4*2^3 + ...
    = 1 + sum(k*2^(k-1)) with n from 1 to number of bits
    = 1 + (k*2^k - 2^k +1)
    = k*2^k - 2^k + 2
    

    因此可见几何级数。使用上面提到的总和,您可以确定公式

    import math
    
    def log2(x):
        return math.log(x) / math.log(2)
    
    def count_the_total_number_of_bits_till(n):
        neares_2_to_the_power = math.floor(log2(n))
        actual_number_of_bits_required = math.ceil(log2(n))
        
        sum_1 = ((neares_2_to_the_power * (2**neares_2_to_the_power)) - (2**neares_2_to_the_power) + 2)
        extra_sum = ((n - 2**neares_2_to_the_power) * (actual_number_of_bits_required))
        
        return sum_1 + extra_sum
    
    count_the_total_number_of_bits_till(2**10)
    

    你在做什么

    sum_ = 0
    for i in range(2**10): 
    #equivalent to 
    # count_the_total_number_of_bits_till(2**10)
        sum_ += len(bin(i)[2:])
    
    print(sum_)
    

    【讨论】:

      猜你喜欢
      • 2012-02-15
      • 2011-05-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多