ほぼ以下のブログが網羅しているので読んで欲しい
以下、私用のメモ
準備
cmakeをインストールする
Windows win64-x64 Installer で良いだろう
途中のオプションで、Add CMake to the system PATH for the current user
にチェックを入れておく(今回は使わないけど)
zlibのコンパイル
zlib-1.2.11のソースコードをダウンロードし、展開する。Windowsだと7zipを使って展開すると良いだろう。
https://www.zlib.net/zlib-1.2.11.tar.gz
buildフォルダを作り、CMakeにフォルダーとbuildフォルダーを貼り付けた。
構成は以下の画像のようにした。 Configure で Visual Studio 15 2017
と x64
を選び、適宜書き換えて、 Generate
buildフォルダ内のzlib.sln を Visual Studio 2017
開いて、パッチビルドから全てをビルド。
libzipのコンパイル
zlib-1.2.11のソースコードをダウンロードし、展開する。
buildフォルダを作り、CMakeにフォルダーとbuildフォルダーを貼り付けた。
構成は以下の画像のようにした。 Configure で Visual Studio 15 2017
と x64
を選び、適宜書き換えて、 Generate
buildフォルダ内のlibzip.sln を Visual Studio 2017
開いて、パッチビルドから全てをビルド。
RUN_TESTS distcheck update_zip_err_str update_zip_errors check dist
がコンパイルに失敗したが、チェック用なので見なかったことにする。
Visual Studioからライブラリとして使う
環境変数にbinフォルダを、インクルードディレクトリにincludeフォルダを、リンカーに lib\zip.lib
を通す。ソースコードは以下の通り。
ここでは、ファイルから圧縮するのではなく、RAM上のデータから直接ファイルに書き出す(だって、C++でやりたい理由って真っ先にそれやん?) をやってみる。
#include <zip.h> #include <filesystem> //https://gist.github.com/clalancette/bb5069a09c609e2d33c9858fcc6e170e をパクった void zip_file_add_impl(zip_t* zipper, std::string filename, const std::vector<char>& buf) { zip_source_t* source = zip_source_buffer(zipper, buf.data(), buf.size(), 0); if (source == nullptr) { throw std::runtime_error("Failed to add file to zip: " + std::string(zip_strerror(zipper))); } if (zip_file_add(zipper, filename.c_str(), source, ZIP_FL_ENC_UTF_8) < 0) { zip_source_free(source); throw std::runtime_error("Failed to add file to zip: " + std::string(zip_strerror(zipper))); } } int main(int argc, char* argv[]) { //サンプルファイル用 std::vector<char>buf; for (int i = 0; i < 10; i++) { buf.emplace_back(48 + i); } int errorp; std::string output_filename = "test.zip"; //ZIpファイルが既に存在してれば削除 if (std::filesystem::exists(output_filename)) { std::filesystem::remove(output_filename); } //ZIPファイルを作成 zip_t* zipper = zip_open(output_filename.c_str(), ZIP_CREATE | ZIP_EXCL, &errorp); //エラー処理 if (zipper == nullptr) { zip_error_t ziperror; zip_error_init_with_code(&ziperror, errorp); throw std::runtime_error("Failed to open output file " + output_filename + ": " + zip_error_strerror(&ziperror)); } //ファイルをRAMから追加 zip_file_add_impl(zipper, "0.txt", buf); zip_file_add_impl(zipper, "1.txt", buf); zip_file_add_impl(zipper, "2.txt", buf); //ZIPファイルを閉じる zip_close(zipper); return 0; }