荷马史诗
题意:给n个单词出现的次数,然后给个k,让这个单词转换为二进制,然后求总长度最小,以及最大的一个转换后字符串的长度。
题解:我们发现这道题目,要求我们算出哈夫曼编码,也就是最短不重叠前缀的编码,那么我们就可以用上trie字典树的性质配合哈夫曼树进行处理.
#include<cstdio> #include<cstring> #include<algorithm> #include<map> #include<queue> #define ll long long using namespace std; struct point { ll x; ll y; friend bool operator < (point a, point b) { if(a.x==b.x) return a.y>b.y; return a.x > b.x; } }; priority_queue<point> qu; int main() { int n,k; while(~scanf("%d%d",&n,&k)) { for(int i=0;i<n;i++) { point x; scanf("%lld",&x.x); x.y=0; qu.push(x); } while((qu.size()-1)%(k-1)!=0) { point x; x.x=0; x.y=0; qu.push(x); } ll sum=0; while(qu.size()!=1) { ll t=0,deep=-1; for(int i=0;i<k;i++) { point r=qu.top(); t+=r.x; deep=max(deep,r.y); qu.pop(); } point e; e.x=t; e.y=deep+1; qu.push(e); sum+=t; } printf("%lld\n%lld\n",sum,qu.top().y); } }