@Klucva

Как сделать сжатие и распаковку char* в C++ с помощью zlib?

Я хочу сделать код, который будет сжимать и распаковывать текст в отдельных функциях, но когда я сделал, некоторые тексты он распаковывал не до конца. Например я вводил {"a2":"b"} и при распаковке получал {"a2":"`
Код:
char* compress_char(char* source)
{
    char* bytes = new char[strlen(source)];
    uLong ucompSize = strlen(source) + 1;
    uLong compSize = compressBound(ucompSize);
    compress((Bytef *)bytes, &compSize, (Bytef *)source, ucompSize);
    return bytes;
}

char* uncompress_char(unsigned char source[], int length)
{
    char* message = new char[length];
    uLong ucompSize = length + 1;
    uLong compSize = compressBound(ucompSize);
    uncompress((Bytef *)message, &ucompSize, (Bytef *)source, compSize);
    return message;
}

Я также при распаковке и запаковке пытался вручную изменить длинну, но результат не поменялся, что я делаю не так?
  • Вопрос задан
  • 102 просмотра
Пригласить эксперта
Ответы на вопрос 1
jcmvbkbc
@jcmvbkbc
"I'm here to consult you" © Dogbert
что я делаю не так?

Несколько вещей. В compress_char ты сначала выделяешь strlen(source) байт для вывода, а потом находишь compSize, который может быть и больше чем strlen(source). Ты не возвращаешь compSize после вызова compress, а он может измениться. Ты возвращаешь только char*, как будто это строка, но это не строка, там могут быть нулевые байты.
В uncompress_char почти те же самые ошибки. Плюс какая-то путаница между length, compSize и ucompSize. На вход uncompress в параметре compSize должен попасть настоящий размер сжатых данных, а не догадка о нём на основе вызова compressBound.
Я бы поменял код как-то так:
char* compress_char(const char* source, size_t *outCompSize, size_t *outUcompSize)
{
    uLong ucompSize = strlen(source) + 1;
    uLong compSize = compressBound(ucompSize);
    char* bytes = malloc(compSize);
    compress((Bytef *)bytes, &compSize, (Bytef *)source, ucompSize);
    *outCompSize = compSize;
    *outUcompSize = ucompSize;
    return bytes;
}

char* uncompress_char(const unsigned char source[], size_t inCompSize, size_t inUcompSize)
{
    uLong ucompSize = inUcompSize;
    uLong compSize = inCompSize;
    char* message = malloc(ucompSize);
    uncompress((Bytef *)message, &ucompSize, (Bytef *)source, compSize);
    return message;
}

void foo(void)
{
    size_t a, b;
    char *p = compress_char("{\"a2\":\"b\"}", &a, &b);
    char *p1 = uncompress_char(p, a, b);
    printf("%s, %zd -> %zd\n", p1, b, a);
}


Плюс ты не обрабатываешь коды возврата из compress/uncompress.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы