当无限接近零时,循环结束?

时间:2017-09-24 02:59:54

标签: algorithm

所以我想知道以下问题的时间复杂性。正确的解决方案是它的O(logN);如果这个循环终止,我理解这一点。但是因为我们只有一半,所以理论上我可以真正接近0,但永远不会结束?!

int a = 0, i = N;
        while (i > 0) {
            a += i;
            i /= 2;
        }

3 个答案:

答案 0 :(得分:1)

是的,循环实际上会结束。由于iint,因此当您将i减半时,您将执行整数除法。此除法的结果将向下舍入到最接近的整数。 例如:

int i=3;
int j= i/2;
// j really is 1.5, but we're performing integer division
// so the result will be j =1

如果我们考虑运行N=5的程序,我们会:

第一次迭代:

i=5;
i = i/2 = 5/2 = 2.5 = 2; //Round 2.5 down

第二次迭代:

i=2
i = i/2 = 2/2 = 1;

第三次迭代:

i=1;
i = i/2 = 1/2 = 0.5 = 0; //Round 0.5 down, loop finishes

答案 1 :(得分:1)

重要的是要记住,您要划分int,而不是浮点值,因此没有小数部分。相反,任何剩余部分都将被丢弃。因此,一旦你下降到1,其中一半是0.5,因为你只取整数部分,你将得到0.因此,这最终会完成。

例如,如果您从10开始:

10 / 25

5 / 22,余数为1 - 余数被丢弃 - i2

2 / 21

1 / 20,余数为1 - 余数被丢弃 - i0

答案 2 :(得分:1)

由于您使用整数运算,我确实会转到0。 这是使用picoc

的交互式示例
$ picoc -i
starting picoc v2.1
picoc> #include <stdio.h>
#include <stdio.h>
picoc> int a=0, i=10;
int a=0, i=10;
picoc> a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a=10 i=5
picoc> a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a=15 i=2
picoc> a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a=17 i=1
picoc> a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a += i; i /= 2; printf("a=%d i=%d\n",a,i);
a=18 i=0

此时你的循环已经终止。