NOIP TEST

1 permut
1.1 题目描述
求由1到n一共n个数字组成的所有排列中,逆序对个数为k 的有多少个
1.2 输入格式
第一行为一个整数T,为数据组数。
以下T行每行两个整数n,k,意义如题目所述。
1.3 输出格式
对每组数据输出答案对10000取模后的结果
1.4 Sample Input
1
4 1
1.5 Sample Output
3
1.6 数据范围及约定
对于30% 的数据,满足n<12
对于所有数据,满足n<1000,k<1000,T<10

题解:
30%:直接DFS暴力。
100%:DP,f[i][j]表示由1到i组成的全排列中,逆序对数为j个的方案数。对于每个i就相当于把i这个数插入到i-1的全排列中,最多可生成i-1个逆序对,即f[i][j]即为sigema f[i-1][k] min(0,j-i+1)<=k<=j )前缀和优化即可

随后附上我的代码。

2 beautiful
2.1 题目描述
一个长度为n的序列,对于每个位置i的数a[i]都有一个优美值,其定义是:找到序列中最长的一段[l,r],满足l<=i<=r,且[l,r]中位数为ai(我们比较序列中两个位置的数的大小时,以数值为第一关键字,下标为第二关键字比较。这样的话[l,r]的长度只有可能是奇数),r-l+1 就是i的优美值。
接下来有Q个询问,每个询问[l,r]表示查询区间[l,r]内优美值的最大值。
2.2 输入格式
第一行输入n接下来n个整数,代表ai 接下来Q,代表有Q个区间接下来Q行,每行两个整数l,r(l<=r),表示区间的左右端点
2.3 输出格式
对于每个区间的询问,输出答案
2.4 Sample Input
8
16 19 7 8 9 11 20 16
8
3 8
1 4
2 3
1 1
5 5
1 2
2 8
7 8
2.5 Sample Output
7
3
1
3
5
3
7
3
2.6 数据范围及约定
对于30%的数据,满足n,Q<=50
对于70%的数据,满足n,Q<=2000
对于所有数据,满足n<=2000, Q<=100000,ai<=200

随后附上我的代码。

题解:
30%:O(n^3)无脑暴力即可。
70%:O(n^2)预处理,枚举中位数i,先向前枚举j,如果大于中位数则t++,如果小于等于中位数则t–,每次更新p[t]为j,再向后枚举j,记得将t清零,如果大于等于中位数则t–,如果小于中位数则t++,如果p[t]存在一个下标的话,就更新答案为max(ans,j-p[t]+1)。
100%:用线段树进行查询的优化即可。

3 subset
3.1 题目描述
一开始你有一个空集,集合可以出现重复元素,然后有Q个操作
1. add s
在集合中加入数字s。
2. del s
在集合中删除数字s。保证s存在
3. cnt s
查询满足a&s=a条件的a的个数
3.2 输入格式
第一行一个整数Q 接下来Q 行,每一行都是3 个操作中的一个
3.3 输出格式
对于每个cnt 操作输出答案
3.4 Sample Input
7
add 11
cnt 15
add 4
add 0
cnt 6
del 4
cnt 15
3.5 Sample Output
1
2
2
3.6 数据范围及约定
对于30%的数据满足,1<=n<=1000
对于100%的数据满足,1<=n<=200000 ,0<=s<=2^16

题解:
30%:模拟暴力即可。
100%:述我直言,由于数据即水,30分暴力即可AC!在此附上标程一份。

#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
#include <climits>
#include <cmath>
#include <utility>
#include <set>
#include <map>
#include <queue>
#include <ios>
#include <iomanip>
#include <ctime>
#include <numeric>
#include <functional>
#include <fstream>
#include <string>
#include <vector>
#include <bitset>
#include <cstdarg>
#include <complex>
using namespace std;

typedef long long ll;
typedef unsigned int uint;
typedef unsigned long long ull;
typedef long double ld;
#define pair(x, y) make_pair(x, y)
#define runtime() ((double)clock() / CLOCKS_PER_SEC)

inline int read() {
    static int r, sign;
    static char c;
    r = 0, sign = 1;
    do c = getchar(); while (c != '-' && (c < '0' || c > '9'));
    if (c == '-') sign = -1, c = getchar();
    while (c >= '0' && c <= '9') r = r * 10 + (int)(c - '0'), c = getchar();
    return sign * r;
}

template <typename T>
inline void print(T *a, int n) {
    for (int i = 1; i < n; ++i) cout << a[i] << " ";
    cout << a[n] << endl;
}
#define PRINT(_l, _r, _s, _t) { cout << #_l #_s "~" #_t #_r ": "; for (int _i = _s; _i != _t; ++_i) cout << _l _i _r << " "; cout << endl; }

#define N 300
int q, a[N + 1][N + 1];
char cmd[10];

int main(int argc, char *argv[]) {
    freopen("subset19.in", "r", stdin);
    freopen("subset19.out", "w", stdout);

    scanf("%d", &q);
    while (q--) {
        int x, w = 1;
        scanf("%s%d", cmd, &x);
        if (cmd[0] == 'd') w = -1;
        if (cmd[0] != 'c') {
            int pre = x >> 8, suf = x & 255, comp = 255 ^ suf;
            a[pre][suf] += w;
            for (int y = comp; y != 0; y = (y - 1) & comp)
                a[pre][y | suf] += w;
        } else {
            int pre = x >> 8, suf = x & 255;
            int ans = a[0][suf];
            for (int y = pre; y != 0; y = (y - 1) & pre)
                ans += a[y][suf];
            printf("%d\n", ans);
        }
    }

    fclose(stdin);
    fclose(stdout);
    return 0;
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值