std::ifstream の range
テキストファイルの行単位での範囲を取得するとかそんな感じ。
#include <iostream> #include <fstream> #include <string> #define BOOST_FILESYSTEM_VERSION 3 #include <boost/range.hpp> #include <boost/filesystem.hpp> #include <boost/filesystem/fstream.hpp> #include <boost/range/algorithm/for_each.hpp> #include <boost/lexical_cast.hpp> #include <boost/foreach.hpp> #include <boost/iterator_adaptors.hpp> struct ifstream_line_range{ ifstream_line_range(std::ifstream& ifs_) : ifs(ifs_){} struct iterator : boost::iterator_adaptor< iterator, ifstream_line_range*, const std::string&, boost::forward_traversal_tag >{ typedef boost::iterator_adaptor< iterator, ifstream_line_range*, const std::string&, boost::forward_traversal_tag > inheritance; iterator(ifstream_line_range* p) : inheritance(p){} void increment(){ base()->ifs >> base()->line; } const std::string& dereference() const{ return base()->line; } bool operator !=(const iterator& it) const{ return !base()->ifs.eof(); } }; iterator begin(){ ifs.clear(); ifs.seekg(0, std::ios::beg); ifs >> line; return iterator(this); } iterator end(){ return iterator(NULL); } std::ifstream& ifs; std::string line; }; int main(){ namespace fs = boost::filesystem; fs::path test_file("test.txt"); fs::remove(test_file); fs::ofstream ofs(test_file); for(int i = 0 ; i < 10 ; i++){ ofs << "test" + boost::lexical_cast<std::string>(i) << "\n"; } ofs.close(); std::ifstream ifs(test_file.string()); auto range = ifstream_line_range(ifs); for( ifstream_line_range::iterator it = range.begin() ; it != range.end() ; it++ ){ std::cout << *it << std::endl; } return 0; }
ここまでは考えた。
イテレータの部分がかなり適当。
バイナリ単位の範囲をとってきて、\n で区切った range とか作った方が綺麗になりそうな気がする。
stream からバッファの取得の仕方が分からんが・・・。
あとこれだと const_iterator が作れない。
それ以前に boost にファイルの中身を扱うライブラリとかないんだろうか。
暗号化やファイルの結合なんかが出来るとかなりべんりーなんだけども。
ゲームデータとかを1つのファイルにまとめて圧縮したり暗号化するとかそんなイメージ。
風邪気味でこれ以上は頭が回らない・・・。
つpstade::oven::stream_line