zoukankan      html  css  js  c++  java
  • 【LOJ4632】[PKUSC2018]真实排名

    【LOJ4632】[PKUSC2018]真实排名

    题面

    终于有题面啦!!!

    题目描述

    小 C 是某知名比赛的组织者,该比赛一共有 (n) 名选手参加,每个选手的成绩是一个非负整数,定义一个选手的排名是:成绩不小于他的选手的数量(包括他自己)。例如如果 (3) 位选手的成绩分别是 ([1,2 ,2]) ,那么他们的排名分别是 ([3,2,2])

    拥有上帝视角的你知道所有选手的实力,所以在考试前就精准地估计了每个人的成绩,设你估计的第 (i) 个选手的成绩为(A_i)​,且由于你是上帝视角,所以如果不发生任何意外的话,你估计的成绩就是选手的最终成绩。

    但是在比赛当天发生了不可抗的事故(例如遭受到了外星人的攻击),导致有一些选手的成绩变成了最终成绩的两倍,即便是有上帝视角的你也不知道具体是哪些选手的成绩翻倍了,唯一知道的信息是这样的选手恰好有 (k) 个。

    现在你需要计算,经过了不可抗事故后,对于第 (i) 位选手,有多少种情况满足他的排名没有改变。

    由于答案可能过大,所以你只需要输出答案对 (998244353) 取模的值即可。

    输入格式

    第一行两个正整数 (n,k)

    第二行 (n) 个非负整数 (A_1..A_n)

    输出格式

    输出(n)行,第 (i) 行一个非负整数 (ans_i)​,表示经过不可抗事故后,第 (i) 位选手的排名没有发生改变的情况数。

    样例

    样例输入

    3 2
    1 2 3
    

    输出

    3
    1
    2
    

    提示与说明

    对于(10\%)的数据,有 (1leq nleq 151)

    对于(35\%)的数据,有 (1leq nleq 10^3)

    另有(10\%)的数据,满足每个人的成绩都互不相同

    另有(10\%)的数据,满足(A_ileq 10^5)

    另有(10\%)的数据,满足(k=85)(0leq A_ileq 6000)

    对于(100\%)的数据,有(1leq k < nleq 10^5)(0leq A_ileq 10^9)

    题解

    其实还是挺容易的qaq,只不过细节比较多

    分别考虑你现在计算的那个位置选不选

    如果不选,可以选比它大的或小于它(frac 12)的。

    那么假如我们钦定它选,则必须动([a_i,2a_i])的,

    计算一下有多少,其余的随便选就行了。

    每一种情况都预处理阶乘用组合数就好啦

    代码

    #include <iostream>
    #include <cstdio>
    #include <cstdlib>
    #include <cstring> 
    #include <cmath> 
    #include <algorithm>
    using namespace std; 
    inline int gi() {
        register int data = 0, w = 1;
        register char ch = 0;
        while (!isdigit(ch) && ch != '-') ch = getchar(); 
        if (ch == '-') w = -1, ch = getchar();
        while (isdigit(ch)) data = 10 * data + ch - '0', ch = getchar();
        return w * data; 
    }
    const int Mod = 998244353; 
    const int MAX_N = 1e5 + 5;
    int fpow(int x, int y) { 
        int res = 1;
        while (y) {
            if (y & 1) res = 1ll * res * x % Mod; 
            y >>= 1; 
            x = 1ll * x * x % Mod; 
        } 
        return res; 
    } 
    int N, K, A[MAX_N], fac[MAX_N << 1], inv[MAX_N << 1]; 
    int C(int n, int m) {
        if (m > n || m < 0) return 0; 
        return 1ll * fac[n] * inv[m] % Mod * inv[n - m] % Mod;
    } 
    int X1[MAX_N], X2[MAX_N], ans[MAX_N]; 
    
    int main () { 
        N = gi(), K = gi(); 
        fac[0] = 1; for (int i = 1; i <= 2 * N; i++) fac[i] = 1ll * fac[i - 1] * i % Mod; 
        inv[2 * N] = fpow(fac[2 * N], Mod - 2); for (int i = 2 * N - 1; ~i; i--) inv[i] = 1ll * inv[i + 1] * (i + 1) % Mod; 
        for (int i = 1; i <= N; i++) A[i] = gi(), X1[i] = A[i], X2[i] = A[i] << 1; 
        sort(&X1[1], &X1[N + 1]); 
        sort(&X2[1], &X2[N + 1]); 
        for (int i = 1; i <= N; i++) {
            if (A[i] == 0) { ans[i] = C(N, K); continue; } 
            int x = N - 1 - (lower_bound(&X2[1], &X2[N + 1], A[i]) - X2 - 1) - (N - (lower_bound(&X1[1], &X1[N + 1], A[i]) - X1)); 
            int y = (N - (lower_bound(&X1[1], &X1[N + 1], A[i]) - X1) + 1) - 1 - (N - (lower_bound(&X1[1], &X1[N + 1], A[i]) - X1)); 
            ans[i] = C(x, y) * C(N - 1 - x, K - y) % Mod; 
        }
        for (int i = 1; i <= N; i++) {
            if (A[i] == 0) continue;
            int x = N - 1 - (lower_bound(&X2[1], &X2[N + 1], A[i] << 1) - X2 - 1) - (N - (lower_bound(&X1[1], &X1[N + 1], A[i] << 1) - X1) + 1); 
            int y = N - (lower_bound(&X1[1], &X1[N + 1], A[i]) - X1) - (N - (lower_bound(&X1[1], &X1[N + 1], A[i] << 1) - X1) + 1); 
            ans[i] = (ans[i] + C(x, y) * C(N - 1 - x, K - y - 1) % Mod) % Mod;
        }
        for (int i = 1; i <= N; i++) printf("%d
    ", ans[i]); 
        return 0; 
    } 
    
  • 相关阅读:
    【转】[fix] Wireshark error: There are no interfaces on which a capture can be done. on Mac OS X
    【转载】Linux 文件系统的目录结构
    postgreSQL使用
    [转载] Linux启动过程详解-《别怕Linux编程》之八
    冒泡排序
    java值类型和引用类型
    冒泡排序法与二分查找法
    关系型数据库
    SQList的建表并添加数据练习
    数据存储——SQLite数据库存储
  • 原文地址:https://www.cnblogs.com/heyujun/p/10288805.html
Copyright © 2011-2022 走看看