| <?xml version="1.0" encoding="utf-8" ?> |
| <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> |
| <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> |
| <head> |
| <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> |
| <meta name="generator" content="Docutils 0.6: http://docutils.sourceforge.net/" /> |
| <title>Boost Dynamic Property Maps</title> |
| <link rel="stylesheet" href="../../parameter/doc/html/rst.css" type="text/css" /> |
| </head> |
| <body> |
| <div class="document" id="logo-dynamic-property-maps"> |
| <h1 class="title"><a class="reference external" href="../../../index.htm"><img align="middle" alt="Boost" class="align-middle" src="../../../boost.png" /></a> Dynamic Property Maps</h1> |
| |
| <!-- Copyright 2004-5 The Trustees of Indiana University. |
| |
| Use, modification and distribution is subject to the Boost Software |
| License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at |
| http://www.boost.org/LICENSE_1_0.txt) --> |
| <div class="section" id="summary"> |
| <h1><a class="toc-backref" href="#id2">Summary</a></h1> |
| <p>The dynamic property map interfaces provides access to a collection of |
| property maps through a dynamically-typed interface. An algorithm can |
| use it to manipulate property maps without knowing their key or |
| value types at compile-time. Type-safe codes can use dynamic property |
| maps to interface more easily and completely with scripting languages |
| and other text-based representations of key-value data.</p> |
| <div class="contents topic" id="contents"> |
| <p class="topic-title first">Contents</p> |
| <ul class="simple"> |
| <li><a class="reference internal" href="#summary" id="id2">Summary</a></li> |
| <li><a class="reference internal" href="#introduction" id="id3">Introduction</a><ul> |
| <li><a class="reference internal" href="#fred-s-info-revisited" id="id4">"Fred's Info" Revisited</a></li> |
| </ul> |
| </li> |
| <li><a class="reference internal" href="#reference" id="id5">Reference</a><ul> |
| <li><a class="reference internal" href="#member-functions" id="id6">Member Functions</a></li> |
| <li><a class="reference internal" href="#free-functions" id="id7">Free functions</a></li> |
| <li><a class="reference internal" href="#exceptions" id="id8">Exceptions</a></li> |
| </ul> |
| </li> |
| </ul> |
| </div> |
| </div> |
| <div class="section" id="introduction"> |
| <h1><a class="toc-backref" href="#id3">Introduction</a></h1> |
| <p>The Boost Property Map library specifies statically type-safe |
| interfaces through which key-value pairs can be manipulated by |
| generic algorithms. Typically, an algorithm that uses property maps is |
| parameterized on the types of the property maps it uses, and it |
| manipulates them using the interfaces specified by the |
| Boost Property Map Library.</p> |
| <p>The following generic function illustrates property map basics.</p> |
| <pre class="literal-block"> |
| template <typename AgeMap, typename GPAMap> |
| void |
| manipulate_freds_info(AgeMap ages, GPAMap gpas) { |
| |
| typedef typename boost::property_traits<AgeMap>::key_type name_type; |
| typedef typename boost::property_traits<AgeMap>::value_type age_type; |
| typedef typename boost::property_traits<GPAMap>::value_type gpa_type; |
| |
| name_type fred = "Fred"; |
| |
| age_type old_age = get(ages, fred); |
| gpa_type old_gpa = get(gpas, fred); |
| |
| std::cout << "Fred's old age: " << old_age << "\n" |
| << "Fred's old gpa: " << old_gpa << "\n"; |
| |
| age_type new_age = 18; |
| gpa_type new_gpa = 3.9; |
| put(ages, fred, new_age); |
| put(gpas, fred, new_gpa); |
| } |
| </pre> |
| <p>The function is parameterized on two property map types, <tt class="docutils literal"><span class="pre">AgeMap</span></tt> and |
| <tt class="docutils literal"><span class="pre">GPAMap</span></tt>, and takes a value parameter for each of those types. The |
| function uses the <tt class="docutils literal"><span class="pre">property_traits</span></tt> interface to ascertain, at |
| compile-time, the value and key types of the property maps. The code |
| then retrieves Fred's old information, using the <tt class="docutils literal"><span class="pre">get</span></tt> function, and |
| updates it using the <tt class="docutils literal"><span class="pre">put</span></tt> function. The <tt class="docutils literal"><span class="pre">get</span></tt> function is required by the |
| Readable Property Map concept and both <tt class="docutils literal"><span class="pre">get</span></tt> and <tt class="docutils literal"><span class="pre">put</span></tt> are required by the |
| Read/Write Property Map concept.</p> |
| <p>The above function not only requires the two type parameters to model |
| property map concepts, but also makes some extra assumptions. |
| <tt class="docutils literal"><span class="pre">AgeMap</span></tt> and <tt class="docutils literal"><span class="pre">GPAMap</span></tt> must have the same key type, and that type must be |
| constructable from a string. Furthermore, <tt class="docutils literal"><span class="pre">AgeMap</span></tt>'s value type must be |
| constructable from an <tt class="docutils literal"><span class="pre">int</span></tt>. Although these requirements are not |
| explicitly stated, they are statically checked during compilation and |
| failure to meet them yields compile-time errors.</p> |
| <p>Although the static typing of property map interfaces usually provides |
| desirable compile-time safety, some algorithms require a more dynamic |
| interface to property maps. For example, the Boost Graph Library (BGL) |
| provides functions that can initialize a graph by interpreting the |
| contents of a textual graph description (i.e. a GraphML file). Such |
| general-purpose graph description languages can specify an arbitrary |
| number of edge and vertex properties, using strings to represent the |
| key-value pairs. A graph reader function should capture these |
| arbitrary properties, but since function templates can only be |
| parameterized on a fixed number of property maps, the traditional |
| techniques for handling property maps do not suffice to implement them.</p> |
| <p>Dynamic property maps specifically address the need for an interface |
| to property maps whose checking is delayed to runtime. Several |
| components combine to provide support for dynamic property maps. The |
| <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> class collects a |
| group of heterogenous objects that model concepts from |
| the Boost Property Map library. Each property map is assigned a |
| string-based key when it is added to the collection, and it can be |
| addressed using that key. Internally, <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> adapts |
| each contained property map with the dynamic property map interface, |
| which provides <tt class="docutils literal"><span class="pre">get</span></tt> and <tt class="docutils literal"><span class="pre">put</span></tt> functions that |
| can be called using values of any type that meets a few requirements. |
| Internally, the dynamic property map converts key and value pairs to |
| meet the requirements of the underlying property map or signals a |
| runtime exception if it cannot.</p> |
| <div class="section" id="fred-s-info-revisited"> |
| <h2><a class="toc-backref" href="#id4">"Fred's Info" Revisited</a></h2> |
| <p>Here's what the example above looks like using the |
| <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> interface:</p> |
| <pre class="literal-block"> |
| void manipulate_freds_info(boost::dynamic_properties& properties) |
| { |
| using boost::get; |
| std::string fred = "Fred"; |
| |
| int old_age = get<int>("age", properties, fred); |
| std::string old_gpa = get("gpa", properties, fred); |
| |
| std::cout << "Fred's old age: " << old_age << "\n" |
| << "Fred's old gpa: " << old_gpa << "\n"; |
| |
| std::string new_age = "18"; |
| double new_gpa = 3.9; |
| put("age",properties,fred,new_age); |
| put("gpa",properties,fred,new_gpa); |
| } |
| </pre> |
| <p>The new function is not a template parameterized on the property map |
| types but instead a concrete function that takes a <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> |
| object. Furthermore, the code no longer makes reference to key or |
| value types: keys and values are represented with strings. |
| Nonetheless the function still uses non-string types where they are |
| useful. For instance, Fred's old age is represented using an <tt class="docutils literal"><span class="pre">int</span></tt>. |
| It's value is retreived by calling <tt class="docutils literal"><span class="pre">get</span></tt> with a |
| type parameter, which determines its return type. Finally, the |
| <tt class="docutils literal"><span class="pre">get</span></tt> and <tt class="docutils literal"><span class="pre">put</span></tt> functions are each supplied a string-based key that |
| differs depending on the property of concern.</p> |
| <p>Here's an example of how the above function might be called.</p> |
| <pre class="literal-block"> |
| int main() |
| { |
| using boost::get; |
| |
| // build property maps using associative_property_map |
| std::map<std::string, int> name2age; |
| std::map<std::string, double> name2gpa; |
| boost::associative_property_map< std::map<std::string, int> > |
| age_map(name2age); |
| boost::associative_property_map< std::map<std::string, double> > |
| gpa_map(name2gpa); |
| |
| std::string fred("Fred"); |
| // add key-value information |
| name2age.insert(make_pair(fred,17)); |
| name2gpa.insert(make_pair(fred,2.7)); |
| |
| // build and populate dynamic interface |
| boost::dynamic_properties properties; |
| properties.property("age",age_map); |
| properties.property("gpa",gpa_map); |
| |
| manipulate_freds_info(properties); |
| |
| std::cout << "Fred's age: " << get(age_map,fred) << "\n" |
| << "Fred's gpa: " << get(gpa_map,fred) << "\n"; |
| } |
| </pre> |
| <p>The code first creates two property maps using <tt class="docutils literal"><span class="pre">std::map</span></tt> and the |
| <tt class="docutils literal"><span class="pre">associative_property_map</span></tt> adaptor. After initializing the |
| property maps with key-value data, it constructs a |
| <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object and adds to it both property maps, |
| keyed on the strings "age" and "gpa". Finally <tt class="docutils literal"><span class="pre">manipulate_freds_info</span></tt> |
| is passed the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object and the results of its changes are |
| displayed.</p> |
| <p>As shown above, the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object provides, where needed, a |
| dynamically-typed interface to property maps yet preserves the static |
| typing of property map uses elsewhere in an application.</p> |
| </div> |
| </div> |
| <div class="section" id="reference"> |
| <h1><a class="toc-backref" href="#id5">Reference</a></h1> |
| <pre class="literal-block"> |
| class dynamic_properties |
| </pre> |
| <p>The <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> class provides a dynamically-typed interface to |
| a set of property maps. To use it, one must populate |
| an object of this class with property maps using the <tt class="docutils literal"><span class="pre">property</span></tt> member |
| function.</p> |
| <div class="section" id="member-functions"> |
| <h2><a class="toc-backref" href="#id6">Member Functions</a></h2> |
| <pre class="literal-block"> |
| dynamic_properties() |
| dynamic_properties( |
| const boost::function< |
| boost::shared_ptr<dynamic_property_map> ( |
| const std::string&, const boost::any&, const boost::any&) |
| >& fn) |
| </pre> |
| <p>A <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object can be constructed with a function object |
| that, when called, creates a new property map. The library provides the |
| <tt class="docutils literal"><span class="pre">ignore_other_properties</span></tt> function object, which lets the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object ignore any properties that it hasn't been prepared to record. |
| If an attempt is made |
| to <tt class="docutils literal"><span class="pre">put</span></tt> a key-value pair to a nonexistent <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> key, |
| then this function is called with the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> key and the |
| intended property key and value . If <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> is |
| default-constructed, such a <tt class="docutils literal"><span class="pre">put</span></tt> attempt throws |
| <tt class="docutils literal"><span class="pre">property_not_found</span></tt>.</p> |
| <pre class="literal-block"> |
| template<typename PropertyMap> |
| dynamic_properties& |
| property(const std::string& name, PropertyMap property_map) |
| </pre> |
| <p>This member function adds a property map to the set of maps contained, |
| using <tt class="docutils literal"><span class="pre">name</span></tt> as its key.</p> |
| <p>Requirements: <tt class="docutils literal"><span class="pre">PropertyMap</span></tt> must model Readable Property Map or |
| Read/Write Property Map.</p> |
| <pre class="literal-block"> |
| void insert(const std::string& name, boost::shared_ptr<dynamic_property_map> pm) |
| </pre> |
| <p>This member function directly adds a <tt class="docutils literal"><span class="pre">dynamic_property_map</span></tt> |
| to the collection, using <tt class="docutils literal"><span class="pre">name</span></tt> as its key.</p> |
| <pre class="literal-block"> |
| iterator begin() |
| const_iterator begin() const |
| </pre> |
| <p>This member function returns an iterator over the set of property maps |
| held by the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object.</p> |
| <pre class="literal-block"> |
| iterator end() |
| const_iterator end() const |
| </pre> |
| <p>This member function returns a terminal iterator over the set of |
| dynamic property maps held by the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object. It is used to |
| terminate traversals over the set of dynamic property maps</p> |
| <pre class="literal-block"> |
| iterator lower_bound(const std::string& name) |
| </pre> |
| <p>This member function returns an iterator that points to the first |
| property map whose <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> key is <tt class="docutils literal"><span class="pre">name</span></tt>. |
| Bear in mind that multiple property maps may have the same |
| <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> key, so long as their property map key types differ.</p> |
| <p>Invariant: The range [ lower_bound(name), end() ) contains every |
| property map that has name for its <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> key.</p> |
| </div> |
| <div class="section" id="free-functions"> |
| <h2><a class="toc-backref" href="#id7">Free functions</a></h2> |
| <pre class="literal-block"> |
| boost::shared_ptr<boost::dynamic_property_map> |
| ignore_other_properties(const std::string&, |
| const boost::any&, |
| const boost::any&) |
| </pre> |
| <p>When passed to the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> constructor, this function |
| allows the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object to disregard attempts to put |
| values to unknown keys without signaling an error.</p> |
| <pre class="literal-block"> |
| template<typename Key, typename Value> |
| bool put(const std::string& name, dynamic_properties& dp, const Key& key, |
| const Value& value) |
| </pre> |
| <p>This function adds a key-value pair to the property map with the |
| matching name and key type. If no matching property map is found, |
| behavior depends on the availability of a property map generator. If |
| a property map generator was supplied when the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> |
| object was constructed, then that function is used to create a new |
| property map. If the generator fails to generate a property map |
| (returns a null <tt class="docutils literal"><span class="pre">shared_ptr</span></tt>), then the <tt class="docutils literal"><span class="pre">put</span></tt> function returns |
| <tt class="docutils literal"><span class="pre">false</span></tt>. If, on the other hand, the <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> object |
| has no property map generator (meaning it was default-constructed), |
| then <tt class="docutils literal"><span class="pre">property_not_found</span></tt> is thrown. If a candidate property map is |
| found but it does not support <tt class="docutils literal"><span class="pre">put</span></tt>, <tt class="docutils literal"><span class="pre">dynamic_const_put_error</span></tt> is |
| thrown.</p> |
| <pre class="literal-block"> |
| template<typename Value, typename Key> |
| Value get(const std::string& name, const dynamic_properties& dp, |
| const Key& key) |
| </pre> |
| <p>This function gets the value from the property-map whose namee is |
| given and whose key type matches. If <tt class="docutils literal"><span class="pre">Value</span></tt> is <tt class="docutils literal"><span class="pre">std::string</span></tt>, then the |
| property map's value type must either be <tt class="docutils literal"><span class="pre">std::string</span></tt> or model |
| OutputStreamable. In the latter case, the <tt class="docutils literal"><span class="pre">get</span></tt> function converts the |
| value to a string. If no matching property map is found, |
| <tt class="docutils literal"><span class="pre">dynamic_get_failure</span></tt> is thrown.</p> |
| <hr class="docutils" /> |
| <pre class="literal-block"> |
| class dynamic_property_map |
| </pre> |
| <p>This class describes the interface used by <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> to |
| interact with a user's property maps polymorphically.</p> |
| <pre class="literal-block"> |
| boost::any get(const any& key) |
| </pre> |
| <p>Given a representation of a key, return the value associated with that key.</p> |
| <p>Requirement: |
| 1) The object passed as the key must be convertible to a value of the |
| map's key type. Details of that conversion are unspecified. |
| 2) For this expression to be valid, the key must be |
| associated with some value, otherwise the result is undefined.</p> |
| <pre class="literal-block"> |
| std::string get_string(const any& key) |
| </pre> |
| <p>Given a representation of a key, return the string representation |
| of the value associated with that key.</p> |
| <p>Requirements: |
| 1) The object passed as the key must be convertible to the |
| property map's key type. Details of that conversion are unspecified. |
| 2) For this expression to be valid, the key must be |
| associated with some value, otherwise the result is undefined. |
| 3) The value type of the property map must model Output Streamable.</p> |
| <pre class="literal-block"> |
| void put(const any& key, const any& value) |
| </pre> |
| <p>Given a representation of a key and a representation of a value, the |
| key and value are associated in the property map.</p> |
| <p>Requirements: |
| 1) The object passed as the key must be convertible to the |
| property map's key type. Details of that conversion are unspecified. |
| 2) The object passed as the value must be convertible to the |
| property map's value type. Details of that conversion are unspecified. |
| 3) The property map need not support this member function, in which |
| case an error will be signaled. This is the runtime analogue of the |
| Readable Property Map concept.</p> |
| <pre class="literal-block"> |
| const std::type_info& key() const |
| </pre> |
| <p>Returns a <tt class="docutils literal"><span class="pre">type_info</span></tt> object that represents the property map's key type.</p> |
| <pre class="literal-block"> |
| const std::type_info& value() const |
| </pre> |
| <p>Returns a <tt class="docutils literal"><span class="pre">type_info</span></tt> object that represents the property map's value type.</p> |
| </div> |
| <div class="section" id="exceptions"> |
| <h2><a class="toc-backref" href="#id8">Exceptions</a></h2> |
| <pre class="literal-block"> |
| struct dynamic_property_exception : public std::exception { |
| virtual ~dynamic_property_exception() throw() {} |
| }; |
| |
| struct property_not_found : public std::exception { |
| std::string property; |
| property_not_found(const std::string& property); |
| virtual ~property_not_found() throw(); |
| |
| const char* what() const throw(); |
| }; |
| |
| struct dynamic_get_failure : public std::exception { |
| std::string property; |
| dynamic_get_failure(const std::string& property); |
| virtual ~dynamic_get_failure() throw(); |
| |
| const char* what() const throw(); |
| }; |
| |
| struct dynamic_const_put_error : public std::exception { |
| virtual ~dynamic_const_put_error() throw(); |
| |
| const char* what() const throw(); |
| }; |
| </pre> |
| <p>Under certain circumstances, calls to <tt class="docutils literal"><span class="pre">dynamic_properties</span></tt> member |
| functions will throw one of the above exceptions. The three concrete |
| exceptions can all be caught using the general |
| <tt class="docutils literal"><span class="pre">dynamic_property_exception</span></tt> moniker when greater precision is not |
| needed. In addition, all of the above exceptions derive from the |
| standard <tt class="docutils literal"><span class="pre">std::exception</span></tt> for even more generalized error handling. |
| The specific circumstances that result in these exceptions are |
| described above.</p> |
| </div> |
| </div> |
| </div> |
| <div class="footer"> |
| <hr class="footer" /> |
| Generated on: 2010-03-29 18:04 UTC. |
| Generated by <a class="reference external" href="http://docutils.sourceforge.net/">Docutils</a> from <a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructuredText</a> source. |
| |
| </div> |
| </body> |
| </html> |