blob: 95858ca8b09cdbaffff564d8c18a50c5f1f138d8 [file] [log] [blame]
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright 2012 Eric Niebler
Distributed under 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)
-->
<header name="boost/proto/transform/env.hpp">
<namespace name="boost">
<namespace name="proto">
<struct name="key_not_found">
<purpose>
The type of objects returned when a key-based lookup fails in a
transform environment.
</purpose>
</struct>
<!-- empty_env -->
<struct name="empty_env">
<purpose>
The type of an object that represents a transform environment
with no key/value pairs in it.
</purpose>
<method-group name="public member functions">
<method name="operator[]" cv="const">
<type><classname>proto::key_not_found</classname></type>
<parameter name="">
<paramtype><replaceable>unspecified</replaceable></paramtype>
</parameter>
<description>
<para>The type of the argument to this function has a
user-defined implicit conversion from any type.</para>
</description>
</method>
</method-group>
</struct>
<!-- env -->
<struct name="env">
<template>
<template-type-parameter name="Key"/>
<template-type-parameter name="Value"/>
<template-type-parameter name="Env">
<default><classname>proto::empty_env</classname></default>
</template-type-parameter>
</template>
<constructor specifiers="explicit">
<parameter name="value">
<paramtype>Value const &amp;</paramtype>
<description>
<para>
The value to be associated with the <code>Key</code>.
</para>
</description>
</parameter>
<parameter name="other">
<paramtype>Env const &amp;</paramtype>
<default>Env()</default>
<description>
<para>
Another key/value store.
</para>
</description>
</parameter>
</constructor>
<method-group name="public member functions">
<method name="operator[]" cv="const">
<type><replaceable>see-below</replaceable></type>
<parameter name="">
<paramtype><replaceable>see-below</replaceable></paramtype>
</parameter>
<description>
<para>
If called with an object that is implicitly convertible to type <code>Key</code>,
this function returns the <code>Value</code> passed to the constructor. Otherwise, it returns
the result of calling <code>operator[]</code> on the <code>Env</code> passed to
the constructor.
</para>
</description>
</method>
</method-group>
</struct>
<!-- is_env -->
<struct name="is_env">
<template>
<template-type-parameter name="T"/>
</template>
<inherit><type>mpl::bool_&lt;<replaceable>true-or-false</replaceable>&gt;</type></inherit>
<purpose>
<para>A Boolean metafuntion for determining whether or not a type is a Proto
transform environment.</para>
</purpose>
<description>
<para><code>is_env&lt;T&gt;</code> inherits from <code>mpl::true_</code> under the following
conditions:
<itemizedlist>
<listitem>If <code>T</code> is <classname>proto::empty_env</classname>.</listitem>
<listitem>If <code>T</code> is a specialization of <classname>proto::env&lt;&gt;</classname>.</listitem>
<listitem>If <code>T</code> is derived from any of the above.</listitem>
<listitem>If <code>T</code> is a cv-qualified variant of any of the above.</listitem>
<listitem>If <code>T</code> is a reference to any of the above.</listitem>
</itemizedlist>
</para>
<para>Otherwise, <code>is_env&lt;T&gt;</code> inherits from <code>mpl::false_</code>.
</para>
</description>
</struct>
<struct name="data_type">
<purpose>
The type of <code><globalname>proto::data</globalname></code>, a key for use when creating
a transform environment that associates a piece of data with this type.
</purpose>
<description>
<para>
The <code>proto::data_type</code> type, along with the <code><globalname>proto::data</globalname></code>
global, are declared using the <code><macroname>BOOST_PROTO_DEFINE_ENV_VAR</macroname>()</code> macro.
</para>
</description>
<method-group name="public member functions">
<overloaded-method name="operator=">
<signature cv="const">
<template>
<template-type-parameter name="Value"/>
</template>
<type><classname>env</classname>&lt;data_type, <replaceable>see-below</replaceable>&gt;</type>
<parameter name="value">
<paramtype>Value &amp;</paramtype>
</parameter>
</signature>
<signature cv="const">
<template>
<template-type-parameter name="Value"/>
</template>
<type><classname>env</classname>&lt;data_type, <replaceable>see-below</replaceable>&gt;</type>
<parameter name="value">
<paramtype>Value const &amp;</paramtype>
</parameter>
</signature>
<description>
<para>
If <code>Value</code> is a specialization <code>boost::reference_wrapper&lt;T&gt;</code>,
this function returns <code><classname>env</classname>&lt;data_type, T &amp;&gt;(value.get())</code>.
</para>
<para>
Else, if the type <code>Value</code> is non-copyable (i.e., a function, an array, abstract, or an ostream),
this function returns <code><classname>env</classname>&lt;data_type, Value <replaceable>cv</replaceable> &amp;&gt;(value)</code>,
where <code><replaceable>cv</replaceable></code> is <code>const</code> for the second overload, and empty
for the first.
</para>
<para>
Otherwise, this function returns <code><classname>env</classname>&lt;data_type, Value&gt;(value)</code>.
</para>
</description>
</overloaded-method>
</method-group>
</struct>
<data-member name="data">
<description>
<para>A key used for creating a transform environment.</para>
</description>
<type><classname>proto::data_type</classname> const</type>
</data-member>
<namespace name="functional">
<!-- functional::as_env -->
<struct name="as_env">
<inherit><classname>proto::callable</classname></inherit>
<purpose>
A unary <conceptname>PolymorphicFunctionObject</conceptname> for ensuring that an object
is a transform environment. If it isn't already, it is turned into one such that the
object is associated with the <classname>proto::data_type</classname> key.
</purpose>
<struct name="result">
<template>
<template-type-parameter name="Sig"/>
</template>
<typedef name="type">
<type><replaceable>see-below</replaceable></type>
<description>
<para>See <code><methodname>proto::functional::as_env::operator()</methodname></code>.</para>
</description>
</typedef>
<description>
<para>
Encodes the return type of <code><methodname>proto::functional::as_env::operator()</methodname></code>.
The presence of this member template makes <code><classname>proto::functional::as_env</classname></code>
a valid TR1-style function object type usable with <code>boost::result_of&lt;&gt;</code>.
</para>
</description>
</struct>
<method-group name="public member functions">
<overloaded-method name="operator()">
<signature cv="const">
<template>
<template-type-parameter name="T"/>
</template>
<type><replaceable>see-below</replaceable></type>
<parameter name="t">
<paramtype>T &amp;</paramtype>
</parameter>
</signature>
<signature cv="const">
<template>
<template-type-parameter name="T"/>
</template>
<type><replaceable>see-below</replaceable></type>
<parameter name="t">
<paramtype>T const &amp;</paramtype>
</parameter>
</signature>
<description>
<para>
If <code><classname>proto::is_env</classname>&lt;T&gt;::value</code> is <code>false</code>,
this function returns the result of <code>(<globalname>proto::data</globalname> = t)</code>.
See <code><methodname>proto::data_type::operator=</methodname></code> for details.
</para>
<para>
Otherwise, this function returns <code>t</code> by reference.
</para>
</description>
</overloaded-method>
</method-group>
</struct>
<!-- functional::has_env_var -->
<struct name="has_env_var">
<inherit><classname>proto::callable</classname></inherit>
<template>
<template-type-parameter name="Key"/>
</template>
<purpose>
A unary boolean <conceptname>PolymorphicFunctionObject</conceptname> used for determining whether a particular
transform environment has a value associated with a particular key.
</purpose>
<struct name="result">
<template>
<template-type-parameter name="Sig"/>
</template>
<typedef name="type">
<type><replaceable>see-below</replaceable></type>
<description>
<para>See <code><methodname>proto::functional::has_env_var::operator()</methodname></code>.</para>
</description>
</typedef>
<description>
<para>
Encodes the return type of <code><methodname>proto::functional::has_env_var::operator()</methodname></code>.
The presence of this member template makes <code><classname>proto::functional::has_env_var</classname></code>
a valid TR1-style function object type usable with <code>boost::result_of&lt;&gt;</code>.
</para>
</description>
</struct>
<method-group name="public member functions">
<method name="operator()" cv="const">
<template>
<template-type-parameter name="Env"/>
</template>
<type><replaceable>see-below</replaceable></type>
<parameter name="e">
<paramtype>Env const &amp;</paramtype>
</parameter>
<description>
<para>
This function behaves as follows:
<itemizedlist>
<listitem>
If <code><classname>proto::is_env</classname>&lt;Env&gt;::value</code> is <code>true</code>:
<itemizedlist>
<listitem>
If <code>e[Key()]</code> returns an instance of
<code><classname>proto::key_not_found</classname></code>, return
<code>mpl::false_</code>. See <code><methodname>proto::env::operator[]</methodname></code>
for more information.
</listitem>
<listitem>
Otherwise, return <code>mpl::true_</code>.
</listitem>
</itemizedlist>
</listitem>
<listitem>
Otherwise:
<itemizedlist>
<listitem>
If <code>Key</code> is <code><classname>proto::data_type</classname></code>,
return <code>mpl::true_</code>.
</listitem>
<listitem>
Otherwise, return <code>mpl::false_</code>.
</listitem>
</itemizedlist>
</listitem>
</itemizedlist>
</para>
</description>
</method>
</method-group>
</struct>
<!-- functional::env_var -->
<struct name="env_var">
<inherit><classname>proto::callable</classname></inherit>
<template>
<template-type-parameter name="Key"/>
</template>
<purpose>
A unary <conceptname>PolymorphicFunctionObject</conceptname> used for fetching the value
associated with a particular key in a transform environment.
</purpose>
<struct name="result">
<template>
<template-type-parameter name="Sig"/>
</template>
<typedef name="type">
<type><replaceable>see-below</replaceable></type>
<description>
<para>See <code><methodname>proto::functional::env_var::operator()</methodname></code>.</para>
</description>
</typedef>
<description>
<para>
Encodes the return type of <code><methodname>proto::functional::env_var::operator()</methodname></code>.
The presence of this member template makes <code><classname>proto::functional::env_var</classname></code>
a valid TR1-style function object type usable with <code>boost::result_of&lt;&gt;</code>.
</para>
</description>
</struct>
<method-group name="public member functions">
<method name="operator()" cv="const">
<template>
<template-type-parameter name="Env"/>
</template>
<type><replaceable>see-below</replaceable></type>
<parameter name="e">
<paramtype>Env const &amp;</paramtype>
</parameter>
<description>
<para>
This function behaves as follows:
<itemizedlist>
<listitem>
If <code>Key</code> is <code><classname>proto::data_type</classname></code>:
<itemizedlist>
<listitem>
If <code><classname>proto::is_env</classname>&lt;Env&gt;::value</code> is <code>true</code>,
return <code>e[<globalname>proto::data</globalname>]</code>.
</listitem>
<listitem>
Otherwise, return <code>e</code>.
</listitem>
</itemizedlist>
</listitem>
<listitem>
Otherwise, return <code>e[Key()]</code>.
</listitem>
</itemizedlist>
</para>
<para>
See <code><methodname>proto::env::operator[]</methodname></code> for additional information.
</para>
</description>
</method>
</method-group>
</struct>
</namespace>
<namespace name="result_of">
<struct name="as_env">
<template>
<template-type-parameter name="T"/>
</template>
<inherit><type>boost::result_of&lt;<classname>proto::functional::as_env</classname>(T)&gt;</type></inherit>
<purpose>
Metafunction for computing the return type of <code><functionname>proto::as_env()</functionname></code>.
</purpose>
</struct>
<struct name="has_env_var">
<template>
<template-type-parameter name="Env"/>
<template-type-parameter name="Key"/>
</template>
<inherit><type>boost::result_of&lt;<classname>proto::functional::has_env_var</classname>&lt;Key&gt;(Env)&gt;::type</type></inherit>
<purpose>
Metafunction for computing the return type of <code><functionname>proto::has_env_var()</functionname></code>.
</purpose>
</struct>
<struct name="env_var">
<template>
<template-type-parameter name="Env"/>
<template-type-parameter name="Key"/>
</template>
<inherit><type>boost::result_of&lt;<classname>proto::functional::env_var</classname>&lt;Key&gt;(Env)&gt;</type></inherit>
<purpose>
Metafunction for computing the return type of <code><functionname>proto::env_var()</functionname></code>.
</purpose>
</struct>
</namespace>
<!-- proto::as_env -->
<overloaded-function name="as_env">
<signature>
<template>
<template-type-parameter name="T"/>
</template>
<type>typename <classname>proto::result_of::as_env</classname>&lt;T &amp;&gt;::type</type>
<parameter name="t">
<paramtype>T &amp;</paramtype>
</parameter>
</signature>
<signature>
<template>
<template-type-parameter name="T"/>
</template>
<type>typename <classname>proto::result_of::as_env</classname>&lt;T const &amp;&gt;::type</type>
<parameter name="t">
<paramtype>T const &amp;</paramtype>
</parameter>
</signature>
<purpose>
For ensuring that the given argument is a transform environment. If it is not already,
it is made one as if by <code>(<globalname>proto::data</globalname> = t)</code>.
</purpose>
<description>
<para>
See also:
<itemizedlist>
<listitem>
<code><methodname>proto::data_type::operator=</methodname></code>
</listitem>
<listitem>
<code><methodname>proto::functional::as_env::operator()</methodname></code>
</listitem>
</itemizedlist>
</para>
</description>
<returns><code><classname>proto::functional::as_env</classname>()(t)</code></returns>
</overloaded-function>
<!-- proto::has_env_var -->
<overloaded-function name="has_env_var">
<signature>
<template>
<template-type-parameter name="Key"/>
<template-type-parameter name="Env"/>
</template>
<type>typename <classname>proto::result_of::has_env_var</classname>&lt;Env &amp;, Key&gt;::type</type>
<parameter name="e">
<paramtype>Env &amp;</paramtype>
</parameter>
</signature>
<signature>
<template>
<template-type-parameter name="Key"/>
<template-type-parameter name="Env"/>
</template>
<type>typename <classname>proto::result_of::has_env_var</classname>&lt;Env const &amp;, Key&gt;::type</type>
<parameter name="e">
<paramtype>Env const &amp;</paramtype>
</parameter>
</signature>
<purpose>
For testing to see whether a value exists in a transform environment corresponding to the
specified <code>Key</code>.
</purpose>
<description>
<para>
See also:
<itemizedlist>
<listitem>
<code><methodname>proto::functional::has_env_var::operator()</methodname></code>
</listitem>
</itemizedlist>
</para>
</description>
<returns><code><classname>proto::functional::has_env_var&lt;Key&gt;</classname>()(e)</code></returns>
</overloaded-function>
<!-- proto::env_var -->
<overloaded-function name="env_var">
<signature>
<template>
<template-type-parameter name="Key"/>
<template-type-parameter name="Env"/>
</template>
<type>typename <classname>proto::result_of::env_var</classname>&lt;Env &amp;, Key&gt;::type</type>
<parameter name="e">
<paramtype>Env &amp;</paramtype>
</parameter>
</signature>
<signature>
<template>
<template-type-parameter name="Key"/>
<template-type-parameter name="Env"/>
</template>
<type>typename <classname>proto::result_of::env_var</classname>&lt;Env const &amp;, Key&gt;::type</type>
<parameter name="e">
<paramtype>Env const &amp;</paramtype>
</parameter>
</signature>
<purpose>
For fetching the value from a transform environment corresponding to the
specified <code>Key</code>.
</purpose>
<description>
<para>
See also:
<itemizedlist>
<listitem>
<code><methodname>proto::functional::env_var::operator()</methodname></code>
</listitem>
</itemizedlist>
</para>
</description>
<returns><code><classname>proto::functional::env_var&lt;Key&gt;</classname>()(e)</code></returns>
</overloaded-function>
<!-- proto::operator, -->
<overloaded-function name="operator,">
<signature>
<template>
<template-type-parameter name="Env"/>
<template-type-parameter name="Key"/>
<template-type-parameter name="Value"/>
</template>
<type><classname>proto::env</classname>&lt;Key, Value, <replaceable>UNCVREF</replaceable>(typename <classname>proto::result_of::as_env</classname>&lt;Env &amp;&gt;::type)&gt;</type>
<parameter name="other">
<paramtype>Env &amp;</paramtype>
</parameter>
<parameter name="head">
<paramtype><classname>proto::env</classname>&lt;Key, Value&gt; const &amp;</paramtype>
</parameter>
</signature>
<signature>
<template>
<template-type-parameter name="Env"/>
<template-type-parameter name="Key"/>
<template-type-parameter name="Value"/>
</template>
<type><classname>proto::env</classname>&lt;Key, Value, <replaceable>UNCVREF</replaceable>(typename <classname>proto::result_of::as_env</classname>&lt;Env const &amp;&gt;::type)&gt;</type>
<parameter name="other">
<paramtype>Env const &amp;</paramtype>
</parameter>
<parameter name="head">
<paramtype><classname>proto::env</classname>&lt;Key, Value&gt; const &amp;</paramtype>
</parameter>
</signature>
<purpose>
For composing a larger transform environment from two smaller ones.
</purpose>
<description>
<para>
The effect of this function is to take two transform environments and compose them into
a larger environment that contains the key/values pairs of the two. The first argument
is allowed to not be a transform environment, in which case it is turned into one with
the <functionname>proto::as_env()</functionname> function before composition with the
second argument. The second argument is required to be a transform environment with exactly
one key/value pair.
</para>
<para>
<emphasis role="bold">Example:</emphasis>
</para>
<para>
Given user-defined keys <code>key0</code> and <code>key1</code> of types <code>key0_type</code>
and <code>key1_type</code>, the following code demonstrates how the chained use of <code>operator,</code>
can build a composite transform environment containing a number of key/value pairs:
<programlisting><classname>proto::env</classname>&lt;
key1_type
, int
, <classname>proto::env</classname>&lt;
key0_type
, char const (&amp;)[6]
, <classname>proto::env</classname>&lt;<classname>proto::data_type</classname>, int&gt;
&gt;
&gt; myenv = (<globalname>proto::data</globalname> = 1, key0 = "hello", key1 = 42);
// NOTE: operator, here --^ and here --^
// Check the results:
assert(1 == myenv[proto::data]);
assert(0 == std::strcmp(myenv[key0], "hello"));
assert(42 == myenv[key1]);</programlisting>
</para>
<para>
<emphasis role="bold">Note:</emphasis> In the return type and the "Returns" clause, <code><replaceable>UNCVREF</replaceable>(X)</code> is
the type <code>X</code> stripped of top-level reference and cv-qualifiers.
</para>
<para>
<emphasis role="bold">Note:</emphasis> In the "Returns" clause, <code><replaceable>cv</replaceable></code> is replaced with <code>const</code>
for the second overload, and nothing for the first.
</para>
<para>
<emphasis role="bold">See also:</emphasis>
<itemizedlist>
<listitem>
<code><methodname>proto::env::operator[]</methodname></code>
</listitem>
</itemizedlist>
</para>
</description>
<returns><code><classname>proto::env</classname>&lt;Key, Value, <replaceable>UNCVREF</replaceable>(typename <classname>proto::result_of::as_env</classname>&lt;Env <replaceable>cv</replaceable> &amp;&gt;::type)&gt;(head[Key()], <functionname>proto::as_env</functionname>(other))</code></returns>
</overloaded-function>
<!-- struct _env_var -->
<struct name="_env_var">
<template>
<template-type-parameter name="Key"/>
</template>
<purpose>
A primitive transform that returns the value associated with a particular <code>Key</code>
in the current transform environment.
</purpose>
<inherit>
<type><classname>proto::transform</classname>&lt;_env_var&lt;Key&gt; &gt;</type>
</inherit>
<struct name="impl">
<template>
<template-type-name name="Expr"/>
<template-type-name name="State"/>
<template-type-name name="Data"/>
</template>
<inherit>
<type><classname>proto::transform_impl</classname>&lt;Expr, State, Data&gt; &gt;</type>
</inherit>
<typedef name="result_type">
<type>typename <classname>proto::result_of::env_var</classname>&lt;Data, Key&gt;::type</type>
</typedef>
<method-group name="public member functions">
<method name="operator()" cv="const">
<type>result_type</type>
<parameter name="">
<paramtype>typename impl::expr_param</paramtype>
</parameter>
<parameter name="">
<paramtype>typename impl::state_param</paramtype>
</parameter>
<parameter name="data">
<paramtype>typename impl::data_param</paramtype>
<description>
<para>The current transform environment</para>
</description>
</parameter>
<description>
<para>
Fetches the value associated with <code>Key</code> from the transform environment
passed in the data (third) parameter.
</para>
</description>
<requires>
<para>
<code><classname>proto::is_env</classname>&lt;Data&gt;::value</code>
is <code>true</code>.
</para>
</requires>
<returns>
<para>
<code><functionname>proto::env_var</functionname>(data)</code>
</para>
</returns>
</method>
</method-group>
</struct>
<description>
<para>
See <code><classname>proto::_env_var::impl</classname></code> for the full details.
</para>
</description>
</struct>
<!-- struct _env -->
<struct name="_env">
<purpose>
A primitive transform that returns the current transform environment unmodified.
</purpose>
<inherit>
<type><classname>proto::transform</classname>&lt;_env&gt;</type>
</inherit>
<struct name="impl">
<template>
<template-type-name name="Expr"/>
<template-type-name name="State"/>
<template-type-name name="Data"/>
</template>
<inherit>
<type><classname>proto::transform_impl</classname>&lt;Expr, State, Data&gt;</type>
</inherit>
<typedef name="result_type">
<type>Data</type>
</typedef>
<method-group name="public member functions">
<method name="operator()" cv="const">
<type>result_type</type>
<parameter name="">
<paramtype>typename impl::expr_param</paramtype>
</parameter>
<parameter name="">
<paramtype>typename impl::state_param</paramtype>
</parameter>
<parameter name="data">
<paramtype>typename impl::data_param</paramtype>
<description>
<para>The current transform environment </para>
</description>
</parameter>
<description>
<para>
Returns the current transform environment
passed in the data (third) parameter.
</para>
</description>
<returns>
<para>
<code>data</code>
</para>
</returns>
</method>
</method-group>
</struct>
<description>
<para>
See <code><classname>proto::_env::impl</classname></code> for the full details.
</para>
</description>
</struct>
</namespace>
</namespace>
<!-- BOOST_PROTO_DEFINE_ENV_VAR() -->
<macro name="BOOST_PROTO_DEFINE_ENV_VAR" kind="functionlike">
<macro-parameter name="Type"/>
<macro-parameter name="Name"/>
<purpose>
Define a type and a global variable of that type that can be used
to initialize a slot in a Proto transform environment.
</purpose>
<description>
<para>
Proto primitive transforms can optionally accept an environment in
their third parameter which is a key/value store of environment
variables. Use the <code>BOOST_PROTO_DEFINE_ENV_VAR()</code> macro
to define the keys.
</para>
<para>
See the description for <code><classname alt="boost::proto::data_type">proto::data_type</classname></code>
for an example of the class interface created by this macro.
</para>
<para>
<emphasis role="bold">Example:</emphasis>
</para>
<para>
<programlisting>BOOST_PROTO_DEFINE_ENV_VAR(mykey_type, mykey);
struct FetchMyKey
: <classname alt="boost::proto::when">proto::when</classname>&lt; <classname alt="boost::proto::_">_</classname>, <classname alt="boost::proto::_env_var">proto::_env_var</classname>&lt;mykey_type&gt; &gt;
{};
int main()
{
<classname alt="boost::proto::terminal">proto::terminal</classname>&lt;int&gt;::type i = {42};
char const * sz = FetchMyKey()(i, 0, (mykey = "hello!"));
assert(0 == std::strcmp(sz, "hello!");
}</programlisting>
</para>
</description>
</macro>
</header>