Boost logo

Boost :

Subject: Re: [boost] GSOC 2015 : Project on Concurrent Hash Tables
From: Niall Douglas (s_sourceforge_at_[hidden])
Date: 2015-03-14 12:43:53


On 14 Mar 2015 at 15:24, Amarnath V A wrote:

> > The move constructor can be written in two lines I believe. Think in
> > terms of what other functions already present could be called to
> > implement the move constructor for you. You should find the move
> > constructor becomes quite trivial to implement, maybe two calls into
> > other routines.
>
> Taking hints from Niall's suggestions, I have re-implemented the move
> constructor using the member functions. Now, I extract the items first
> and then insert them into the new map.
>
> concurrent_unordered_map(concurrent_unordered_map &&old_map)
> BOOST_NOEXCEPT :
> _hasher(std::move(old_map._hasher)),
> _key_equal(std::move(old_map._key_equal)),
> _allocator(std::move(old_map._allocator)),
> _max_load_factor(std::move(old_map._max_load_factor)),
> _min_bucket_capacity(std::move(old_map._min_bucket_capacity)),
> _oldbucketit(_oldbuckets.begin())
> {
> _oldbuckets.fill(nullptr);
> auto items=old_map.extract(old_map.begin(), old_map.end());
> buckets_type *buckets=new buckets_type(items.size());
> buckets=_buckets.exchange(buckets, memory_order_acq_rel);
> insert(std::make_move_iterator(items.begin()),
> std::make_move_iterator(items.end()));
> }

Much better.

Though in fact you can do better again. As I mentioned, I think maybe
two lines. Remember in C++ 11 constructors can call other
constructors.

> > I don't believe the copy constructor is as easy though. That you will
> > have to implement yourself.
>
> I am copying the snapshot of the original map when the call to the
> constructor was made.
>
> concurrent_unordered_map(const concurrent_unordered_map &old_map) :
> _hasher(old_map._hasher),
> _key_equal(old_map._key_equal),
> _allocator(old_map._allocator),
> _max_load_factor(old_map._max_load_factor),
> _min_bucket_capacity(old_map._min_bucket_capacity),
> _oldbucketit(_oldbuckets.begin())
> {
> _oldbuckets.fill(nullptr);
> buckets_type
> *tempbuckets=old_map._buckets.load(memory_order_consume);
> buckets_type *buckets=new buckets_type(tempbuckets->size());
> buckets=_buckets.exchange(buckets, memory_order_acq_rel);
> for(const auto &ob : *tempbuckets)
> {
> if(ob.count.load(memory_order_relaxed))
> {
> for(auto &i : ob.items)
> {
> if(i.p)
> {
> insert(*(i.p));
> }
> }
> }
> }
> }

Now you're beginning to think more like an engineer. Good.

The above is closer to working properly, but you've got a while to go
yet.

> Please let me know if I have got it completely wrong again. If that is
> the case, I don't think I should apply for GSoC this year. I have to
> take a step back and learn more about concurrent data structures to
> gain more knowledge.

"completely wrong" is too strong. Lack of experience that's all, same
as any GSoC student.

I'd aim for solid unit testing next. Really the competency test is
testing whether students know how to test whether their solution is
correct or not. I think the community ranking would favour a solid
unit testing of an incorrect solution more than poor unit testing of
a correct solution.

Niall

-- 
ned Productions Limited Consulting
http://www.nedproductions.biz/ 
http://ie.linkedin.com/in/nialldouglas/



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