# Codeforces Round #297 (Div. 2)E. Anya and Cubes

275人阅读 评论(0)

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<map>
#include<vector>
using namespace std;

typedef long long ll;
ll n, k, s, tmp;
ll san[30], jc[1000], a[30];
map<ll, int>mp[2][30];  //2是归属范围 ，0代表前一半，1代表后一半
ll re[30],b[30], d[30], top;

ll cal(ll x)
{
if(x >= tmp) return -1;
else return jc[x];
}

void work(int x)
{
for(int i = 0; i < san[top]; i++)
{
int cnt = 0; //阶乘的个数
ll sum = 0;
int t = i, id = 0;
while(t)
{
if(t % 3 == 1)
{
cnt++; sum += d[id];
if (d[id] < 0)
{
sum = s + 1; break;
}
}
else if ((t % 3) == 2)
{
sum += b[id];
}
if (cnt > k || sum > s)break;
t /= 3; id++;
}
if (cnt <= k && sum <= s) mp[x][cnt][sum]++;
}
}

int main()
{
scanf("%I64d%I64d%I64d", &n, &k , &s);
san[0] = 1;
for(int i = 1; i < 30; i++)
{
san[i] = san[i-1] * 3;
}
jc[1] = 1;
for(int i = 2; ; i++)
{
jc[i] = jc[i-1] * i;
if(s / jc[i] <= i)
{
tmp = i+1;
break;
}
}
for(int i = 0; i < n ; i++)
{
scanf("%I64d", &a[i]);
re[i] = cal(a[i]);
}
for(int i = 0; i < n/2; i++)
{
b[i] = a[i];
d[i] = re[i];
}
top = n / 2;
work(0);

for (int i = n / 2; i < n; i++)
{
b[i - n / 2] = a[i];
d[i - n / 2] = re[i];
}
top = n - n / 2;
work(1);

ll ans = 0;
for(int i = 0; i <= k; i++)
{
for(map<ll,int>::iterator h = mp[0][i].begin(); h != mp[0][i].end(); h++)
{
pair<ll, int> it = *h;
for (int j = 0; j + i <= k; j++)
{
if (mp[1][j].count(s - it.first))
ans += (ll)it.second * mp[1][j][s - it.first];
}
}
}
printf("%I64d\n", ans);
return 0;
} 

0
0

* 以上用户言论只代表其个人观点，不代表CSDN网站的观点或立场
个人资料
• 访问：36383次
• 积分：1353
• 等级：
• 排名：千里之外
• 原创：103篇
• 转载：1篇
• 译文：0篇
• 评论：5条
最新评论