面试问题 - 查找数字

时间:2010-08-31 19:22:48

标签: algorithm

我刚刚在SE职位面试中得到了这个问题,除了蛮力外,我不太清楚如何回答这个问题:

给定自然数N,找到两个数字A和P,这样:

N = A +(A + 1)+(A + 2)+ ... +(A + P-1)

P应尽可能最大。

Ex:对于N = 14,A = 2且P = 4

N = 2 +(2 + 1)+(2 + 2)+(4 + 2-1) N = 2 + 3 + 4 + 5

有什么想法吗?

5 个答案:

答案 0 :(得分:17)

如果N是偶数/奇数,我们在总和中需要偶数/奇数个奇数。这已经是可能解决方案数量的一半。例如。对于N = 14,检查P为奇数的任何组合都没有意义。

重写给定的公式,我们得到:

N = A + (A+1) + (A+2) + ... + (A+P-1)
    = P*A + 1 + 2 + ... + (P-1)
    = P*A + (P-1)P/2 *
    = P*(A + (P-1)/2)
    = P/2*(2*A + P-1)

最后一行意味着N必须可以被P / 2整除,这也排除了许多可能性。例如。 14只有这些除数:1,2,7,14。所以P的可能值是2,4,14和28. 14和28由于显而易见的原因而被统治(事实上,任何高于N / 2的P都可以忽略)。

这应该比蛮力方法快得多。

(*前n个自然数之和为n(n + 1)/ 2)

答案 1 :(得分:3)

通过面试问题,考虑问题的目的通常是明智的。如果我问你这个问题,那不是因为我认为你知道解决方案,而是我想看到你找到解决方案。重新制定问题,制定影响,设计已知的内容,......这就是我希望看到的内容。

  • 如果你只是坐下来告诉我“我不知道如何解决它”,你立刻就没能通过面试。

  • 如果你说:我知道如何通过强力解决它,我知道它可能会很慢,我会给你一些提示或帮助你开始。如果这没有帮助,你很可能会失败(除非你展示一些非凡的技能来弥补你在一般问题分析领域可能缺乏的事实,例如你将展示如何为许多核心实现并行化的解决方案或实施在GPU上。)

  • 如果你给我一个现成的解决方案,但你无法得到它,我会给你另一个类似的问题,因为我对解决方案不感兴趣,我对你的想法很感兴趣。

    < / LI>

答案 2 :(得分:1)

A + (A+1) + (A+2) + ... + (A+P-1)简化为P*A + (P*(P-1)/2) resp P*(A+(P-1)/2)

因此,您可以枚举N的所有除数,然后将每个除数P测试为以下内容:

A = (N-(P*(P-1)/2))/P(解决了A的第一次简化)是一个整数吗? (我认为它应该是一个整数,否则它将是微不足道的。)如果是这样,将其作为解决方案返回。

答案 3 :(得分:0)

可以使用0-1背包解决方案解决。

观察:N / 2 + N / 2 + 1> Ñ

所以我们的系列是1,2,...,N / 2

考虑所有元素的W = N和vi = 1的约束,我认为这通常映射到0-1背包,O(n ^ 2)

答案 4 :(得分:0)

这是一个O(n)解决方案。

它使用算术级数之和的属性。 S =差*(first_term + last_term)/ 2

这里我们的总和为N,差值为P,第一项为A.

操纵上面的等式我们得到一些方程式,我们可以将P从1迭代到n - 1以获得有效的A。

def solve(n,p):
return (2*n - (p**2) + p)/(2*p)

def condition(n,p,a):
if (2*n == (2*a*p) + (p**2) - p) and (a*-1 < 0):
    return True
else:
    return False

def find(n):
for x in xrange(n,-1,-1):
    a = solve(n,x)
    if condition(n,x,a):
        return n,x,a