資源簡介
LZO實現(xiàn)原理詳解,通過舉例使你更加容易理解.比較與lz77、lzw等算法的優(yōu)缺點,最后對lzo優(yōu)化。

代碼片段和文件信息
#include?
#include?
#include?
typedef?unsigned?char?byte;
int?_stdcall?compress(byte?*src?unsigned?src_len?byte?*dst);
int?_stdcall?decompress(byte?*src??unsigned?src_len byte?*dst);
//?新字符(<18):?-3匹配長度-1匹配位置-1保留位:新字符數(shù)
//?新字符(>18):-18
//?開始查找,如果沒有匹配字符時,記錄其位置
//?直到找到匹配字符,開始輸出記錄的新字符
//?然后?計算出匹配字符的長度與位置,
//?并根據(jù)其區(qū)間輸出其位置
static?unsigned?_do_compress?(byte?*in?unsigned?in_len?byte?*out?unsigned?*out_len)
{
static?long?wrkmem?[16384L];
register?byte?*ip;
byte?*op;
byte?*in_end?=?in?+?in_len;
byte?*ip_end?=?in?+?in_len?-3;
byte?*ii; //?指向開始編碼的位置
byte?**dict?=?(byte?**)wrkmem;
op?=?out;
ip?=?in;
ii?=?ip;
ip?+=?4;
????????for(;;)
{
register?byte?*m_pos;
unsigned?m_off;
unsigned?m_len;
unsigned?dindex; //?hashkey(ip[0]?ip[1]?ip[2]?ip[3])
dindex?=?((0x21*(((((((unsigned)(ip[3])<<6)^ip[2])<<5)^ip[1])<<5)^ip[0]))>>5)?&?0x3fff;
m_pos?=?dict?[dindex];
if(((unsigned)m_pos?(unsigned)in)?||
(m_off?=?(unsigned)((unsigned)ip-(unsigned)m_pos)?)?<=?0?||
m_off?>?0xbfff) //?0xc000?48kb
goto?literal;
if(m_off?<=?0x0800?||?m_pos[3]?==?ip[3]) //?回指長度小于2Kb
goto?try_match;
dindex?=?(dindex?&?0x7ff?)?^?0x201f; //?處理沖突第二次hash
m_pos?=?dict[dindex];
if((unsigned)(m_pos)?(unsigned)(in)?||
(m_off?=?(unsigned)(?(int)((unsigned)ip-(unsigned)m_pos)))?<=?0?||
m_off?>?0xbfff)
????goto?literal;
if?(m_off?<=?0x0800?||?m_pos[3]?==?ip[3])?//?回指長度小于2Kb
goto?try_match; //?第三個字節(jié)相等
goto?literal;
try_match: //?m_pos[0]m_pos[1]m_pos[2]都匹配成功時繼續(xù)比較
if(*(unsigned?short*)m_pos?==?*(unsigned?short*)ip?&&?m_pos[2]==?ip[2])
goto?match;
literal: //?匹配不成功時或者無記錄
dict[dindex]?=?ip; //?記錄字符串為ip[0]ip[1]ip[2]ip[3]的地址
++ip;
if?(ip?>=?ip_end)
break;
continue;
match: //?在得到匹配長度與位置之前先輸出未匹配的字符
dict[dindex]?=?ip; //?更新,字符匹配時的位置(未編碼)
if(ip?-?ii?>?0) //?存在新字符
{
register?unsigned?t?=?ip?-?ii; //?t:新字符的數(shù)目(未匹配的)
if?(t?<=?3) //?新字符數(shù)目<3時
op[-2]?|=?(byte)t; //?對兩個保留字元賦值
else?if(t?<=?18) //?新字符數(shù)目<18時
*op++?=?(byte)(t?-?3);
else
{
register?unsigned?tt?=?t?-?18;
*op++?=?0;
while(tt?>?255) //?構建新位元組
{
tt?-=?255;
*op++?=?0;
}
*op++?=?(byte)tt;
}
do
{
*op++?=?*ii++;? //?ii指向開始匹配的位置(未編碼)
}while?(--t?>?0); //?輸出?t個新字符
}
ip?+=?3; //?跳過與m_pos[0]??m_pos[1]?m_pos[2]的比較
if(m_pos[3]?!=?*ip++?||?m_pos[4]?!=?*ip++?||?m_pos[5]?!=?*ip++?||
m_pos[6]?!=?*ip++?||?m_pos[7]?!=?*ip++?||?m_pos[8]?!=?*ip++?)
{
--ip;
m_len?=?ip?-?ii; //?得到重復長度<=8
if(m_off?<=?0x0800?) //??回指長度小于2kb
{
--m_off; //?m_off與m_len在輸出時都減1
// m_off在第一位元組(byte)占三位m_off&7?小于8
*op++?=?(byte)(((m_len?-?1)?<5)?|?((m_off?&?7)?<2));
*op++?=?(byte)(m_off?>>?3); //?去除已用的低3位
}
else
if?(m_off?<=?0x4000?) //?回指長度小于16kb
{
--?m_off;
*op++?=?(byte)(32?|?(m_len?
?屬性????????????大小?????日期????時間???名稱
-----------?---------??----------?-----??----
?????文件???????9645??2009-06-17?09:25??lzo.cpp
?????文件????2473803??2009-06-15?09:15??lzo.pdf
-----------?---------??----------?-----??----
??????????????2483448????????????????????2
- 上一篇:MyEclipse10注冊機
- 下一篇:串口調試助手源代碼 VS+Qt
評論
共有 條評論