当前位置: 首页 > 知识库问答 >
问题:

范围内squarefree数的计数

刘玉石
2023-03-14
1, 2, 3, 5, 6, 7, 10, 11, 13, 14, 15 ...
1 <= X,Y <= 10^9

0 <= |X-Y| <= 10^6

x=10 , Y=15 
ans=5

我的方法是生成所有素数直到squareroot(10^9)(埃拉托色尼筛),并检查给定范围内的每个数是否可被素数的平方整除。这些数字的计数从范围的长度中减去,以给出平方自由数。

但是这种方法在复杂度上超时了,请建议一些其他的方法

共有1个答案

牟辰龙
2023-03-14

使用包含-排除原则:

f(n)=1...n中非平方自由数的个数。我们只在素数的平方上做包含-排除,以避免对平方的平方进行超算。

我们有:

f(n) = n / 4      => these are divisible by 4, so NOT square-free
       +
       n / 9      => these are divisible by 9, so NOT square-free
       + 
       n / 25     => these are divisible by 16, so NOT square-free
       +
       ...
       -
       n / (4*9)  => these are divisible by both 4 and 9, so we overcounted
       -
       n / (4*25) => these are divisible by both 4 and 25, so we overcounted 
       -
       ...

这样的效率有多高?

我们只需要素数p,这样p^2<=10^9,意思是p<31623。这已经不是很多素数,任何琐碎的筛子(甚至可能是试除)都应该足够快。然后应用包含-排除,这也会很快,因为平方素数的乘积会很快变大,所以在很多情况下可以过早终止(n/something=0,每当something>n)。

为了了解您为什么能够过早终止,请将上面的内容改写为:

f(n) = n / (2^2) -
       n / (2^2*3^2) +
       n / (2^2*3^2*5^2) -  <= this becomes 0 very fast. 
                               When it does, 
                               backtrack and increment the previous term.
                               For example, if this were 0,
                               you'd do - n / (2^2*5^2) next
       ...
 类似资料:
  • 我医生看起来像 我想拥有超过 100个文档在50到100个之间少于100个文档我尝试使用不同的聚合,但我不知道如何在另一个聚合的计数上进行范围聚合 谢谢你的帮助,

  • 我参加了一个编程比赛,我无法解决问题,问题是: 给定一个n个整数的数组A,我需要计算给定范围内求逆的次数。提供一个整数m,它表示范围的数量,然后是m行,在每一行中给出两个整数li和ri。 我们必须只计算指定范围内的反转,即从li到ri(包括0)的反转(基于0的索引)。 如果 A[i] 两个元素 A[i] 和 A[j] 添加到反演中 反转是: 输入: 输出: 约束: 我知道在整个数组上计算O(nlo

  • 假设您有一个间隔列表,例如[(0 4),(1 3),(2 5),(2 6)]。此列表未排序。然后给您一个范围,如[1 5]。您必须返回适合范围内的间隔数。在这个问题中,它将返回2。((1 3)和(2 5)) 间隔列表保持不变,但我们最多得到100000个查询,每个查询由一个范围组成。对于每个范围查询,我们必须返回适合其中的间隔数。 在研究之后,我读到了间隔树。但是,您只能查询与任何给定范围重叠的间

  • 对于我的Java类,我正在编写一个小程序,首先选择一个介于1和100之间的数字。然后,它会提示用户开始猜测正确的。如果用户对的猜测过高或过低,程序会打印出一个新范围,供他们在该范围内进行猜测。如果用户输入或,程序只需重新要求用户输入,但不会以任何方式更改范围。 示例输出(当机密号为20时)如下所示: 该项目似乎已经基本完成,但只有一个例外。其中一个要求是,当用户键入的超出我们给定的1和100范围时

  • 问题内容: 在这里,最低年龄是10岁,因此我们首先计算范围10-15。该范围内有5个学生。对于第二个范围,我们需要找到年龄> 15(即18)。因此,第二个范围是18-23,依此类推。如果能自动计算范围并计算该范围内的数据,我将不胜感激。 问题答案: 您可以在SUM()语句中使用条件来获取该条件所在的计数。我会计算年龄在BETWEEN()必要范围内的条件。试试这个: 这只会返回一行,但是它将包含您需

  • 本文向大家介绍在C ++中计算给定范围内的阶乘数,包括了在C ++中计算给定范围内的阶乘数的使用技巧和注意事项,需要的朋友参考一下 给定范围是从变量保存的整数值开始,比如说从开始直到变量结束,而任务是计算给定范围内可用的阶乘数的总数。 什么是阶乘数 数字的阶乘是通过将数字中的数字相乘,同时将数字的值减1来计算的。它由符号“!”表示 即0!,1!,2!,3!,5!,....等 0阶乘!和1!始终为1