简体   繁体   中英

What is the time complexity of the following code and how can I change it into linear or logarithmic time complexity?

long int num,max,mod,a,i,j;
cin>>num;
long int arr[num];
for(a=0;a<num;a++)
{
    cin>>arr[a];
}
max=arr[0]%arr[0];
for(i=0;i<num;i++)
{
    for(j=0;j<num;j++)
    {
        mod=arr[i]%arr[j];
        if(mod>max)
        {
            max=mod;
        }
    }
}
cout<<max;

I guess it is o(n^n) if not then please tell the time complexity and how?
And secondly can above code be transformed within linear or logarithmic time complexity. I am new in Data-Structures and algorithms field please help me out to solve this problem.
It will be great if you provide the code. Thank You :)

I don't understand why people are down voting this question. It's quite interesting.

If all inputs are positive numbers, the result you want is actually the second maximum value. I believe you can code it yourself. The proof is, the result has to be a number mod the maximum number, meanwhile the second maximum number mod the largest will give the optimal result, and it's equivalent to the second largest number. But be careful if there are more than one maximum numbers, you need to check the next largest one.

If some numbers are negative, it may be a little bit tricky. I assume the the result of modulus are always positive. (Although in C it doesn't work this way, but you can simply ignore these negative numbers in this case). First we need a copy of the array, while all negative numbers are converted to positive. Secondly, we need three numbers from the two array, the second maximum positive and the largest negative number (the one closest to 0) from the original array, and the largest number from the second array (all converted to positives). Compare the both the first two numbers mod the third number, output the larger one.

I made your original code working so you have a starting point.

template <class T>
T maxmod(vector<T> const& arr)
{
   auto max = numeric_limits<T>::lowest();
   for(auto x : arr)
      for (auto y : arr)
         max = std::max(max, y ? x%y : 0);
   return max;
}

Your problem is in fact quite interesting and depends on the sign conventions of the modulo operation (which was implementation defined up to C++03). Generally it should be possible to be solved in linear time by combining maximum searchs with some transformations. Here is a first linear attempt

template <class T>
T my_maxmod(vector<T> arr) // deep copy array because we change it
{
   T max = *std::max_element(arr.cbegin(), arr.cend()); // O(N)
   assert(max != 0); // TODO
   std::transform(arr.begin(), arr.end(), arr.begin(), [max](T const& a){ // O(N)
      return a % max; 
   }); 
   max = *std::max_element(arr.cbegin(), arr.cend()); // O(N)
   return max;
}

This does not work for all inputs. And you still have to think about negative numbers and so on. But it might give you a starting point. Here is a Demo

Good Luck.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM