⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 main.cpp

📁 几种常用的压缩算法 本程序包含以下功能: 1、 Arithmetic coding 2、 Huffman coding 3、 LZ77 coding 4、 LZ78 coding 5、 L
💻 CPP
📖 第 1 页 / 共 2 页
字号:
#include "Codec/Huffman.h"#include "Codec/LZ77.h"#include "Codec/LZ78.h"#include "Codec/LZW.h"#include "Codec/Arithmetic.h"#include "Codec/RLE.h"#include "Generic.h"  #include "Fatal/Fatal.h"  #include <stdio.h>#include <stdlib.h>#include <memory.h>#include <ctype.h>     #include <string.h>
#include <iostream.h>#define	BLOCK_SIZE	0x10000#define SIGNATURE	"CODR"DWORD	block_size;
void Encode(BYTE* pSource, long Length, char Code, BYTE* pData, long& CmpLength)
{
	long slen, tlen, scount;
	BYTE *source, *target;
	
	int i = 0;
	for (scount = 0; scount < Length; scount += block_size)
	{
		if ((Length - block_size * i) < block_size)
		{
			slen = Length - block_size * i;
		}
		else
		{
			slen = block_size;
		}
		i++;
		
		source = new BYTE[block_size];
		memmove(source, pSource, slen);
		pSource=pSource+slen;
		
		switch(tolower(Code))
		{
		case 'a':
			{
				printf("Encoding Arithmetic, source block[%d] size = %4ld\n", i,slen);
				TGeneric<CArithmetic> *ar = new TGeneric<CArithmetic>;
				tlen = ar->GetMaxEncoded(slen);
				target = new BYTE[tlen+1];
				ar->Encode(target+1, tlen, source, slen);
				if (tlen)
				{
					target[0] = 'a';
					delete source;
					source = target;
					slen = tlen+1;
					printf("Encoding Arithmetic, Compressed block size = %4ld\n", slen);
				} else
				{
					delete target;
					target = new BYTE[slen+1];
					target[0] = 0;
					memcpy(target+1, source, slen);
					delete source;
					source = target;
					slen++;
					printf("Encoding Arithmetic, Unpacked block size = %4ld\n", slen);
				}
				delete ar;
			}
			break;
			
		case 'h':
			{
				printf("Encoding Huffman, source block[%d] size = %4ld\n", i,slen);
				TGeneric < CHuffman > * huf = new TGeneric < CHuffman >;
				tlen = huf->GetMaxEncoded(slen);
				target = new BYTE[tlen + 1];
				huf->Encode(target + 1, tlen, source, slen);
				if (tlen)
				{
					target[0] = 'h';
					delete source;
					source = target;
					slen = tlen + 1;
                    printf("Encoding Huffman, Compressed block size = %4ld\n", slen);
				}
				else
				{
					delete target;
					target = new BYTE[slen + 1];
					target[0] = 0;
					memcpy(target + 1, source, slen);
					delete source;
					source = target;
					slen++;
					printf("Encoding Huffman, Unpacked block size = %4ld\n", slen);
				}
				delete huf;
			}
			break;
		case '7':
			{
				printf("Encoding LZ77, source block[%d] size = %4ld\n", i,slen);
				TGeneric < CLZ77 > * lz = new TGeneric < CLZ77 > ;
				tlen = lz->GetMaxEncoded(slen);
				target = new BYTE[tlen + 1];
				lz->Encode(target + 1, tlen, source, slen);
				if (tlen)
				{
					target[0] = '7';
					delete source;
					source = target;
					slen = tlen + 1;
					printf("Encoding LZ77, Compressed block size = %4ld\n", slen);
				}
				else
				{
					delete target;
					target = new BYTE[slen + 1];
					target[0] = 0;
					memcpy(target + 1, source, slen);
					delete source;
					source = target;
					slen++;
                    printf("Encoding LZ77, Unpacked block size = %4ld\n", slen);
				}
				delete lz;
			}
			break;
		case '8':
			{
				printf("Encoding LZ78, source block[%d] size = %4ld\n", i,slen);
				TGeneric < CLZ78 > * lz = new TGeneric < CLZ78 > ;
				tlen = lz->GetMaxEncoded(slen);
				target = new BYTE[tlen + 1];
				lz->Encode(target + 1, tlen, source, slen);
				if (tlen)
				{
					target[0] = '8';
					delete source;
					source = target;
					slen = tlen + 1;
					printf("Encoding LZ78, Compressed block size = %4ld\n", slen);
				}
				else
				{
					delete target;
					target = new BYTE[slen + 1];
					target[0] = 0;
					memcpy(target + 1, source, slen);
					delete source;
					source = target;
					slen++;
					printf("Encoding LZ78, Unpacked block size = %4ld\n", slen);
				}
				delete lz;
			}
			break;
		case 'w':
			{
				printf("Encoding LZW, source block[%d] size = %4ld\n", i,slen);
				TGeneric < CLZW > * lz = new TGeneric < CLZW > ;
				tlen = lz->GetMaxEncoded(slen);
				target = new BYTE[tlen + 1];
				lz->Encode(target + 1, tlen, source, slen);
				if (tlen)
				{
					target[0] = 'w';
					delete source;
					source = target;
					slen = tlen + 1;
					printf("Encoding LZW, Compressed block size = %4ld\n", slen);
				}
				else
				{
					delete target;
					target = new BYTE[slen + 1];
					target[0] = 0;
					memcpy(target + 1, source, slen);
					delete source;
					source = target;
					slen++;
					printf("Encoding LZW, Unpacked block size = %4ld\n", slen);
				}
				delete lz;
			}
			break;
		case 'r':
			{
				printf("Encoding RLE, source block[%d] size = %4ld\n", i,slen);
				TGeneric < CRLE > * rle = new TGeneric < CRLE > ;
				tlen = rle->GetMaxEncoded(slen);
				target = new BYTE[tlen + 1];
				rle->Encode(target + 1, tlen, source, slen);
				if (tlen)
				{
					target[0] = 'r';
					delete source;
					source = target;
					slen = tlen + 1;
					printf("Encoding RLE, Compressed block size = %4ld\n", slen);
				}
				else
				{
					delete target;
					target = new BYTE[slen + 1];
					target[0] = 0;
					memcpy(target + 1, source, slen);
					delete source;
					source = target;
					slen++;
					printf("Encoding RLE, Unpacked block size = %4ld\n", slen);
				}
				delete rle;
			}
			break;
		case 'c':
			delete source;
			FatalError("DCT compression is not implemented yet!\n");
			break;
		case 'f':
			delete source;
			FatalError("Furie Transform compression is not implemented yet!\n");
			break;
		default:
			delete source;
			FatalError("Unrecognized method of compression!\n");
			break;
            }
			
			memmove(pData, source, slen);
			pData=pData+slen;
			CmpLength += slen;
			delete source;
	}
	
	printf("Compression successfull. Compressed total size = %ld\n", CmpLength);
}

void Decode(BYTE* pData, long CmpLength, BYTE* pSource, long& Length)
{
	long slen,tlen,temp,scount=0;
	int delta,saved;
	BYTE *source, *target;
	slen = min((DWORD)CmpLength,block_size);
	while(scount<CmpLength)
	{   
        delta = 0;
		saved = 0;
		
		source = new BYTE[block_size];
		memmove(source, pData, slen); 
		
		
		temp = 0;
		
		switch(source[delta])
		{ case 'a':
		{
			printf("Decoding Arithmetic, compressed size = %ld\n", slen);
			TGeneric<CArithmetic> *ar = new TGeneric<CArithmetic>;
			tlen = ar->GetMaxDecoded(source+1+delta);
			target = new BYTE[tlen];
			temp = ar->Decode(target, tlen, source+1+delta, slen-1-delta);
			delete source;
			source = target;
			slen = tlen;
			delta = 0;
			delete ar;
		}
		break;
		case 'h':
			{    
				printf("Decoding Huffman, compressed size = %ld\n", slen);
				TGeneric<CHuffman> *huf = new TGeneric<CHuffman>;
				tlen = huf->GetMaxDecoded(source+1+delta);
				target = new BYTE[tlen];
				temp = huf->Decode(target, tlen, source+1+delta, slen-1-delta);
				delete source;
				source = target;
				slen = tlen;
				delta = 0;
				delete huf;
			}
			break;
		case '7':
			{
				printf("Decoding LZ77, compressed size = %ld\n", slen);
				TGeneric<CLZ77> *lz = new TGeneric<CLZ77>;
				tlen = lz->GetMaxDecoded(source+1+delta);
				target = new BYTE[tlen];
				temp = lz->Decode(target, tlen, source+1+delta, slen-1-delta);
				delete source;
				source = target;
				slen = tlen;
				delta = 0;
				delete lz;
			}
			break;
		case '8':
			{
				printf("Decoding LZ78, compressed size = %ld\n", slen);
				TGeneric<CLZ78> *lz = new TGeneric<CLZ78>;
				tlen = lz->GetMaxDecoded(source+1+delta);
				target = new BYTE[tlen];
				temp = lz->Decode(target, tlen, source+1+delta, slen-1-delta);
				delete source;
				source = target;
				slen = tlen;
				delta = 0;
				delete lz;
			}
			break;
		case 'w':
			{
				printf("Decoding LZW, compressed size = %ld\n", slen);
				TGeneric<CLZW> *lz = new TGeneric<CLZW>;
				tlen = lz->GetMaxDecoded(source+1+delta);
				target = new BYTE[tlen];
				temp = lz->Decode(target, tlen, source+1+delta, slen-1-delta);
				delete source;
				source = target;
				slen = tlen;
				delta = 0;
				delete lz;
			}
			break;
		case 'r':
			{
				printf("Decoding RLE, compressed size = %ld\n", slen);
				TGeneric<CRLE> *rle = new TGeneric<CRLE>;
				tlen = rle->GetMaxDecoded(source+1+delta);
				target = new BYTE[tlen];
				temp = rle->Decode(target, tlen, source+1+delta, slen-1-delta);
				delete source;
				source = target;
				slen = tlen;
				delta = 0;
				delete rle;
			}
			break;
		case 'c':
			delete source;
			FatalError("DCT decompression is not implemented yet!\n");
			break;
		case 'f':
			delete source;
			FatalError("Furie Transform decompression is not implemented yet!\n");
			break;
		case 0:	// not coded data
			printf("Unpacked data block, size = %ld\n", slen);
			delta++;
			temp = 0;
			break;
		default:
			delete source;
			FatalError("Unrecognized method of decompression!\n");
			break;
			}
			if (!delta && !saved)
			{
				scount += temp + 1;
				pData=pData+temp + 1;
				saved = 1;
				printf("Decoding , compressed size = %ld\n", temp+1);
			}
			
			if (!saved)
			{
				delete source;
				source = new BYTE[block_size+delta];
				memmove(source, pData, slen+delta); 
				
				
				scount += slen + delta;
				pData=pData+slen+delta;
				printf("Decoding , compressed size = %ld\n", slen+delta);
				
				
			}
			
			memmove(pSource, source+ delta, slen);//-delta);
			pSource=pSource+slen;//-delta;
			Length += slen;//-delta;
			
			delete source;
	}
	printf("Decompression successfull. Decompressed size = %ld\n", Length);
	
}

void Encode(FILE* s, FILE* t, char* sequence)
{
    int i;
    long slen, tlen, scount, length, compressed = 0;
    BYTE* source, * target;
    BYTE* signature = (BYTE*)SIGNATURE;
    compressed += fwrite(signature, 1, strlen((char*)signature), t);
    compressed += fwrite(&block_size, 1, sizeof(DWORD), t);
    fseek(s, 0, SEEK_END);
    length = ftell(s);
    fseek(s, 0, SEEK_SET);
    for (scount = 0; scount < length; scount += block_size)
    {   
		int n=(scount+block_size)/block_size;
        source = new BYTE[block_size];
        slen = fread(source, 1, block_size, s);
        if (!slen)
            break;
        for (i = 0; sequence[i]; i++)
        {
            switch (tolower(sequence[i]))
            {
			case 'a':
				{
					printf("Encoding Arithmetic, source block[%d] size = %4ld\n", n,slen);
					TGeneric < CArithmetic > * ar = new TGeneric <CArithmetic > ;
					tlen = ar->GetMaxEncoded(slen);
					target = new BYTE[tlen + 1];
					ar->Encode(target + 1, tlen, source, slen);
					if (tlen)
					{
						target[0] = 'a';
						delete source;
						source = target;
						slen = tlen + 1;
                        printf("Encoding Arithmetic, Compressed block size = %4ld\n", slen);
					}
					else
					{
						delete target;
						target = new BYTE[slen + 1];
						target[0] = 0;
						memcpy(target + 1, source, slen);
						delete source;
						source = target;
						slen++;
                        printf("Encoding Arithmetic, Unpacked block size = %4ld\n", slen);
					}
					delete ar;
				}
				break;
			case 'h':
				{
					printf("Encoding Huffman, source block[%d] size = %4ld\n", n,slen);
					TGeneric < CHuffman > * huf = new TGeneric < CHuffman >
						;
					tlen = huf->GetMaxEncoded(slen);
					target = new BYTE[tlen + 1];
					huf->Encode(target + 1, tlen, source, slen);
					if (tlen)
					{
						target[0] = 'h';
						delete source;
						source = target;
						slen = tlen + 1;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -