Proxies: Who's wearing the trousers?
TL;DR I want to be able to do this:
producer_active_object(enqueuer_proxy(concurrent_queue));
consumer_active_object(dequeuer_proxy(concurrent_queue));
Today' reference will mostly be:
producer_active_object(enqueuer_proxy(concurrent_queue));
consumer_active_object(dequeuer_proxy(concurrent_queue));
Today' reference will mostly be:
The proxy pattern[1] provides restricted or modified access to hidden or protected resources. There are a few subsets of proxies:
Okay so here is the design description:
References:
[1] Wikipedia Proxy Pattern
[2] When should you use 'friend' in C++?
- remote proxy
- virtual proxy
- protection proxy
- smart reference
The kind of proxy that the message_queue type needs is combination of the last 2 that offers:
- Access to the head and tail of the message queue via its various private enqueue and dequeue member functions.
- Counting the number of references to the message queue and closing it down when either there are no more interested consumer(s) or the producer(s) have finished producing.
Okay so the design choices are to either:
- Have a zoo of some_message_queue types each with member functions for generating their own proxies that use the extremely useful friendship C++ language feature[2]
- Select a specific some_message_queue policy from the zoo and wrap it in a generic message_queue type which dishes out the head and tail proxies.
Well at least there is no goat in this problem so in true Monty Hall style
"Let's see what's behind door number 2..."
Okay so here is the design description:
- A concurrent_queue wrapper shared_queue locked up tighter than a chastity belt.
- 2 concurrent_queue befriended enqueuer and dequeuer proxies that template specialise on the queue type but both have the key of friendship to shared_queue's chastity.
- 3(+) queue interfaces (for wait, try & timed wait queue access) carrying queue closure semantics.
And the class diagram that results:
libfbp queue package class diagram (created with GenMyModel) |
Here is how to use these classes:
Producing this output:
The queue sharing shared_queue class that manages dequeuer(s) and enqueuer(s) and closes the underlying queue as appropriate:
The dequeuer class:
Full code for all the interacting queue classes at: github.com/ifknot/libfbp
Producing this output:
1,2,3,4,5,
6,7,8,9,10, (╯°□°)╯︵ ┻━┻ Access to resource is closed!
The queue sharing shared_queue class that manages dequeuer(s) and enqueuer(s) and closes the underlying queue as appropriate:
The dequeuer class:
Full code for all the interacting queue classes at: github.com/ifknot/libfbp
References:
[1] Wikipedia Proxy Pattern
[2] When should you use 'friend' in C++?
No comments:
Post a Comment