Algorithm 不同数字计数

Algorithm 不同数字计数,algorithm,count,distinct,digit,Algorithm,Count,Distinct,Digit,是否可以在恒定时间内对数字中的不同数字进行计数O(1) 假设n=1519输出应该是3,因为有3不同的数字(1,5,9) 我在O(N)time中做过,但是有人知道如何在O(1)time中找到它吗?我假设N是N的位数。如果n的大小是无限的,则通常不能在O(1)时间内完成 考虑数字n=11111…111,有2万亿位。如果我将其中一个数字从1切换到2,如果不以某种方式查看每个数字,就无法发现这一点。因此,处理一个2万亿位数的数字必须至少进行2万亿次运算,一般来说,一个N位数的数字必须至少进行N次运算 然

是否可以在恒定时间内对数字中的不同数字进行计数
O(1)

假设
n=1519
输出应该是
3
,因为有
3
不同的数字
(1,5,9)


我在
O(N)
time中做过,但是有人知道如何在
O(1)
time中找到它吗?

我假设
N
N
的位数。如果
n
的大小是无限的,则通常不能在O(1)时间内完成

考虑数字
n=11111…111
,有2万亿位。如果我将其中一个数字从
1
切换到
2
,如果不以某种方式查看每个数字,就无法发现这一点。因此,处理一个2万亿位数的数字必须至少进行2万亿次运算,一般来说,一个
N
位数的数字必须至少进行
N
次运算


然而,对于几乎所有的数字,简单的
O(N)
算法完成得非常快,因为当你得到10个不同的数字时,你可以立即停止。几乎所有长度足够的数字都有10位数字:例如,在查看前100位数字后,不以答案“10”终止的概率约为0.00027,在前1000位数字后,不以答案“10”终止的概率约为1.7e-45。但不幸的是,在看到有人真的对这个问题给出了严肃的答案后,我宁愿在这里重复我自己的欺骗,这是@SimonNickerson描述的答案的一个特例:

O(1)是不可能的,除非你是在基数2上,因为那样的话,除0之外的每个数字都有1和0,因此我的“解”不仅适用于整数

编辑


2^k-1怎么样?这不都是1吗


该死!真的。。。我应该知道,当事情看起来如此简单时,它不知何故是有缺陷的。。。如果我把所有0个案例都包括在内,我也应该把所有1个案例都包括在内

幸运的是,这种情况可以很快进行测试(如果加法和按位and被认为是一种O(1)运算):如果x是要测试的数字,则通过以下方式计算y:
y=(x+1)和x
。如果
y=0
,则
x=2^k-1
。因为这是唯一一种需要通过加法翻转所有位的情况。当然,这有点缺陷,因为位长度超过了总线宽度,位运算符不再是O(1),而是O(N)

同时,我认为它可以降到O(logN),将数字分成总线宽度大小的块,并将相邻的块放在一起,重复直到只剩下一个:如果测试的数字中没有0,最后一个也将是满1


编辑2:我错了。。。这仍然是O(N)。

您必须访问每个数字。常数意味着您将使用相同的时间来计算n=1,就像您将n=123456789O(n)用于什么n?n的大小?位数(即日志)?预先计算所有值,然后你可以通过一个简单的索引操作在O(1)中查找结果:)对于有限的边界,有可能:建立一个列表,将列表中的数字保存在里面,只要你的内存持续,你就可以在O(1)中…还有,我有一个新想法。。。对于基数2,所有数字都可以用O(1)::)::)表示!(此处插入epic evil genius Lough)如果给定的数字与底层机器字相符,则有一个简单的O(1)算法;也就是说,按照Jon Skeet的建议(开玩笑地说),在查找表中查找答案。对于N号将军,我想我的观点仍然是。对不起,我不明白你的意思。无论单词大小是什么,它都是固定的有限大小。因此,任何必须处理任意大小数据的算法的性能都与单词的大小无关。对单词进行算术是没有帮助的,即使这样的运算可以用每个单词O(1)来完成,因为表示数字n所需的单词数本身就是O(n)。2^k-1怎么样?这不都是1吗?该死!真的。。。我应该知道,当事情看起来如此简单时,它不知何故是有缺陷的。。。如果我把所有0个案例都包括在内,我也应该把所有1个案例都包括在内。幸运的是,这种情况可以很快进行测试(如果加法和按位and被认为是一种O(1)运算):如果x是要测试的数字,则通过以下方式计算y:
y=(x+1)和x
。如果
y=0
,则
x=2^k-1
。因为这是唯一需要翻转所有位的情况。当然,这有点缺陷,因为位长度超过总线宽度,位运算符不再是O(1),而是O(N)。。。