您的位置:首页 > 其它

Codeforces 752D Santa Claus and a Palindrome map应用

2016-12-29 17:16 260 查看
点击打开链接

题意:k个字符数串,每个字符串长度为n ,val<=1e4(1<=k,n<=1e5,n*k<=1e5) 求这些string拼接成回文时能得到的最大val

//组成回文:

类1:A!=R(A) A和R(A)放在字符串两边  && val > 0 

类2:两个相同回文 放在字符串两边 && val>0

中间可以放一个回文 从剩下中最大的未配对的选 maxn 或者 原来配对的回文中与最小负数val配对的哪一个 ans-minn 

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int inf=1e9;
struct cmp
{
bool operator()(int &a,int &b){
return a<b;
}
};
map<string,priority_queue<int,vector<int>,cmp> >mp;//每个string 按value 大->小
int n,k;
//ans-minn,ans+maxn
int main()
{

cin>>n>>k;
for(int i=1;i<=n;i++)
{
int x;
string s;
cin>>s>>x;
mp[s].push(x);
}
int ans=0,minn=0,maxn=0;//

for(map<string,priority_queue<int,vector<int>,cmp> >::iterator it=mp.begin();it!=mp.end();it++)
{
string s1=it->first;
string s2=s1;
reverse(s2.begin(),s2.end());
//不是回文两两配对即可
if(s1!=s2&&mp.find(s2)!=mp.end())
{
while(!mp[s1].empty()&&!mp[s2].empty())
{
int k=mp[s1].top()+mp[s2].top();
mp[s1].pop();
mp[s2].pop();
if(k>0)
{
ans+=k;
}
else
break;
}
}
else if(s1==s2)
{
while(mp[s1].size()>=2)
{
int x=mp[s1].top();
mp[s1].pop();
int y=mp[s1].top();
mp[s1].pop();

if(x+y>0)
{
ans+=x+y;
minn=min(minn,y);//inf+1,-inf 取消一个与最小负数配对的s1放中间
}
else
{
//其中一个回文可能放在中间
mp[s1].push(x);
mp[s1].push(y);
break;
}
}
}
}
for(map<string,priority_queue<int,vector<int>,cmp> >::iterator it=mp.begin();it!=mp.end();it++)
{
string s1=it->first;
string s2=s1;
reverse(s2.begin(),s2.end());
//从剩下的回文中选一个最大的放中间
if(s1==s2&&!mp[s1].empty())
{
maxn=max(maxn,mp[s1].top());
}
}
ans=max(ans-minn,ans+maxn);
cout<<ans<<endl;

return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: