<!--
    Licensed to the Apache Software  Foundation (ASF) under one or more
    contributor  license agreements.  See  the NOTICE  file distributed
    with  this  work  for  additional information  regarding  copyright
    ownership.   The ASF  licenses this  file to  you under  the Apache
    License, Version  2.0 (the  License); you may  not use  this file
    except in  compliance with the License.   You may obtain  a copy of
    the License at

    http://www.apache.org/licenses/LICENSE-2.0

    Unless required by applicable law or agreed to in writing, software
    distributed under the  License is distributed on an  "AS IS" BASIS,
    WITHOUT  WARRANTIES OR CONDITIONS  OF ANY  KIND, either  express or
    implied.   See  the License  for  the  specific language  governing
    permissions and limitations under the License.

    Copyright 1999-2007 Rogue Wave Software, Inc.
-->

<HTML>
<HEAD>
<TITLE>indirect_array</TITLE>
<LINK REL=StyleSheet HREF="../rw.css" TYPE="text/css" TITLE="Apache stdcxx Stylesheet"></HEAD>
<BODY BGCOLOR=#FFFFFF>
<A HREF="includes.html"><IMG SRC="images/bprev.gif" WIDTH=20 HEIGHT=21 ALT="Previous file" BORDER=O></A><A HREF="noframes.html"><IMG SRC="images/btop.gif" WIDTH=56 HEIGHT=21 ALT="Top of Document" BORDER=O></A><A HREF="booktoc.html"><IMG SRC="images/btoc.gif" WIDTH=56 HEIGHT=21 ALT="Contents" BORDER=O></A><A HREF="tindex.html"><IMG SRC="images/bindex.gif" WIDTH=56 HEIGHT=21 ALT="Index page" BORDER=O></A><A HREF="inner-product.html"><IMG SRC="images/bnext.gif" WIDTH=25 HEIGHT=21 ALT="Next file" BORDER=O></A><DIV CLASS="DOCUMENTNAME"><B>Apache C++ Standard Library Reference Guide</B></DIV>
<H2>indirect_array</H2>
<P><B>Library:</B>&nbsp;&nbsp;<A HREF="2-10.html">Numerics</A></P>

<PRE><HR><B><I>Does not inherit</I></B><HR></PRE>

<UL>
<LI><A HREF="#sec1">Local Index</A></LI>
<LI><A HREF="#sec2">Summary</A></LI>
<LI><A HREF="#sec3">Synopsis</A></LI>
<LI><A HREF="#sec4">Description</A></LI>
<LI><A HREF="#sec5">Interface</A></LI>
<LI><A HREF="#sec6">Constructors</A></LI>
<LI><A HREF="#sec7">Assignment Operators</A></LI>
<LI><A HREF="#sec8">Computed Assignment Operators</A></LI>
<LI><A HREF="#sec9">Example</A></LI>
<LI><A HREF="#sec10">See Also</A></LI>
<LI><A HREF="#sec11">Standards Conformance</A></LI>
</UL>
<A NAME="sec1"><H3>Local Index</H3></A>
<H4>Members</H4>
<UL><TABLE CELLPADDING=3>
<TR><TD VALIGN=top>
<A HREF="#idx658">indirect_array()</A><BR>
<A HREF="#idx662">operator%=()</A><BR>
<A HREF="#idx662">operator&amp;=()</A><BR>
</TD>
<TD VALIGN=top><A HREF="#idx662">operator&gt;&gt;=()</A><BR>
<A HREF="#idx662">operator&lt;&lt;=()</A><BR>
<A HREF="#idx662">operator*=()</A><BR>
</TD>
<TD VALIGN=top><A HREF="#idx662">operator+=()</A><BR>
<A HREF="#idx662">operator-=()</A><BR>
<A HREF="#idx662">operator/=()</A><BR>
</TD>
<TD VALIGN=top><A HREF="#idx659">operator=()</A><BR>
<A HREF="#idx662">operator^=()</A><BR>
<A HREF="#idx662">operator|=()</A><BR>
</TD></TR>
</TABLE></UL>

<A NAME="sec2"><H3>Summary</H3></A>
<P>A numeric array class used to represent elements selected from a <B><I><A HREF="valarray.html">valarray</A></I></B></P>
<A NAME="sec3"><H3>Synopsis</H3></A>

<PRE>#include &lt;valarray&gt;

namespace std {
  template &lt;class T&gt;
  class indirect_array;
}
</PRE>
<A NAME="sec4"><H3>Description</H3></A>
<P><B><I>indirect_array</I></B> creates a selective view into a <B><I><A HREF="valarray.html">valarray</A></I></B>. An <B><I>indirect_array</I></B> is produced by applying the indirect subscript operator to a <B><I>valarray</I></B>. The indirect array produced by this subscript contains only the elements of the <B><I>valarray</I></B> whose indices appear as values in the argument. The elements in an <B><I>indirect_array</I></B> are references to selected elements in the <B><I>valarray</I></B>. For this reason, changing an element in the <B><I>indirect_array</I></B> really changes the corresponding element in the <B><I>valarray</I></B>. An <B><I>indirect_array</I></B> does not itself hold any distinct elements. The template cannot be instantiated directly since all its constructors are private. However, you can copy an <B><I>indirect_array</I></B> to a <B><I>valarray</I></B> using either the <B><I>valarray</I></B> copy constructor or the assignment operator. Reference semantics are lost at that point. </P>
<A NAME="sec5"><H3>Interface</H3></A>

<UL><PRE>namespace std{ 

  template &lt;class T&gt; class indirect_array {
  public:

    // types
    typedef T value_type;

    // destructor
    ~indirect_array();

    // public assignment
    void operator=(const valarray&lt;T&gt;&amp; array) const;
  
    // computed assignment
    void operator*=(const valarray&lt;T&gt;&amp; array) const;
    void operator/=(const valarray&lt;T&gt;&amp; array) const;
    void operator%=(const valarray&lt;T&gt;&amp; array) const;
    void operator+=(const valarray&lt;T&gt;&amp; array) const;
    void operator-=(const valarray&lt;T&gt;&amp; array) const;
    void operator^=(const valarray&lt;T&gt;&amp; array) const;
    void operator&amp;=(const valarray&lt;T&gt;&amp; array) const;
    void operator|=(const valarray&lt;T&gt;&amp; array) const;
    void operator&lt;&lt;=(const valarray&lt;T&gt;&amp; array) const;
    void operator&gt;&gt;=(const valarray&lt;T&gt;&amp; array) const;
 
    // fill function
    void operator=(const T&amp;);  

  private:
    // constructors
    indirect_array();
    indirect_array(const indirect_array&lt;T&gt;&amp;);
  
    // operator = 
    indirect_array&lt;T&gt;&amp; 
       operator=(const indirect_array&lt;T&gt;&amp; array);
  };
}
</PRE></UL>
<A NAME="sec6"><H3>Constructors</H3></A>

<A NAME="idx658"></A><PRE><B>indirect_array</B>();
<B>indirect_array</B>(const indirect_array&amp;);</PRE>
<UL>
<P>All <B><I>indirect_array</I></B> constructors are private and cannot be called directly. This prevents copy construction of <B><I>indirect_arrays</I></B>.</P>
</UL>

<A NAME="sec7"><H3>Assignment Operators</H3></A>

<A NAME="idx659"></A><PRE>void <B>operator=</B>(const valarray&lt;T&gt;&amp; x) const;</PRE>
<UL>
<P>Assigns values from <SAMP>x </SAMP>to the selected elements of the <B><I><A HREF="valarray.html">valarray</A></I></B> that self refers to. Remember that an <B><I>indirect_array</I></B> never holds any elements itself; it simply refers to selected elements in the <B><I>valarray</I></B> used to generate it.</P>
</UL>


<A NAME="idx660"></A><PRE>indirect_array&lt;T&gt;&amp; 
<B>operator=</B>(const indirect-_array&lt;T&gt;&amp; x);</PRE>
<UL>
<P>Private assignment operator. Cannot be called directly, thus preventing assignment between <B><I>indirect_arrays</I></B>.</P>
</UL>


<A NAME="idx661"></A><PRE>void <B>operator=</B>(const T&amp; x);</PRE>
<UL>
<P>Assigns <SAMP>x</SAMP> to the selected elements of the <B><I><A HREF="valarray.html">valarray</A></I></B> that self refers to. </P>
</UL>

<A NAME="sec8"><H3>Computed Assignment Operators</H3></A>

<A NAME="idx662"></A><PRE>void <B>operator*=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator/=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator%=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator+=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator-=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator^=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator&amp;=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator|=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator&lt;&lt;=</B>(const valarray&lt;T&gt;&amp; val) const;
void <B>operator&gt;&gt;=</B>(const valarray&lt;T&gt;&amp; val) const;</PRE>
<UL>
<P>Applies the indicated operation using elements from <SAMP>val</SAMP> to the selected elements of the <B><I><A HREF="valarray.html">valarray</A></I></B> that self refers to. Remember that an <B><I>indirect_array</I></B> never holds any elements itself; it simply refers to selected elements in the <B><I>valarray</I></B> used to generate it.</P>
</UL>

<A NAME="sec9"><H3>Example</H3></A>

<UL><PRE>//
//  indirect_array.cpp
//

#include &lt;valarray.h&gt;  // Includes valarray and 
                       // provides stream inserter.

typedef std::valarray&lt;int&gt;    valarray_t;
typedef std::valarray&lt;size_t&gt; selector_t;

int main(void) {

  // Create a valarray of integers.
  valarray_t::value_type vbuf[10] = {0,1,2,3,4,5,6,7,8,9};
  valarray_t vi(vbuf, (sizeof vbuf / sizeof *vbuf));

  // Create a valarray of indices for a selector.
  selector_t::value_type sbuf[6] = {0,2,3,4,7,8};
  selector_t selector(sbuf, (sizeof sbuf / sizeof *sbuf));

  // Print out the valarray&lt;int&gt;.
  std::cout &lt;&lt; "original valarray vi\n\n" &lt;&lt; vi &lt;&lt; "\n\n";

  // Print out the selective array.
  std::cout &lt;&lt; "vi[0,2,3,4,7,8]\n\n" &lt;&lt;  vi[selector] &lt;&lt; "\n\n";
  
  // Double the selected values.
  vi[selector] += vi[selector];

  // Print out the modified valarray.
  std::cout &lt;&lt; "vi[0,2,3,4,7,8] += vi[0,2,3,4,7,8]\n\n" &lt;&lt; vi 
            &lt;&lt; std::endl;

  return 0;
}


Program Output:
</PRE></UL>
<UL><PRE>original valarray vi

[0,1,2,3,4,5,6,7,8,9]

vi[0,2,3,4,7,8]

[0,2,3,4,7,8]

vi[0,2,3,4,7,8] += vi[0,2,3,4,7,8]

[0,1,4,6,8,5,6,14,16,9]
</PRE></UL>
<A NAME="sec10"><H3>See Also</H3></A>
<P><B><I><A HREF="slice.html">slice</A></I></B>, <B><I><A HREF="slice-array.html">slice_array</A></I></B>, <B><I><A HREF="valarray.html">valarray</A></I></B>, <B><I><A HREF="gslice.html">gslice</A></I></B>, <B><I><A HREF="gslice-array.html">gslice_array</A></I></B>, <B><I><A HREF="mask-array.html">mask_array</A></I></B></P>
<A NAME="sec11"><H3>Standards Conformance</H3></A>
<P><I>ISO/IEC 14882:1998 -- International Standard for Information Systems -- Programming Language C++, Section 26.3.9</I></P>

<BR>
<HR>
<A HREF="includes.html"><IMG SRC="images/bprev.gif" WIDTH=20 HEIGHT=21 ALT="Previous file" BORDER=O></A><A HREF="noframes.html"><IMG SRC="images/btop.gif" WIDTH=56 HEIGHT=21 ALT="Top of Document" BORDER=O></A><A HREF="booktoc.html"><IMG SRC="images/btoc.gif" WIDTH=56 HEIGHT=21 ALT="Contents" BORDER=O></A><A HREF="tindex.html"><IMG SRC="images/bindex.gif" WIDTH=56 HEIGHT=21 ALT="Index page" BORDER=O></A><A HREF="inner-product.html"><IMG SRC="images/bnext.gif" WIDTH=20 HEIGHT=21 ALT="Next file" BORDER=O></A>

<!-- Google Analytics tracking code -->
<script src="http://www.google-analytics.com/urchin.js" type="text/javascript">
</script>
<script type="text/javascript">
    _uacct = "UA-1775151-1";
    urchinTracker();
</script>
<!-- end of Google Analytics tracking code -->

</BODY>
</HTML>
