4 Temmuz 2017 Salı

iostreams filtering_streambuf Sınıfı

Giriş
Şu satırı dahil ederiz.
#include <boost/iostreams/filtering_streambuf.hpp>
bzip için şu satırı dahil ederiz.
#include <boost/iostreams/filter/bzip2.hpp>
gzip için şu satırı dahil ederiz.
#include <boost/iostreams/filter/gzip.hpp>
zlib için şu satırı dahil ederiz. Aslında gzip.hpp, zlib.hpp dosyasını dahil ediyor ama ben yine de yazdım
#include <boost/iostreams/filter/zlib.hpp>
Bu sınıfı ile filtering_stream sınıfı arasındaki farkı tam anlamadım. Her ikisi de aynı şeyi yapıyor gibi görünüyor.

typedef
filtering_istream aslında bir filtering_streambuf nesnesidir. Şöyledir yani bir typdef'tir.
typedef boost::iostreams::filtering_streambuf<boost::iostreams::input>
 filtering_istream;
filtering_ostream aslında bir filtering_streambuf nesnesidir. Şöyledir yani bir typdef'tir.
typedef boost::iostreams::filtering_streambuf<boost::iostreams::out> 
  filtering_ostream;
Constructor
Şöyle yaparız.
boost::iostreams::filtering_streambuf<...> streamBuf;
Şöyle yaparız.
boost::iostreams::filtering_streambuf<boost::iostreams::input> in;
flush metodu
Şöyle yaparız.
streamBuf.flush();
operator << metodu
Şöyle yaparız.
std::ifstream ifs = ...;
streamBuf << ifs.rdbuf();
push metodu - compressor
Şöyle yaparız.
boost::iostreams::filtering_ostream out;
1. stringstream'e yazma
Şöyle yaparız. Önce sıkıştırma işlemi yapar. Daha sonra bir sonraki stream'e sıkıştırılmış veriyi yazar.
out.push (boost::iostreams::zlib_compressor());

std::stringstream outStream;
out.push (outStream);
Sıkıştırmak işlemini şöyle yaparız. İstersek source stream'in rdbuf() metodunu da kullanabiliriz.
std::stringstream source;
source << ...;

boost::iostreams::copy (source, out);
Daha sonra stream'i string'e çevirip kullanırız.
std::string data = outStream.str();
2. iostream'e yazma
Yani socket'e yazarız. Şöyle yaparız.
tcp::iostream ss = ...;

boost::iostreams::filtering_ostream out;
out.push (boost::iostreams::zlib_compressor());
out.push (ss);

std::ifstream ifs("main.cpp", std::ios::binary);
out << ifs.rdbuf();
out.flush();
3. binary_oarchive'a yazma
Temelde dosyaya yazma ile aynı şey. Şöyle yaparız.
template <typename T>
void write_data(std::string const& fname, std::vector<T> const& data) {
  std::ofstream ofs(fname, std::ios_base::binary);
  bio::filtering_ostream out;

  out.push(bio::zlib_compressor());
  out.push(ofs);

  boost::archive::binary_oarchive oa(out);
  oa << data;
}
push metodu - decompressor
Şöyle yaparız.
boost::iostreams::filtering_istream in;
1. Dosyadan okuma
Örnek
Dosyadan okuyup cout'a yazmak için şöyle yaparız. Önce sıkıştırılmış veriyi okur daha sonra açma işlemini yapar.
in.push (boost::iostreams::gzip_decompressor());

std::ifstream gzfile ("a.gz",std::ios::binary);
in.push (gzfile);
Açma işlemini için şu satırı dahil ederiz.
#include <boost/iostreams/copy.hpp>
Şöyle yaparız.
boost::iostreams::copy (in,std::cout); 
Örnek
Şöyle yaparız.
ifstream file("hello.z", ios_base::in | ios_base::binary);
filtering_streambuf<input> in;
in.push(zlib_decompressor());
in.push(file);
boost::iostreams::copy(in, cout);
Örnek
Şöyle yaparız
ifstream file = ("file.z", ios_base::in | ios_base::binary);
boost::iostreams::filtering_streambuf<boost::iostreams::input> in;
in.push(boost::iostreams::zlib_decompressor());
in.push(file);
std::istream *inf = new std::istream(&in);

std::streambuf *sb = inf->rdbuf();
//Print 30 characters
int i = 30;
while ( i > 0 )
{
  cout << (char)sb->sbumpc();
  --i;
}
2. iostream'den okuma
Socketten okurken socket EOF sinyalleyebilir. Soketten okuyup dosyaya yazmak için şöyle yaparız.
tcp::iostream ss = ...;

boost::iostreams::filtering_istream in;
in.push(boost::iostreams::zlib_decompressor());
in.push (ss);

std::ofstream ofs ("main.cpp", std::ios::binary);
boost::iostreams::copy  (in, ofs);
socketten okumak için streambuf'ta kullanılabilir. Şöyle yaparız.
// Prepare decompressing istream
boost::asio::streambuf sbuf;
boost::iostreams::filtering_istream is;
is.push(boost::iostreams::zlib_decompressor());
is.push(sbuf);
3. binary_iarchive'dan okuma
Temelde dosyadan okuma ile aynı şey. Şöyle yaparız.
template <typename T>
std::vector<T> read_data(std::string const& fname) {
  std::vector<T> result;

  std::ifstream file_in(fname, std::ios_base::binary);
  bio::filtering_istream in;

  in.push(bio::zlib_decompressor());
  in.push(file_in);

  boost::archive::binary_iarchive ia(in);
  ia >> result;

  return result;
}



Hiç yorum yok:

Yorum Gönder