CCF CSP题解:解压缩(202305-3)

链接和思路

OJ链接:传送门

本题要为压缩文件写解码器,需求很明确,不存在太多的复杂度优化的空间,主要的难度是将业务需求仔细实现。由于位操作并非经常涉及,所以可能因大小端问题或粗心而出错。

AC代码

#include 
#include 
#include 

using namespace std;

vector<unsigned char> bin_code;
string input;
unsigned int cur_idx = 0;
string output;

void print_output() {
    for (int i = 0; i < ceil(output.length() / 16.0); i++) {
        cout << output.substr(16 * i, 16) << endl;
    }
}

void init() {
    int s;
    cin >> s;
    bin_code.resize(s);
    for (int i = 0; i < (ceil(s / 8.0)); ++i) {
        string line;
        cin >> line;
        input.append(line);
    }
    for (int i = 0; i < input.length(); i += 2) {
        char tmp[3];
        tmp[0] = input[i];
        tmp[1] = input[i + 1];
        tmp[2] = 0;
        unsigned v;
        sscanf(tmp, "%x", &v);
        bin_code[i / 2] = v;
    }
}

void lead_in() {
    while (bin_code[cur_idx++] & 0x80);
//     cout << cur_idx << endl;
}

void literal_handle() {
//    cout << "start literal handle: cur_idx is " << cur_idx << endl;
    unsigned l = bin_code[cur_idx++] >> 2;
    if (l < 60) {
        l++;
    } else {
        int tmp = (int) l - 59;
        l = 0;
        for (int i = 0; i < tmp; i++) {
            l = l | (bin_code[cur_idx++] << (8 * i));
        }
        l++;
    }
    output.append(input.substr(cur_idx * 2, l * 2));
    cur_idx += l;
//    print_output();
//    cout << "---------" << endl;
//    cout << "end literal handle: cur_idx is " << cur_idx << endl;
}

void recall_handle() {
    unsigned type = bin_code[cur_idx] & 0x3;
//    cout << "start recall handle, type: " << type << endl;
    unsigned l = 0, o = 0;
    if (0x1 == type) {
        l = ((bin_code[cur_idx] >> 2) & 0x7) + 4;
        o = bin_code[cur_idx] & 0xe0;
        o = o << 3;
        o |= bin_code[++cur_idx];
    } else {
        l = (bin_code[cur_idx] >> 2) + 1;
        o |= bin_code[++cur_idx];
        o |= (bin_code[++cur_idx] << 8);
    }
    unsigned cur_len = output.length();
    for (unsigned i = cur_len - o * 2; l--;) {
        output.push_back(output[i]);
        output.push_back(output[i + 1]);
        i = i + 2;
        if (i == cur_len)
            i = cur_len - o * 2;
    }
    cur_idx++;
//    print_output();
//    cout << "---------" << endl;
}


void decode_data() {
    while (cur_idx < bin_code.size()) {
        unsigned type = bin_code[cur_idx] & 0x3;
        switch (type) {
            case 0x0:
                literal_handle();
                break;
            case 0x1:
            case 0x2:
                recall_handle();
                break;
            default:
                cout << "?????";
                exit(EXIT_FAILURE);
                break;
        }
    }
}

int main() {
    init();
    lead_in();
    decode_data();
    print_output();
}

你可能感兴趣的:(CCF,CSP,算法与数据结构,算法,数据结构,c++,CCF,CSP,压缩编码,解码)