Educational Codeforces Round 32 E

E. Maximum Subsequence

You are given an array a consisting of n integers, and additionally an integer m. You have to choose some sequence of indices b1, b2, ..., bk (1 ≤ b1 < b2 < ... < bk ≤ n) in such a way that the value of is maximized. Chosen sequence can be empty.

Print the maximum possible value of .

Input

The first line contains two integers n and m (1 ≤ n ≤ 35, 1 ≤ m ≤ 109).

The second line contains n integers a1, a2, ..., an (1 ≤ ai ≤ 109).

Output

Print the maximum possible value of .

Examples

Input

4 45 2 4 1

Output

3

Input

3 20199 41 299

Output

19

Note

In the first example you can choose a sequence b = {1, 2}, so the sum is equal to 7 (and that‘s 3 after taking it modulo 4).

In the second example you can choose a sequence b = {3}.

有一串数列   可以从中任取k个数字   令k个数字相加除摸m   求最大的值。

n<=35  如果直接dfs的话  是2^35看到会爆掉,所以可以分两次  这样最大也就是2^18  才二十多万看到能过了。

先求出前半部分的,在求出后半部分的。然后在其中一个里找某个数  使的更接近m就行,这样就要用到二分了

总的复杂度是2^(n/2)*log(n/2)  足够算出这个题目了。

 1 #include <bits/stdc++.h>
 2 #define ll long long
 3 using namespace std;
 4 const int N = 1<<18;
 5 ll a[40], b[40], c[N], d[N], k, ans, sum, n, m;
 6 void dfs(int x) {
 7     if(x == ans + 1) {
 8         c[++k] = sum%m;
 9         return ;
10     }
11     sum += b[x]; dfs(x + 1);
12     sum -= b[x]; dfs(x + 1);
13 }
14 int main() {
15     cin >> n >> m;
16     for(int i = 1; i <= n; i ++) cin >> a[i], a[i] %= m, b[i] = a[i];
17     ans = n/2;
18     dfs(1);
19     ll n1 = k;
20     for(int i = 1; i <= k; i ++) d[i] = c[i];
21     memset(c, 0, sizeof(c));
22     ans = n; k = 0;
23     dfs(n/2+1);
24     ll MAX = -1;
25     sort(d+1,d+n1+1);
26     for(int i = 1; i <= k; i ++) {
27         int t = lower_bound(d+1,d+n1,m-c[i]-1)-d;
28         while(c[i]+d[t]>=m)t--;
29         MAX=max(MAX,c[i] + d[t]);
30     }
31     printf("%lld\n",MAX);
32     return 0;
33 }
时间: 2024-11-08 08:31:42

Educational Codeforces Round 32 E的相关文章

Educational Codeforces Round 32

Educational Codeforces Round 32 A. Local Extrema 直接模拟一下- B. Buggy Robot x和y轴无关,分别考虑即可 C. K-Dominant Character 想到了做法,但是没过... 就是记录一下相同字母的最大间距,然后取最小的即可- 不过要注意首尾的处理,WA了好多发都没注意到这个问题=_=|| D. Almost Identity Permutations k很小,直接组合数+错排搞一下就好了

Educational Codeforces Round 32 E 巨型背包

思路:n只有35, 将n份为2部分,一部分为前n/2个物品的取舍(取或不去), 另一部分为剩下物品的取舍,复杂度为2^(n/2),枚举左边的数,然后二分右边的数找到最优解,写lower_bound需要去重,手写二分就不需要了 AC代码: #include "iostream" #include "iomanip" #include "string.h" #include "stack" #include "queue

Educational Codeforces Round 32 E. Maximum Subsequence

E. Maximum Subsequence 题意: n 个数,选出其中  k 个数,使得他们的和对 m 取模后最大. 输出这个最大值. tags:注意到 n 很小, 所以折半枚举. // E #include<bits/stdc++.h> using namespace std; #pragma comment(linker, "/STACK:102400000,102400000") #define rep(i,a,b) for (int i=a; i<=b; +

Educational Codeforces Round 21 G. Anthem of Berland(dp+kmp)

题目链接:Educational Codeforces Round 21 G. Anthem of Berland 题意: 给你两个字符串,第一个字符串包含问号,问号可以变成任意字符串. 问你第一个字符串最多包含多少个第二个字符串. 题解: 考虑dp[i][j],表示当前考虑到第一个串的第i位,已经匹配到第二个字符串的第j位. 这样的话复杂度为26*n*m*O(fail). fail可以用kmp进行预处理,将26个字母全部处理出来,这样复杂度就变成了26*n*m. 状态转移看代码(就是一个kmp

Educational Codeforces Round 26 D. Round Subset(dp)

题目链接:Educational Codeforces Round 26 D. Round Subset 题意: 给你n个数,让你选其中的k个数,使得这k个数的乘积的末尾的0的个数最大. 题解: 显然,末尾乘积0的个数和因子2和因子5的个数有关. 然后考虑dp[i][j]表示选i个数,当前因子5的个数为j时,能得到因子2最多的为多少. 那么对于每个数,记录一下因子2和5的个数,做一些01背包就行了. 1 #include<bits/stdc++.h> 2 #define mst(a,b) me

Educational Codeforces Round 23 F. MEX Queries(线段树)

题目链接:Educational Codeforces Round 23 F. MEX Queries 题意: 一共有n个操作. 1.  将[l,r]区间的数标记为1. 2.  将[l,r]区间的数标记为0. 3.  将[l,r]区间取反. 对每个操作,输出标记为0的最小正整数. 题解: hash后,用线段树xjb标记一下就行了. 1 #include<bits/stdc++.h> 2 #define ls l,m,rt<<1 3 #define rs m+1,r,rt<&l

Educational Codeforces Round 23 D. Imbalanced Array(单调栈)

题目链接:Educational Codeforces Round 23 D. Imbalanced Array 题意: 给你n个数,定义一个区间的不平衡因子为该区间最大值-最小值. 然后问你这n个数所有的区间的不平衡因子和 题解: 对每一个数算贡献,a[i]的贡献为 当a[i]为最大值时的 a[i]*(i-l+1)*(r-i+1) - 当a[i]为最小值时的a[i]*(i-l+1)*(r-i+1). 计算a[i]的l和r时,用单调栈维护.具体看代码,模拟一下就知道了. 然后把所有的贡献加起来.

Educational Codeforces Round 25 F. String Compression(kmp+dp)

题目链接:Educational Codeforces Round 25 F. String Compression 题意: 给你一个字符串,让你压缩,问压缩后最小的长度是多少. 压缩的形式为x(...)x(...)  x表示(...)这个出现的次数. 题解: 考虑dp[i]表示前i个字符压缩后的最小长度. 转移方程解释看代码,这里要用到kmp来找最小的循环节. 当然还有一种找循环节的方式就是预处理lcp,然后通过枚举循环节的方式. 这里我用的kmp找的循环节.复杂度严格n2. 1 #inclu

Educational Codeforces Round 23 E. Choosing The Commander (trie)

题目链接: Educational Codeforces Round 23 E. Choosing The Commander 题意: 一共有n个操作. 1.  插入一个数p 2.  删除一个数p 3.  询问有多少个数 使得 x^p<l 题解: 对于前两种操作用01trie就能解决. 对于对三个操作,我们考虑在trie上搜索. 1.  当l的bit位是1时,那边bit位是p的字数全部的数都会小于l,(因为p^p=0) 2.  当l的bit为是0时,那边只能向bit位是p的子树中搜. 这样算下来