找出一个等于输入数的四次方的数字

时间:2019-01-19 17:58:00

标签: c algorithm

接收输入数字,找到一种有效的算法来查找是否存在和  以4的幂数表示的一对数字等于该数字。 例如:


Input: val=337

x=3^4=81

y=4^4=256

81+256=337

另一个例子是:

val=641
x=5^4=625
y=2^4=16
val=x+y=641

我正尝试使用C代码解决此问题。

我考虑了这个问题,我只是想对所有可能的数字进行迭代,使它们的4的幂将提供一个小于请求输入的数字,并检查所有可能数字的总和是否与此匹配数字。

似乎效率不高。 拜托,你能帮忙吗? 谢谢

4 个答案:

答案 0 :(得分:1)

#include<stdio.h>
#include<math.h>

long long int binarySearch(long long int limit){
    long long int low = 1,high = sqrt(sqrt(limit));
    long long int mid = 0;
    long long int ans = 0;
    while(low <= high){
        mid = low + (high - low) / 2;
        long long int raiseToFour = mid * mid * mid * mid;
        if(raiseToFour > limit) high = mid - 1;
        else if(raiseToFour < limit){
            low = mid + 1;
            ans = mid;
        }else{
            ans = mid;
            break;
        }
    }

    return ans;
}

int main(void) {
    long long int sum = 337;
    long long int i;
    long long int left = 1, right = binarySearch(sum);
    while(left <= right){
        long long int leftFourthPower  = left * left * left * left;
        long long int rightFourthPower = right * right * right * right;
        if(leftFourthPower + rightFourthPower == sum){
            printf("%lld ^ 4 + %lld ^ 4 = %lld",left,right,sum);
            break;
        }else if(leftFourthPower  + rightFourthPower > sum){
            right--;
        }else{
            left++;
        }
    }


    return 0;
}

它给出:

3 ^ 4 + 4 ^ 4 = 337
  • 好吧,从1sqrt(sqrt(sum))进行二进制搜索,以找到幂数最接近sum的4 次幂的数字。
  • 现在,使用2指针方法(leftright,其中right是二进制搜索函数的上限),找到第4个 幂加起来等于给定的和。如果总和超过,则我们递减right指针,如果它小于给定的总和,则增加left指针。
  • 空间复杂度为 O(1)

答案 1 :(得分:0)

一种简单的启发式方法是检查输入sqrt(sqrt(n))小于或等于n的值。因此,该算法的复杂度为"choose 2 from sqrt(sqrt(n))" = O(sqrt(n))

答案 2 :(得分:0)

解决方案1:O(n)的时间和O(n)的空间

伪代码

  1. 使用预先计算的值初始化哈希表:对于每个项x,将其存储在哈希表x^4
  2. 搜索对:对于每个x,检查val-x^4是否在哈希表中

如果第2步找到匹配项,则存在满足要求的一对。

复杂度

用于构建哈希表的复杂度为O(n),而用于扫描的复杂度为O(n)。此外,所需的额外空间为O(n)

实施

对于 c 实现,可以使用unordered_set

  • 为简单起见,假定所有值都是唯一的。如果不能保证,则必须对值进行计数(以避免x^4+x^4=val在输入中x仅出现一次)。

解决方案2:O(n*log(n))时间和O(1)空间

伪代码

  1. 就地对所有输入值进行排序:按升序对数组的值进行排序
  2. 搜索对:对于每个x,二进制搜索sqrt(val-x^4)

如果第2步找到匹配项,则存在满足要求的一对。

自慰

排序的复杂度为O(n*log(n))。每次二进制搜索需要O(log(n))时间并执行n次。因此,整体时间复杂度为O(n*log(n))

实施

对于 c 实现,可以使用qsort

答案 3 :(得分:0)

可以使用以下公式快速完成此操作:

enter image description here

我们可以计算出幂4的最大数,这就是开始。 为了最大程度地减少for循环,我们可以在数目减半时结束。解决方案还支持其他功能。 下面的完整代码(C#)

public static void Main(string[] args)
    {
        const int raisedPow = 4;
        long num = 3262811042;

        Console.WriteLine("{0}", num);
        int start = (int) Math.Pow(Math.E, (Math.Log(num) / Math.Log(Math.E)) / raisedPow);
        int end = (int) Math.Pow(Math.E, (Math.Log(num/2) / Math.Log(Math.E)) / raisedPow);
        int y = -1;
        int stepCount = 0;

        for (int i = start; i>end;i--)
        {
            stepCount++;
            long rest = (long) (num - (Math.Pow(i, raisedPow)));
            int j = (int) Math.Round(Math.Pow(Math.E, (Math.Log(rest) / Math.Log(Math.E)) / raisedPow));
            if (rest - (Math.Pow(j, raisedPow)) == 0)
            {
                Console.WriteLine("{0} {1}", i, j);

                y = j;
            }
        }
        Console.WriteLine("steps {0}", stepCount);
        if (y == -1) Console.WriteLine("No Solution");

        Console.ReadKey();
    }