📜  在给定的单调序列中查找元素位置

📅  最后修改于: 2021-09-16 11:09:10             🧑  作者: Mango

给定一个整数k和一个单调递增的序列:
f(n) = an + bn [log2(n)] + cn^3其中 ( a = 1, 2, 3, …), ( b = 1, 2, 3, …), ( c = 0, 1, 2、3、……)
这里,[log 2 (n)] 的意思是,将 log 取到基数 2 并将值向下舍入 因此,
如果 n = 1,则值为 0。
如果 n = 2-3,则值为 1。
如果 n = 4-7,则值为 2。
如果 n = 8-15,则值为 3。
任务是找到值n使得f(n) = k ,如果k不属于序列,则打印0

注:数值以64位表示,a、b、c三个整数不超过100。

例子:

朴素方法:给定 a、b、c 的值,为 n 的每个值找到 f(n) 的值并进行比较。

高效方法:使用二分搜索,选择n = (min + max) / 2其中minmaxn可能的最小值和最大值,然后,

  • 如果f(n) < k则增加n
  • 如果f(n) > k则递减n
  • 如果f(n) = kn是必需的答案。
  • 重复上述步骤,直到找到所需值或在序列中不可能。

下面是上述方法的实现:

C++
// C++ implementation of the approach
#include 
#include 
#define SMALL_N 1000000
#define LARGE_N  1000000000000000
using namespace std;
 
// Function to return the value of f(n) for given values of a, b, c, n
long long func(long long a, long long b, long long c, long long n)
{
    long long res = a * n;
    long long logVlaue = floor(log2(n));
    res += b * n * logVlaue;
    res += c * (n * n * n);
    return res;
}
 
long long getPositionInSeries(long long a, long long b,
                             long long c, long long k)
{
    long long start = 1, end = SMALL_N;
 
    // if c is 0, then value of n can be in order of 10^15.
    // if c!=0, then n^3 value has to be in order of 10^18
    // so maximum value of n can be 10^6.
    if (c == 0) {
        end = LARGE_N;
    }
    long long ans = 0;
 
    // for efficient searching, use binary search.
    while (start <= end) {
        long long mid = (start + end) / 2;
        long long val = func(a, b, c, mid);
        if (val == k) {
            ans = mid;
            break;
        }
        else if (val > k) {
            end = mid - 1;
        }
        else {
            start = mid + 1;
        }
    }
    return ans;
}
 
// Driver code
int main()
{
    long long a = 2, b = 1, c = 1;
    long long k = 12168587437017;
 
    cout << getPositionInSeries(a, b, c, k);
 
    return 0;
}


Python3
# Python 3 implementation of the approach
from math import log2, floor
SMALL_N = 1000000
LARGE_N = 1000000000000000
 
# Function to return the value of f(n)
# for given values of a, b, c, n
def func(a, b, c, n) :
     
    res = a * n
    logVlaue = floor(log2(n))
    res += b * n * logVlaue
    res += c * (n * n * n)
    return res
 
def getPositionInSeries(a, b, c, k) :
     
    start = 1
    end = SMALL_N
 
    # if c is 0, then value of n
    # can be in order of 10^15.
    # if c!=0, then n^3 value has
    # to be in order of 10^18
    # so maximum value of n can be 10^6.
    if (c == 0) :
        end = LARGE_N
     
    ans = 0
 
    # for efficient searching,
    # use binary search.
    while (start <= end) :
         
        mid = (start + end) // 2
        val = func(a, b, c, mid)
        if (val == k) :
            ans = mid
            break
     
        elif (val > k) :
            end = mid - 1
 
        else :
            start = mid + 1
         
    return ans;
 
# Driver code
if __name__ == "__main__" :
     
    a = 2
    b = 1
    c = 1
    k = 12168587437017
 
    print(getPositionInSeries(a, b, c, k))
 
# This code is contributed by Ryuga


PHP
 $k)
            $end = $mid - 1;
 
        else
            $start = $mid + 1;
    }
    return $ans;
}
 
// Driver code
$a = 2;
$b = 1;
$c = 1;
$k = 12168587437017;
 
print(getPositionInSeries($a, $b, $c, $k));
 
// This code is contributed by mits
?>


Javascript


输出:
23001

如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程学生竞争性编程现场课程