123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389 |
- <?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>
|