「暑期訓練」「Brute Force」 Multiplication Table (CFR256D2D)

SamHX發表於2018-08-10

題意

給定一矩陣M,Mij=ij,求第k大值。

分析

這個題不看題解我是想不到二分的,但是二分當然屬於暴力,不爽不要玩;)
實際上,現在做題解的時候,意識到一個有意思的結論:第k大xxx往往都與二分思想有關。我們還會與分治思想再見的。
具體做法:二分第k大值p。求陣列中p元素是第幾大即可。

程式碼

#include <bits/stdc++.h>
#define MP make_pair
#define PB push_back
#define fi first
#define se second
#define ZERO(x) memset((x), 0, sizeof(x))
#define ALL(x) (x).begin(),(x).end()
#define rep(i, a, b) for (int i = (a); i <= (b); ++i)
#define per(i, a, b) for (int i = (a); i >= (b); --i)
#define QUICKIO                  \
    ios::sync_with_stdio(false); \
    cin.tie(0);                  \
    cout.tie(0);
using namespace std;
using ll = long long;
using ull = unsigned long long;
using pi = pair<int, int>;
using pii = pair<int, pi>;

template<typename T>
T read()
{
    T tmp; cin>>tmp;
    return tmp;
}

int main()
{
    ll n,m,k; cin>>n>>m>>k;
    ll l=0,r=(ll)n*m+1;
    //cout<<r<<endl;
    while(r-l>1)
    {
        ll mid=l+(r-l)/2;
        ll cnt=0;
        rep(i,1,n)
        {
            cnt+=min(ll(ceil(double(mid)/i)-1),(ll)m);
        }
        if(cnt+1>k)
        {
            r=mid;
        }
        else l=mid;
    }
    cout<<(l+r)/2<<endl;
    return 0;
}

相關文章