LINQ for C++ というライブラリーにjoinというメソッドがあります。
これを使うとSQLのJOINみたいなこと超簡単にできます。
やっつけで作ったサンプルですが、join_test.cppのmain()の中で使っています。
あと、このライブラリーはモダンな作りでヘッダー・オンリーなので使いやすいです。
join_test.cpp
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <utility>
#include <cstdlib>
#include "cpplinq.hpp"
using namespace std;
struct test_data
{
test_data() : string_code(), numeric_data()
{}
test_data(string string_code0, long numeric_data0) : string_code(string_code0), numeric_data(numeric_data0)
{}
string string_code;
long numeric_data;
};
void read_file(vector<test_data>& input, const char *filename)
{
ifstream in(filename);
string line;
while (getline(in, line)) {
size_t pos = line.find('\t');
if (pos != string::npos) {
long numeric_data = atol(&line[pos] + 1);
input.emplace_back(line.substr(0, pos), numeric_data);
}
}
}
int main()
{
using namespace cpplinq;
vector<test_data> input1, input2;
read_file(input1, "input1.tsv");
read_file(input2, "input2.tsv");
auto query = from(input1)
>> join (
from(input2),
[](test_data const& left) { return left.string_code; },
[](test_data const& right) { return right.string_code; },
[](test_data const& left, test_data const& right) { return make_pair(left.numeric_data, right.numeric_data); })
>> to_vector()
;
for (auto const& row : query) {
cout << row.first << "\t" << row.second << endl;
}
return 0;
}
ビルド用のファイル
Jamroot
import testing ;
run join_test.cpp
:
:
: <toolset>gcc:<cxxflags>-std=gnu++0x <toolset>clang:<cxxflags>-std=c++11
;
テストデータ作成ツール
gen_test_data.py
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import uuid
import random
from optparse import OptionParser
parser = OptionParser()
parser.add_option("-n", "--num", dest="num", default="100")
(options, args) = parser.parse_args()
data = [ (uuid.uuid4(), num) for num in range(0, int(options.num)) ]
random.shuffle(data)
with open('input1.tsv', 'wb') as f:
for row in data:
print >>f, "%s\t%d" % (row[0], row[1])
random.shuffle(data)
with open('input2.tsv', 'wb') as f:
for row in data:
print >>f, "%s\t%d" % (row[0], row[1])
使い方の例
./gen_test_data.py --num=100
time bjam variant=release -a
同じようなライブラリーで、Ovenというのを使ってもできそうな気がしますが、こちらは試してないです。