Hatena::ブログ(Diary)

Life like a clown このページをアンテナに追加 RSSフィード Twitter

2009-01-08

文字列の16進数ダンプ

文字列を 16 進数でダンプする関数が必要になりそうなので作成しました.入力/出力用のイテレータを引数に指定すると,入力から1文字ずつ読み込み,16進数の文字列として出力します.ただ,この関数を使用する場合 hexdump<char>(src.begin(), src.end(), dest) のように,わざわざテンプレート引数に char を指定しなければならないので,入力として文字列およびストリームを指定する関数をオーバーロードしました.

#include <iterator>
#include <limits>
#include <sstream>

template <class CharT, class InIter, class OutIter>
OutIter hexdump(InIter first, InIter last, OutIter dest) {
    static const int shift = ((sizeof(unsigned long) - sizeof(CharT)) * 8);
    static const unsigned long mask = std::numeric_limits<unsigned long>::max() >> shift;
    
    std::basic_stringstream<CharT> ss;
    for (; first != last; ++first, ++dest) {
        ss << std::hex << (static_cast<int>(*first) & mask);
        *dest = ss.str();
        ss.str("");
    }
    return dest;
}

template <class CharT, class OutIter>
OutIter hexdump(std::basic_istream<CharT>& src, OutIter dest) {
    std::istream_iterator<CharT> input(src);
    std::istream_iterator<CharT> last;
    return hexdump<CharT>(input, last, dest);
}

template <class CharT, class OutIter>
OutIter hexdump(const std::basic_string<CharT>& src, OutIter dest) {
    return hexdump<CharT>(src.begin(), src.end(), dest);
}

サンプルプログラムと実行結果は以下の通り.

#include <iostream>
#include <iterator>
#include "hexdump.h"

int main(int argc, char* argv[]) {
    std::ostream_iterator<std::string> out(std::cout, " ");
    hexdump(std::cin, out);
    return 0;
}
Result

$ ./test < example_hexdump.cpp 
23 69 6e 63 6c 75 64 65 3c 69 6f 73 74 72 65 61 6d 3e 23 69 6e 63 6c 75 64 65 3c 
69 74 65 72 61 74 6f 72 3e 23 69 6e 63 6c 75 64 65 22 63 6c 78 2f 68 65 78 64 75 
6d 70 2e 68 22 69 6e 74 6d 61 69 6e 28 69 6e 74 61 72 67 63 2c 63 68 61 72 2a 61 
72 67 76 5b 5d 29 7b 73 74 64 3a 3a 6f 73 74 72 65 61 6d 5f 69 74 65 72 61 74 6f 
72 3c 73 74 64 3a 3a 73 74 72 69 6e 67 3e 6f 75 74 28 73 74 64 3a 3a 63 6f 75 74 
2c 22 22 29 3b 63 6c 78 3a 3a 68 65 78 64 75 6d 70 28 73 74 64 3a 3a 63 69 6e 2c 
6f 75 74 29 3b 72 65 74 75 72 6e 30 3b 7d