- 论坛徽章:
- 0
|
本帖最后由 fiendcly 于 2012-08-22 08:57 编辑
# 作者 : FIEND
# 文章來源 :
http://bbs.ecstart.com/forum.php ... id=43305&extra=
或
http://bbs.chinaunix.net/forum.p ... mp;fromuid=20071307
# 轉貼請注明出處 , 以方便討論.
在使用 C++ 做 Socket 的服務端時 , 利用 GZIP 和 ZLIB 做 Deflate 和 Inflate 來做 壓縮的 Stream Server
以下是我利用 POCO 來編寫的.
在使用這個元件時 , 我發現它的 GZIP 的 deflate 和 infalte 不能用 .
所以另外寫了一個獨立的 元件 .
在編寫過程中 , 發現這個 FREE 的 元件庫 問題還蠻多的 , 只好 一 一 解決.
這是我碰到這個問題時的討論主題 :
http://bbs.chinaunix.net/thread-3766361-1-1.html
http://bbs.ecstart.com/thread-43305-1-1.html
不想花錢 : (SUPPORT 是要錢的.)
http://pocoproject.org/download/index.html
使用版本 : 1.4.3p1 , 請先下載編譯.
請服用 .......
1.
zlib.h- #ifndef _ZLIB_H
- #define _ZLIB_H
- #pragma once
- #include <string>
- #define ZLIB_HEADER_LENGTH 1
- #define ZLIB_END_LENGTH 4
- //#define ZLIB_HEADER_STR "0x780x9c"
- //#define ZLIB_END_STR "0x0d0xd50x230x55"
- class Zlib
- {
- private:
- //static int len ;
- public:
- char zlibHeader[ZLIB_HEADER_LENGTH];
- char zlibEnd[ZLIB_END_LENGTH] ;
- static std::string zlibHeaderStr ;
- static std::string zlibEndStr ;
- unsigned int i ;
- unsigned int num ;
- //const char* zlibHeader ;
- //const char* zlibEnd ;
- static std::string inflateStr ;
- static std::string deflateStr ;
- static std::string zlibDeflateStr ;
- static std::string fixHeader ;
- //std::string inflate (const std::string &source,int level);
- std::string inflate (const std::string &source);
- //std::string inflate2 (const std::string &source);
- std::string deflate (const std::string &source,int level);
- // convert zlib deflate to gzip deflate
- std::string gzdeflate (const std::string &source,int level);
- // convert zlib inflate to gzip inflate
- std::string gzinflate (const std::string &source);
- };
- #endif
复制代码 2. CPP- #include <cstdlib>
- #include <iostream>
- #include <string>
- #include <stdio.h>
- #include <math.h>
- #include <sstream>
- // zlib
- #include "Poco/InflatingStream.h"
- #include "Poco/DeflatingStream.h"
- #include "Poco/StreamCopier.h"
- #include <fstream>
- using namespace std;
- using Poco::InflatingInputStream;
- using Poco::InflatingOutputStream;
- using Poco::DeflatingOutputStream;
- using Poco::DeflatingStreamBuf;
- using Poco::StreamCopier;
- #include "wge/zlib.h"
- std::string Zlib::inflateStr ;
- std::string Zlib::deflateStr ;
- std::string Zlib::fixHeader ;
- char zlibHeader[ZLIB_HEADER_LENGTH];
- char zlibEnd[ZLIB_END_LENGTH] ;
- /*
- * zlib deflate 字串壓縮
- */
- std::string Zlib::deflate (const std::string &source , int level = (-1)) {
- std::istringstream in(source);
- std::ostringstream out;
- Poco::DeflatingOutputStream deflaterOut(out,DeflatingStreamBuf::STREAM_ZLIB,level);
- deflaterOut << in.str() ;
- deflaterOut.close() ;
- //std::cout << " input : " << in.str() << endl ;
- //std::cout << " input length : " << in.str().length() << endl ;
- //std::cout << " output : " << out.str() << endl ;
- //std::cout << " output length : " << out.str().length() << endl ;
- deflateStr = out.str();
- return deflateStr ;
- }
- /*
- * zlib inflate 解壓縮
- */
- //std::string Zlib::inflate (const std::string &source , int level = (-1)) {
- std::string Zlib::inflate (const std::string &source) {
- std::istringstream in(source);
- //std::cout << in.str() << endl ;
- std::ostringstream out;
- Poco::InflatingInputStream inflaterIn(in,DeflatingStreamBuf::STREAM_ZLIB); // 建立 inflaterIn
- //Poco::InflatingInputStream inflaterIn(in); // 建立 inflaterIn
- // 將解壓縮的內容復制到 out stringtream .
- StreamCopier::copyStream(inflaterIn , out);
- inflateStr = out.str();
- return inflateStr ;
- }
复制代码
- /*
- * gzip deflate 字串壓縮
- */
- std::string Zlib::gzdeflate (const std::string &source , int level = (-1)) {
- std::istringstream in(source);
- std::ostringstream out;
- Poco::DeflatingOutputStream deflaterOut(out,DeflatingStreamBuf::STREAM_ZLIB,level);
- deflaterOut << in.str() ;
- deflaterOut.close() ;
- std::string zlibDeflateStr ;
- zlibDeflateStr = out.str();
- zlibDeflateStr = zlibDeflateStr.substr(2,zlibDeflateStr.length()-6);
- deflateStr = zlibDeflateStr ;
- return deflateStr ;
- }
复制代码
- /*
- * gzip inflate 解壓縮
- */
- std::string Zlib::gzinflate (const std::string &source) {
- // fix header & end
- //zlibHeader[ZLIB_HEADER_LENGTH] = ZLIB_HEADER_STR;
- //zlibEnd[ZLIB_END_LENGTH] = ZLIB_END_STR ;
- // zlib Header
- std::string fixsource;
- //std::string str = source ;
- zlibHeader[0] = 0x78 ;
- zlibHeader[1] = 0x9c ;
- std::string zlibHeaderStr = zlibHeader;
- std::string fixZlibHeaderStr = zlibHeaderStr.substr(0,2);
- zlibEnd[0] = 0xd ;
- zlibEnd[1] = 0xd5 ;
- zlibEnd[2] = 0x23 ;
- zlibEnd[3] = 0x55 ;
- std::string zlibEndStr = zlibEnd ;
- std::string fixZlibEndStr = zlibEndStr.substr(0,2);
- fixsource = fixZlibHeaderStr + source + fixZlibEndStr ;
- std::istringstream in(fixsource);
- //std::cout << in.str() << endl ;
- std::ostringstream out;
- Poco::InflatingInputStream inflaterIn(in,DeflatingStreamBuf::STREAM_ZLIB); // 建立 inflaterIn
- //Poco::InflatingInputStream inflaterIn(in); // 建立 inflaterIn
- StreamCopier::copyStream(inflaterIn , out);
- //std::cout << "Inflate Success \n" ;
- //std::cout << out.str() ;
- inflateStr = out.str();
- return inflateStr ;
- }
复制代码 test.cpp- #include <cstdlib>
- #include <iostream>
- #include <string.h>
- #include <string>
- #include <stdio.h>
- #include <ctime>
- //#include <unistd.h>
- #include <sys/time.h>
- #include "zlib.h"
- using namespace std;
- int main (int argc, char *argv[])
- {
- std::cout << "Zlib test start ...................\n" ;
- unsigned int i ;
- unsigned int num ;
- //std::cout << std::endl ;
- Zlib zlib ; // init Zlib object
- std::string test2 = "{\"SID\":\"123456789\",\"BID\":\"LD0001\",\"DATA\":{\"args\":{\"name\":\"test1\",\"passwd\":\"test1\",\"item\":[\"itme1\",\"itme2\",\"itme3\",\"itme4\"]}}}" ;
- std::string inflate ;
- std::string deflate ;
- deflate = zlib.deflate(test2,-1);
- inflate = zlib.inflate(deflate);
- std::cout << "deflate attribute : \n" << zlib.deflateStr << std::endl;
- std::cout << "deflate return : \n" << deflate << std::endl;
- std::cout << "PHP deflate HEX : \n" ;
- for(i=0 ; i< zlib.deflateStr.length(); i++){
- num = zlib.deflateStr[i] ;
- std::cout << hex << num << " " ;
- }
- std::cout << std::endl ;
- std::cout << "inflate attribute : \n" << zlib.inflateStr << std::endl;
- std::cout << "inflate return : \n" << inflate << std::endl;
- std::cout << "Test the wrong compression string format : " << endl ;
- std::string wrongStr = "Input the wrong compression string........." ;
- inflate = zlib.inflate(wrongStr);
- if(inflate == ""){
- std::cout << ".........................The compression string is wrong!!" << endl;
- }
- std::cout << std::endl ;
- std::cout << std::endl ;
- /*
- * BASE64 是我另外寫的一個元件庫....懶得貼 , 這裡不用測試 請淦掉.....
- std::cout << "gzip test start ...................\n" ;
- std::string test3 = "q1YK9nRRslIyNDI2MTUzt7BU0lFyAov4uBgYGBgCuS6OIY5KVtVKiUXpxSA6LzE3FShfklpcApIuSCwuLk9BEsgsSc1VsooG0rmpEH5uqhGUNobSJkqxtbW1AA==" ;
- std::cout << "PHP gzInflate & Base64Decode string is : \n" ;
- std::cout << test3 << std::endl ;
- std::cout << std::endl ;
- decode = base64.decode(test3);
- std::cout << "Base64 Decode attribute : \n" << base64.decodeStr << std::endl;
- std::cout << std::endl ;
- std::cout << "PHP deflate HEX : \n" ;
- for(i=0 ; i< base64.decodeStr.length(); i++){
- num = base64.decodeStr[i] ;
- std::cout << hex << num << " " ;
- }
- std::cout << std::endl ;
- std::cout << std::endl ;
- inflate = zlib.gzinflate(decode);
- std::cout << "Gzip Inflate String : \n" << inflate << std::endl; ;
- std::cout << std::endl ;
- */
- std::cout << std::endl ;
- std::cout << std::endl ;
- std::cout << "zlib deflate : \n" ;
- deflate = zlib.gzdeflate(test2,-1);
- std::cout << "gzdeflate attribute : \n" << zlib.deflateStr << std::endl;
- std::cout << std::endl ;
- std::cout << "GZIP deflate HEX : \n" ;
- for(i=0 ; i< zlib.deflateStr.length(); i++){
- num = zlib.deflateStr[i] ;
- std::cout << hex << num << " " ;
- }
- std::cout << std::endl ;
- std::cout << "Gzip indeflate : \n" ;
- inflate = zlib.gzinflate(deflate);
- std::cout << "Gzip Inflate String : \n" << inflate << std::endl; ;
- }
复制代码 |
|