【云备份】第三方库

7. 环境搭建-gcc升级7.3版本
sudo yum install centos-release-scl-rh centos-release-scl
sudo yum install devtoolset-7-gcc  devtoolset-7-gcc-c++
source /opt/rh/devtoolset-7/enable 
echo "source /opt/rh/devtoolset-7/enable" >> ~/.bashrc
[san@localhost example]$ g++ -v
Using built-in specs.
COLLECT_GCC=g++
COLLECT_LTO_WRAPPER=/opt/rh/devtoolset-7/root/usr/libexec/gcc/x86_64-redhat-linux/7/lto-wrapper
Target: x86_64-redhat-linux
Configured with: ../configure --enable-bootstrap --enable-languages=c,c++,fortran,lto --prefix=/opt/rh/devtoolset-7/root/usr --mandir=/opt/rh/devtoolset-7/root/usr/share/man --infodir=/opt/rh/devtoolset-7/root/usr/share/info --with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-shared --enable-threads=posix --enable-checking=release --enable-multilib --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-gnu-unique-object --enable-linker-build-id --with-gcc-major-version-only --enable-plugin --with-linker-hash-style=gnu --enable-initfini-array --with-default-libstdcxx-abi=gcc4-compatible --with-isl=/builddir/build/BUILD/gcc-7.3.1-20180303/obj-x86_64-redhat-linux/isl-install --enable-libmpx --enable-gnu-indirect-function --with-tune=generic --with-arch_32=i686 --build=x86_64-redhat-linux
Thread model: posixs
gcc version 7.3.1 20180303 (Red Hat 7.3.1-5) (GCC) 
8. 环境搭建-安装jsoncpp库
sudo yum install epel-release
sudo yum install jsoncpp-devel
[san@localhost ~]$ ls /usr/include/jsoncpp/json/
assertions.h  config.h    forwards.h  reader.h  version.h
autolink.h    features.h  json.h      value.h   writer.h
#注意,centos版本不同有可能安装的jsoncpp版本不同,安装的头文件位置也就可能不同了。
9. 环境搭建-下载bundle数据压缩库

GitHub链接

sudo yum install git
git clone https://github.com/r-lyeh-archived/bundle.git
10. 环境搭建-下载httplib

GitHub链接

git clone https://github.com/yhirose/cpp-httplib.git
11. 第三方库认识-json认识

json是一种数据交换格式,采用完全独立于编程语言的文本格式来存储和表示数据。

例如:小明同学的学生信息

char name = "小明";
int age = 18;
float score[3] = {88.5, 99, 58};
则json这种数据交换格式是将这多种数据对象组织成为一个字符串:
[
    {
        "姓名" : "小明",
        "年龄" : 18,
        "成绩" : [88.5, 99, 58]
    },
    {
        "姓名" : "小黑",
        "年龄" : 18,
        "成绩" : [88.5, 99, 58]
    }
]

json数据类型:对象,数组,字符串,数字

对象:使用花括号{}括起来的表示一个对象。

数组:使用中括号[]括起来的表示一个数组。

字符串:使用常规双引号""括起来的表示一个字符串

数字:包括整形和浮点型,直接使用。

12. 第三方库认识-jsoncpp认识

jsoncpp库用于实现json格式的序列化和反序列化,完成将多个数据对象组织成为json格式字符串,以及将json格式字符串解析得到多个数据对象的功能。

这其中主要借助三个类以及其对应的少量成员函数完成:

//Json数据对象类
class Json::Value{
    Value &operator=(const Value &other); //Value重载了[]和=,因此所有的赋值和获取数据都可以通过
    Value& operator[](const std::string& key);//简单的方式完成 val["姓名"] = "小明";
    Value& operator[](const char* key);
    Value removeMember(const char* key);//移除元素
    const Value& operator[](ArrayIndex index) const; //val["成绩"][0]
    Value& append(const Value& value);//添加数组元素val["成绩"].append(88); 
    ArrayIndex size() const;//获取数组元素个数 val["成绩"].size();
    std::string asString() const;//转string 	 string name = val["name"].asString();
    const char* asCString() const;//转char*   char *name = val["name"].asCString();
    Int asInt() const;//转int				int age = val["age"].asInt();
    float asFloat() const;//转float
    bool asBool() const;//转 bool
};

//json序列化类,低版本用这个更简单
class JSON_API Writer {
  virtual std::string write(const Value& root) = 0;
}
class JSON_API FastWriter : public Writer {
  virtual std::string write(const Value& root);
}
class JSON_API StyledWriter : public Writer {
  virtual std::string write(const Value& root);
}
//json序列化类,高版本推荐,如果用低版本的接口可能会有警告
class JSON_API StreamWriter {
    virtual int write(Value const& root, std::ostream* sout) = 0;
}
class JSON_API StreamWriterBuilder : public StreamWriter::Factory {
    virtual StreamWriter* newStreamWriter() const;
}

//json反序列化类,低版本用起来更简单
class JSON_API Reader {
	bool parse(const std::string& document, Value& root, bool collectComments = true);
}
//json反序列化类,高版本更推荐
class JSON_API CharReader {
    virtual bool parse(char const* beginDoc, char const* endDoc, 
                       Value* root, std::string* errs) = 0;
}
class JSON_API CharReaderBuilder : public CharReader::Factory {
    virtual CharReader* newCharReader() const;
}
13. 第三方库认识-jsoncpp实现序列化
int main()
{
    const char *name = "小明";
    int age = 18;
    float score[] = {88.5, 98, 58};
    Json::Value val;
    val["姓名"] = name;
    val["年龄"] = age;
    val["成绩"].append(score[0]);
    val["成绩"].append(score[1]);
    val["成绩"].append(score[2]);
    
    Json::StreamWriterBuilder swb;
    std::unique_ptr sw(swb.newStreamWriter());
    std::ostringstream os;
    sw->write(val, &os);
    std::string str = os.str();
    std::cout << str <
g++ json_example1.cpp -o json_example1 -ljsoncpp
14. 第三方库认识-jsoncpp实现反序列化
int main()
{
    std::string str = R"({"姓名":"小明", "年龄":18, "成绩":[76.5, 55, 88]})";
    Json::Value root;
    Json::CharReaderBuilder crb;
    std::unique_ptr cr(crb.newCharReader());
    std::string err;
    cr->parse(str.c_str(), str.c_str() + str.size(), &root, &err);
    
    std::cout << root["姓名"].asString() << std::endl;
    std::cout << root["年龄"].asInt() << std::endl;
    int sz = root["成绩"].size();
    for (int i = 0; i < sz; i++) {
    	std::cout << root["成绩"][i].asFloat() << std::endl;
    }
    for (auto it = root["成绩"].begin(); it != root["成绩"].end(); it++){
    	std::cout << it->asFloat() << std::endl;
    }
    return 0;
}
g++ json_example2.cpp -o json_example2 -ljsoncpp
15. 第三方库认识-bundle文件压缩库认识

BundleBundle是一个嵌入式压缩库,支持23种压缩算法和2种存档格式。使用的时候只需要加入两个文件bundle.hbundle.cpp即可。

namespace bundle
{
  // low level API (raw pointers)
  bool is_packed( *ptr, len );
  bool is_unpacked( *ptr, len );
  unsigned type_of( *ptr, len );
  size_t len( *ptr, len );
  size_t zlen( *ptr, len );
  const void *zptr( *ptr, len );
  bool pack( unsigned Q, *in, len, *out, &zlen );
  bool unpack( unsigned Q, *in, len, *out, &zlen );

  // medium level API, templates (in-place)
  bool is_packed( T );
  bool is_unpacked( T );
  unsigned type_of( T );
  size_t len( T );
  size_t zlen( T );
  const void *zptr( T );
  bool unpack( T &, T );
  bool pack( unsigned Q, T &, T );

  // high level API, templates (copy)
  T pack( unsigned Q, T );
  T unpack( T );
}
16. 第三方库认识-bundle库实现文件压缩
#include 
#include 
#include 
#include "bundle.h"

int main(int argc, char *argv[])
{
    std::cout <<"argv[1] 是原始文件路径名称\n";
    std::cout <<"argv[2] 是压缩包名称\n";
    if (argc < 3) return -1;

    std::string ifilename = argv[1];
    std::string ofilename = argv[2];

    std::ifstream ifs;
    ifs.open(ifilename, std::ios::binary);//打开原始文件
    ifs.seekg(0, std::ios::end);//跳转读写位置到末尾
    size_t fsize = ifs.tellg();//获取末尾偏移量--文件长度
    ifs.seekg(0, std::ios::beg);//跳转到文件起始
    std::string body;
    body.resize(fsize);//调整body大小为文件大小
    ifs.read(&body[0], fsize);//读取文件所有数据到body找给你

    std::string packed = bundle::pack(bundle::LZIP, body);//以lzip格式压缩文件数据

    std::ofstream ofs;
    ofs.open(ofilename, std::ios::binary);//打开压缩包文件
    ofs.write(&packed[0], packed.size());//将压缩后的数据写入压缩包文件

    ifs.close();
    ofs.close();
    return 0;
}
17. 第三方库认识-bundle库实现文件解压缩
#include 
#include 
#include 
#include "bundle.h"

int main(int argc, char *argv[])
{
    if (argc < 3) {
        printf("argv[1]是压缩包名称\n");
        printf("argv[2]是解压后的文件名称\n");
        return -1; 
    }   
    std::string ifilename = argv[1];//压缩包名
    std::string ofilename = argv[2];//解压缩后文件名

    std::ifstream ifs;
    ifs.open(ifilename, std::ios::binary);
    ifs.seekg(0, std::ios::end);
    size_t fsize = ifs.tellg();
    ifs.seekg(0, std::ios::beg);
    std::string body;
    body.resize(fsize);
    ifs.read(&body[0], fsize);
    ifs.close();

    std::string unpacked = bundle::unpack(body);//对压缩包数据解压缩

    std::ofstream ofs;
    ofs.open(ofilename, std::ios::binary);
    ofs.write(&unpacked[0], unpacked.size());
    ofs.close();
    return 0;
}
[san@localhost ~]$ g++ compress.cpp bundle.cpp -o compress -lpthread
[san@localhost ~]$ g++ uncompress.cpp bundle.cpp -o uncompress -lpthread
[san@localhost ~]$ ./compress ./bundle.cpp ./bundle.cpp.lz
[san@localhost ~]$ ./uncompress ./bundle.cpp.lz ./bundle2.cpp
[san@localhost ~]$ md5sum bundle.cpp
4cb64c7a8354c82402dd6fe080703650  bundle.cpp
[san@localhost ~]$ md5sum bundle2.cpp 
4cb64c7a8354c82402dd6fe080703650  bundle2.cpp
18. 第三方库认识-httplib

httplib库,一个C++11单文件头的跨平台HTTP/HTTPS库。安装起来非常容易。只需包含httplib.h在你的代码中即可。

httplib库实际上是用于搭建一个简单的http服务器或者客户端的库,这种第三方网络库,可以让我们免去搭建服务器或客户端的时间,把更多的精力投入到具体的业务处理中,提高开发效率。

namespace httplib{
    struct MultipartFormData {
        std::string name;
        std::string content;
        std::string filename;
        std::string content_type;
    };
    using MultipartFormDataItems = std::vector;
    struct Request {
        std::string method;
        std::string path;
        Headers headers;
        std::string body;
        // for server
        std::string version;
        Params params;
        MultipartFormDataMap files;
        Ranges ranges;
        bool has_header(const char *key) const;
        std::string get_header_value(const char *key, size_t id = 0) const;
        void set_header(const char *key, const char *val);
        bool has_file(const char *key) const;
        MultipartFormData get_file_value(const char *key) const;
    };
    struct Response {
        std::string version;
        int status = -1;
        std::string reason;
        Headers headers;
        std::string body;
        std::string location; // Redirect location
		void set_header(const char *key, const char *val);
        void set_content(const std::string &s, const char *content_type);
    };
	class Server {
        using Handler = std::function;
        using Handlers = std::vector>;
        std::function new_task_queue;
        Server &Get(const std::string &pattern, Handler handler);
  		Server &Post(const std::string &pattern, Handler handler);
        Server &Put(const std::string &pattern, Handler handler);
  		Server &Patch(const std::string &pattern, Handler handler);  
  		Server &Delete(const std::string &pattern, Handler handler);
  		Server &Options(const std::string &pattern, Handler handler);
        bool listen(const char *host, int port, int socket_flags = 0);
	};
    class Client {
        Client(const std::string &host, int port);
  		Result Get(const char *path, const Headers &headers);
        Result Post(const char *path, const char *body, size_t content_length,
              const char *content_type);
        Result Post(const char *path, const MultipartFormDataItems &items);
    }
}
19. 第三方库认识-httplib库搭建简单服务器
/* 前端测试页面 test.html 直接使用浏览器打开即可看到网页 */
<html>
  <body>
	<form action="http://服务器IP:端口/upload" method="post" enctype="multipart/form-data">
      <input type="file" name="file">
	  <input type="submit" value="上传">
	form>
  body>
html>
#include "httplib.h"

int main(void)
{
    using namespace httplib;
    Server svr;
    svr.Get("/hi", [](const Request& req, Response& res) {
    	res.set_content("Hello World!", "text/plain");
    });
    svr.Get(R"(/numbers/(\d+))", [&](const Request& req, Response& res) {
    	auto numbers = req.matches[1];
    	res.set_content(numbers, "text/plain");
  	});
    svr.Post("/upload", [&](const auto& req, auto& res) {
        auto size = req.files.size();
        auto ret = req.has_file("file1");
        const auto& file = req.get_file_value("file1");
        std::cout << file.filename << std::endl;
        std::cout <<  file.content_type << std::endl;
        std::cout <<  file.content << std::endl;
    });
  	svr.listen("0.0.0.0", 9090);
 	return 0; 	
}
g++ -std=c++14 http_server.cpp -o http_server -lpthread
20. 第三方库认识-httplib库搭建简单客户端
#include "httplib.h"
#define SERVER_IP "你的服务器IP地址"
// HTTP
int main()
{
    httplib::Client cli(SERVER_IP);
    
    auto res = cli.Get("/hi");
    std::cout << res->status << std::endl;
    std::cout << res->body << std::endl;
    
    auto res = cli.Get("/numbers/678");
    std::cout << res->status << std::endl;
    std::cout << res->body << std::endl;
    
    httplib::MultipartFormDataItems items = {
      { "file1", "this is file content", "hello.txt", "text/plain" },
    };
    auto res = cli.Post("/upload", items);
    std::cout << res->status << std::endl;
    std::cout << res->body << std::endl;
    return 0;
}

你可能感兴趣的:(云备份,开发语言)