48#ifndef Sawyer_Attribute_H 
   49#define Sawyer_Attribute_H 
   51#include <boost/any.hpp> 
   52#include <boost/foreach.hpp> 
   53#include <boost/lexical_cast.hpp> 
   54#include <Sawyer/Exception.h> 
   55#include <Sawyer/Map.h> 
   56#include <Sawyer/Optional.h> 
   57#include <Sawyer/Sawyer.h> 
   58#include <Sawyer/Synchronization.h> 
  169SAWYER_EXPORT 
Id id(
const std::string &name);
 
  177SAWYER_EXPORT 
const std::string& name(
Id);
 
  188        : Exception::NotFound(attrName + 
" does not exist in object") {}
 
 
 
  198        : Exception::
AlreadyExists(attrName + 
" is already a declared attribute (id=" +
 
  199                                   boost::lexical_cast<std::string>(
id) + 
")") {}
 
 
 
  214template<
class SyncTag = SAWYER_THREAD_TAG>
 
  222    mutable typename Sync::Mutex mutex_;
 
  235        typename Sync::LockGuard lock(other.mutex_);
 
  236        values_ = other.values_;
 
 
  243        typename Sync::LockGuard2 lock(mutex_, other.mutex_);
 
  244        values_ = other.values_;
 
 
  254        typename Sync::LockGuard lock(mutex_);
 
  255        return values_.
exists(
id);
 
 
  265        typename Sync::LockGuard lock(mutex_);
 
 
  273        typename Sync::LockGuard lock(mutex_);
 
 
  286        typename Sync::LockGuard lock(mutex_);
 
  287        values_.
insert(
id, boost::any(value));
 
 
  299        typename Sync::LockGuard lock(mutex_);
 
  300        if (!values_.
exists(
id)) {
 
  301            values_.
insert(
id, boost::any(value));
 
 
  316        typename Sync::LockGuard lock(mutex_);
 
  317        AttrMap::ConstNodeIterator found = values_.
find(
id);
 
  318        if (found == values_.
nodes().end()) {
 
  321                throw DoesNotExist(
"attribute id " + boost::lexical_cast<std::string>(
id) + 
" [not declared]");
 
 
  335        typename Sync::LockGuard lock(mutex_);
 
  337        if (
const auto foundAny = values_.
getOptional(
id)) {
 
  338            return boost::any_cast<T>(*foundAny);
 
 
  353        typename Sync::LockGuard lock(mutex_);
 
 
  367        typename Sync::LockGuard lock(mutex_);
 
  368        AttrMap::ConstNodeIterator found = values_.
find(
id);
 
  369        if (found == values_.
nodes().end())
 
  371        return boost::any_cast<T>(found->value());
 
 
  381        typename Sync::LockGuard lock(mutex_);
 
  382        AttrMap::ConstNodeIterator found = values_.
find(
id);
 
  383        if (found == values_.
nodes().end())
 
  385        return boost::any_cast<T>(found->value());
 
 
  392        typename Sync::LockGuard lock(mutex_);
 
  393        return values_.
size();
 
 
  400        typename Sync::LockGuard lock(mutex_);
 
  401        std::vector<Id> retval;
 
  402        retval.reserve(values_.
size());
 
  403        BOOST_FOREACH (
Id id, values_.
keys())
 
  404            retval.push_back(
id);
 
 
 
 
Exception thrown when redeclaring an existing attribute.
 
AlreadyExists(const std::string &attrName, Id id)
Constructor taking an attribute name or description.
 
Exception for non-existing values.
 
DoesNotExist(const std::string &attrName)
Constructor taking an attribute name or description.
 
API and storage for attributes.
 
std::vector< Id > attributeIds() const
Returns ID numbers for all IDs stored in this container.
 
bool setAttributeMaybe(Id id, const T &value)
Store an attribute if not already present.
 
Sawyer::Optional< T > optionalAttribute(Id id) const
Return the attribute as an optional value.
 
size_t nAttributes() const
Number of attributes stored.
 
void eraseAttribute(Id id)
Erase an attribute.
 
T attributeOrDefault(Id id) const
Return an attribute or a default-constructed value.
 
T attributeOrElse(Id id, const T &dflt) const
Return an attribute or a specified value.
 
void setAttribute(Id id, const T &value)
Store an attribute.
 
Storage(const Storage &other)
Copy constructor.
 
Sawyer::Optional< T > getAttributeMaybe(const Id id) const
Return an attribute if it exists, or else nothing.
 
void clearAttributes()
Erase all attributes.
 
bool attributeExists(Id id) const
Check attribute existence.
 
Storage & operator=(const Storage &other)
Assignment operator.
 
Storage()
Default constructor.
 
T getAttribute(Id id) const
Get an attribute that is known to exist.
 
Container associating values with keys.
 
NodeIterator find(const Key &key)
Find a node by key.
 
bool exists(const Key &key) const
Determine if a key exists.
 
size_t size() const
Number of nodes, keys, or values in this container.
 
Optional< Value > getOptional(const Key &key) const
Lookup and return a value or nothing.
 
Map & erase(const Key &key)
Remove a node with specified key.
 
boost::iterator_range< NodeIterator > nodes()
Iterators for container nodes.
 
boost::iterator_range< ConstKeyIterator > keys()
Iterators for container keys.
 
Map & insert(const Key &key, const Value &value)
Insert or update a key/value pair.
 
Map & clear()
Remove all nodes.
 
Error for existing values.
 
Error for non-existing values.
 
Holds a value or nothing.
 
Value orDefault() const
Obtain a value or a default.
 
const Value & orElse(const Value &dflt) const
Obtain value or something else.
 
const Id INVALID_ID
Invalid attribute ID.
 
boost::bad_any_cast WrongQueryType
Exception thrown when wrong data type is queried.
 
Id declareMaybe(const std::string &name)
Register a new attribute key if not already registered.
 
const std::string & name(Id)
Returns the name for an attribute ID.
 
size_t Id
Attribute identification.
 
Id id(const std::string &name)
Returns the ID for an attribute name.
 
Id declare(const std::string &name)
Register a new attribute key.
 
void checkBoost()
Check for valid boost version or abort.
 
Traits for thread synchronization.