Boost logo

Boost :

From: Arkadiy Vertleyb (vertleyb_at_[hidden])
Date: 2005-10-05 19:38:09


"Arkadiy Vertleyb" <vertleyb_at_[hidden]> wrote

> Another example -- you have table of cities, and you need to get all the
> pairs, such as the distance between them is less than certain number. How
> would one solve the problem with the conventional SQL approach? This is a
> self-join. But how to make this query fast?
>
> With RTL approach, we could create an index on this self-join.

Here is a simple example that illustrates this. The attached program does
the following:

1) creates table of one column;
2) self-joins the table
3) selects records where columns are equal.

This by itself doesn't make any sence, but it closely approximates the task
of finding close cities, stars, billiard balls, monsters and soldiers, etc.

Here is the text (Boost CVS head was used to be able to use typeof):

/////////////////////
#include <table_delta.hpp>
#include <utils.hpp>
#include <selection_delta.hpp>
#include <key_index_delta.hpp>
#include <crossproduct_delta.hpp>
#include <rename_delta.hpp>
#include <boost/lambda/lambda.hpp>
#include <boost/typeof/typeof.hpp>
#include <expression_registry.hpp>
#include <transaction.hpp>
#include <cstdlib>

using namespace boost;
using namespace boost::lambda;

BOOST_RTL_DEFINE_COLUMN(int, c1);

struct my_info : rel::table_info<
    mpl::vector<c1>
>{};

typedef rel::table<my_info> my_table;
typedef my_table::value_type my_tuple;

struct a;
typedef rel::alias<c1, a> c2;

main()
{
    // populate table

    my_table t;

    for (int i = 0; i < 3000; ++i)
        t.insert(my_tuple(i + 1));

    // create and print the view

    BOOST_AUTO(t2, rel::auto_rename<a>(t));

    BOOST_AUTO(xp, rel::cross_product(t, t2));

    BOOST_AUTO(pred,
        _1[c1()] == _1[c2()]
        );

    BOOST_AUTO(sel,
        rel::selection(xp, pred)
        );

    std::cout << "building index" << std::endl;

    BOOST_AUTO(idx,
        (rel::key_index<mpl::vector<c1, c2> >(sel))
        );

    std::cout << "printing index" << std::endl;

    rel::print(idx);

    // update table (index doesn't get fully rebuilt)

    rel::expression_registry exprs;
    exprs.add(idx);

    rel::transaction tr;

    for (i = 0; i < 10; ++i)
        tr.insert(t, my_tuple(-i));

    tr.commit(exprs);

    // print the view once again

    std::cout << "printing updated index" << std::endl;
    rel::print(idx);

    return 0;
}
/////////////////

Regards,
Arkadiy


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk