社区讨论
求改(信息队勿入)不要题解 必关
B3851[GESP202306 四级] 图像压缩参与者 4已保存回复 6
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 6 条
- 当前快照
- 1 份
- 快照标识符
- @m3x2azun
- 此快照首次捕获于
- 2024/11/25 21:26 去年
- 此快照最后确认于
- 2025/11/04 13:55 4 个月前
CPP
// https://www.luogu.com.cn/problem/B3851
#include<bits/stdc++.h>
using namespace std;
// 将一行字符串以2位为单位拆分成多个子字符串
vector<string> splite(string s) {
vector<string> res;
for(int i=0; i<s.size()/2; i++) {
string tmp = s.substr(2*i,2);
res.push_back(tmp);
}
return res;
}
// 计数器
map<string, int> counter;
void counting(vector<string> ss) {
for(auto s : ss) {
counter[s]++;
}
}
// 排序规则
bool order_rule(pair<string, int> p1, pair<string, int> p2) {
if(p1.second>p2.second) {
return true;
}
else if(p1.second<p2.second) {
return false;
}
else {
if(p1.first<p2.first) {
return true;
}
else {
return false;
}
}
}
// 用来排序的临时存储
vector<pair<string, int>> counter_pairs;
// 把16进制转10进制
int c16to10(char x) {
return (x <= '9' ? x - '0' : x - 'A' + 10);
}
// 16进制减法(返回值为10进制)
int minus16(string a, string b) {
int a10 = c16to10(a[0]) * 16 + c16to10(a[1]);
int b10 = c16to10(b[0]) * 16 + c16to10(b[1]);
return a10-b10;
}
// 只存前16名
map<string, char> ziped16;
// 存所有的
map<string, char> ziped;
// 计算每个颜色对应的压缩后的颜色是什么
void ziping() {
for(int i=0; i<16; i++) {
string ziped_key = counter_pairs[i].first;
ziped[ziped_key] = (i<=9 ? '0'+i : 'A'+i-10);
ziped16[ziped_key] = (i<=9 ? '0'+i : 'A'+i-10);
}
for(int i=16; i<counter_pairs.size(); i++) {
string ziped_key = counter_pairs[i].first;
// 在ziped16中,二分查找到比ziped_key相等或大的第一个位置
auto pos = ziped16.lower_bound(ziped_key);
// 没有更大的
if(pos == ziped16.end()) {
pos--;
ziped[ziped_key] = pos->second;
}
// 没有更小的
else if(pos == ziped16.begin()) {
ziped[ziped_key] = pos->second;
}
else{
string greater_key = pos->first;
pos--;
string less_key = pos->first;
if(minus16(greater_key, ziped_key) < minus16(ziped_key, less_key)) {
ziped[ziped_key] = ziped[greater_key];
}
else if(minus16(greater_key, ziped_key) > minus16(ziped_key, less_key)) {
ziped[ziped_key] = ziped[less_key];
}
else {
ziped[ziped_key] = ziped[min(greater_key, less_key)];
}
}
}
}
int n;
vector<string> dt; // 缓存题目输入,用于最后的输出
int main() {
cin >> n;
while(n--) {
string s;
cin >> s;
dt.push_back(s);
vector<string> tt = splite(s);
counting(tt);
}
for(auto s : counter) {
counter_pairs.push_back(s);
}
sort(counter_pairs.begin(), counter_pairs.end(), order_rule);
// 题目要求的一行输出
for(int i=0; i<16; i++) {
cout << counter_pairs[i].first;
}
cout << endl;
ziping();
for(auto s : dt) {
vector<string> tt = splite(s);
for(auto ss : tt) {
cout << ziped[ss];
}
cout << endl;
}
return 0;
}
回复
共 6 条回复,欢迎继续交流。
正在加载回复...