如何检查一个数字是否是基数b的幂?

5 投票
6 回答
15286 浏览
提问于 2025-04-17 18:45

在Python中,如何检查一个数字n是否是以b为底的精确幂?

注意:这个检查需要适用于任何作为参数给出的底数。

以下是我的想法:

假设n和底数都是大于0的整数。

import math
def is_power(n,base):
    return math.log(n,base) == base**n

6 个回答

0
>>> def isPower(n, b):
...   return b**int(math.log(n, b)+.5)==n
... 
>>> isPower(128, 2)
True
>>> isPower(129, 2)
False
>>> isPower(3**10, 3)
True
>>> isPower(3**129, 3)
True
>>> isPower(10**500, 10)
True
>>> isPower(10**(10**6), 10)
True
>>> isPower(1,1)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 2, in isPower
ZeroDivisionError: float division by zero


编辑: 这段代码在 1,1 的情况下确实会出错:

我会让提问者自己决定是想简单修复一下,还是重新写一下他的需求。

5

一个非常简单的解决方案可以这样写:

def ispower(n, base): 

    if n == base:
        return True

    if base == 1:
        return False

    temp = base

    while (temp <= n):
        if temp == n:
            return True
        temp *= base

    return False

结果:

>>> ispower(32, 2)
True
>>> ispower(81, 3)
True
>>> ispower(625, 5)
True
>>> ispower(50, 5)
False
>>> ispower(32, 4)
False
>>> ispower(2,1)
False
>>> ispower(1,1)
True
10

首先,假设你有一个特定的对数运算符(很多编程语言只提供以 10e 为底的对数),那么 logab 可以通过 logxb / logxa 来计算(这里的 x 是你所用语言提供的底数)。

Python 更厉害,因为它可以直接计算任意底数的对数,而不需要上面那种复杂的公式。

所以,不管怎样,你都有方法来获取特定底数的对数。如果 b 在底数 a 下的对数是一个整数(注1),那么 b 就是 a 的幂。

我会从以下代码开始,现在加上了边界情况的检测:

# Don't even think about using this for negative powers :-)

def isPower (num, base):
    if base in {0, 1}:
        return num == base
    power = int (math.log (num, base) + 0.5)
    return base ** power == num

例如,看看下面这个完整的程序,它展示了这个过程是如何运作的:

import math

def isPower (num, base):
    if base in {0, 1}:
        return num == base
    power = int (math.log (num, base) + 0.5)
    return base ** power == num

print isPower (127,2)       # false
print isPower (128,2)       # true
print isPower (129,2)       # false
print

print isPower (26,3)        # false
print isPower (27,3)        # true
print isPower (28,3)        # false
print isPower (3**10,3)     # true
print isPower (3**129,3)    # true
print

print isPower (5,5)         # true
print isPower (1,1)         # true
print isPower (10,1)        # false

如果你担心浮点运算的问题,你可以通过重复乘法来实现,但你应该测试这种方法的性能,因为在软件中可能会比在硬件中慢得多。对于像 isPower(128,2) 这样的情况影响不大,但对于 isPower(verybignum,2) 可能就会成为一个问题。

对于上面代码的非浮点版本:

def isPower (num, base):
    if base in {0, 1}:
        return num == base
    testnum = base
    while testnum < num:
        testnum = testnum * base
    return testnum == num

但要确保在你的最大数字和最小底数上进行测试,以确保不会出现性能上的意外。


(注1) 请记住,浮点数的不精确性可能意味着结果不一定是 完全 的整数。你可能需要使用“足够接近”的比较方法。

撰写回答