1 /* 2 * Copyright 2008-2013 NVIDIA Corporation 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 18 /*! \file inner_product.h 19 * \brief Mathematical inner product between ranges 20 */ 21 22 #pragma once 23 24 #include <thrust/detail/config.h> 25 #include <thrust/detail/execution_policy.h> 26 27 namespace thrust 28 { 29 30 31 /*! \addtogroup reductions 32 * \{ 33 * \addtogroup transformed_reductions Transformed Reductions 34 * \ingroup reductions 35 * \{ 36 */ 37 38 39 /*! \p inner_product calculates an inner product of the ranges 40 * <tt>[first1, last1)</tt> and <tt>[first2, first2 + (last1 - first1))</tt>. 41 * 42 * Specifically, this version of \p inner_product computes the sum 43 * <tt>init + (*first1 * *first2) + (*(first1+1) * *(first2+1)) + ... </tt> 44 * 45 * The algorithm's execution is parallelized as determined by \p exec. 46 * 47 * \param exec The execution policy to use for parallelization. 48 * \param first1 The beginning of the first sequence. 49 * \param last1 The end of the first sequence. 50 * \param first2 The beginning of the second sequence. 51 * \param init Initial value of the result. 52 * \return The inner product of sequences <tt>[first1, last1)</tt> 53 * and <tt>[first2, last2)</tt> plus \p init. 54 * 55 * \tparam DerivedPolicy The name of the derived execution policy. 56 * \tparam InputIterator1 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>, 57 * \tparam InputIterator2 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>, 58 * \tparam OutputType is a model of <a href="http://www.sgi.com/tech/stl/Assignable.html">Assignable</a>, 59 * and if \c x is an object of type \p OutputType, and \c y is an object of \p InputIterator1's \c value_type, 60 * and \c z is an object of \p InputIterator2's \c value_type, then <tt>x + y * z</tt> is defined 61 * and is convertible to \p OutputType. 62 * 63 * The following code demonstrates how to use \p inner_product to 64 * compute the dot product of two vectors using the \p thrust::host execution policy for parallelization. 65 * 66 * \code 67 * #include <thrust/inner_product.h> 68 * #include <thrust/execution_policy.h> 69 * ... 70 * float vec1[3] = {1.0f, 2.0f, 5.0f}; 71 * float vec2[3] = {4.0f, 1.0f, 5.0f}; 72 * 73 * float result = thrust::inner_product(thrust::host, vec1, vec1 + 3, vec2, 0.0f); 74 * 75 * // result == 31.0f 76 * \endcode 77 * 78 * \see http://www.sgi.com/tech/stl/inner_product.html 79 */ 80 template<typename DerivedPolicy, 81 typename InputIterator1, 82 typename InputIterator2, 83 typename OutputType> 84 __host__ __device__ 85 OutputType inner_product(const thrust::detail::execution_policy_base<DerivedPolicy> &exec, 86 InputIterator1 first1, 87 InputIterator1 last1, 88 InputIterator2 first2, 89 OutputType init); 90 91 92 /*! \p inner_product calculates an inner product of the ranges 93 * <tt>[first1, last1)</tt> and <tt>[first2, first2 + (last1 - first1))</tt>. 94 * 95 * Specifically, this version of \p inner_product computes the sum 96 * <tt>init + (*first1 * *first2) + (*(first1+1) * *(first2+1)) + ... </tt> 97 * 98 * Unlike the C++ Standard Template Library function <tt>std::inner_product</tt>, 99 * this version offers no guarantee on order of execution. 100 * 101 * \param first1 The beginning of the first sequence. 102 * \param last1 The end of the first sequence. 103 * \param first2 The beginning of the second sequence. 104 * \param init Initial value of the result. 105 * \return The inner product of sequences <tt>[first1, last1)</tt> 106 * and <tt>[first2, last2)</tt> plus \p init. 107 * 108 * \tparam InputIterator1 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>, 109 * \tparam InputIterator2 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>, 110 * \tparam OutputType is a model of <a href="http://www.sgi.com/tech/stl/Assignable.html">Assignable</a>, 111 * and if \c x is an object of type \p OutputType, and \c y is an object of \p InputIterator1's \c value_type, 112 * and \c z is an object of \p InputIterator2's \c value_type, then <tt>x + y * z</tt> is defined 113 * and is convertible to \p OutputType. 114 * 115 * The following code demonstrates how to use \p inner_product to 116 * compute the dot product of two vectors. 117 * 118 * \code 119 * #include <thrust/inner_product.h> 120 * ... 121 * float vec1[3] = {1.0f, 2.0f, 5.0f}; 122 * float vec2[3] = {4.0f, 1.0f, 5.0f}; 123 * 124 * float result = thrust::inner_product(vec1, vec1 + 3, vec2, 0.0f); 125 * 126 * // result == 31.0f 127 * \endcode 128 * 129 * \see http://www.sgi.com/tech/stl/inner_product.html 130 */ 131 template<typename InputIterator1, typename InputIterator2, typename OutputType> 132 OutputType inner_product(InputIterator1 first1, InputIterator1 last1, 133 InputIterator2 first2, OutputType init); 134 135 136 /*! \p inner_product calculates an inner product of the ranges 137 * <tt>[first1, last1)</tt> and <tt>[first2, first2 + (last1 - first1))</tt>. 138 * 139 * This version of \p inner_product is identical to the first, except that is uses 140 * two user-supplied function objects instead of \c operator+ and \c operator*. 141 * 142 * Specifically, this version of \p inner_product computes the sum 143 * <tt>binary_op1( init, binary_op2(*first1, *first2) ), ... </tt> 144 * 145 * The algorithm's execution is parallelized as determined by \p exec. 146 * 147 * \param exec The execution policy to use for parallelization. 148 * \param first1 The beginning of the first sequence. 149 * \param last1 The end of the first sequence. 150 * \param first2 The beginning of the second sequence. 151 * \param init Initial value of the result. 152 * \param binary_op1 Generalized addition operation. 153 * \param binary_op2 Generalized multiplication operation. 154 * \return The inner product of sequences <tt>[first1, last1)</tt> and <tt>[first2, last2)</tt>. 155 * 156 * \tparam DerivedPolicy The name of the derived execution policy. 157 * \tparam InputIterator1 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>, 158 * and \p InputIterator1's \c value_type is convertible to \p BinaryFunction2's \c first_argument_type. 159 * \tparam InputIterator2 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>. 160 * and \p InputIterator2's \c value_type is convertible to \p BinaryFunction2's \c second_argument_type. 161 * \tparam OutputType is a model of <a href="http://www.sgi.com/tech/stl/Assignable.html">Assignable</a>, 162 * and \p OutputType is convertible to \p BinaryFunction1's \c first_argument_type. 163 * \tparam BinaryFunction1 is a model of <a href="http://www.sgi.com/tech/stl/BinaryFunction.html">Binary Function</a>, 164 * and \p BinaryFunction1's \c return_type is convertible to \p OutputType. 165 * \tparam BinaryFunction2 is a model of <a href="http://www.sgi.com/tech/stl/BinaryFunction.html">Binary Function</a>, 166 * and \p BinaryFunction2's \c return_type is convertible to \p BinaryFunction1's \c second_argument_type. 167 * 168 * \code 169 * #include <thrust/inner_product.h> 170 * #include <thrust/execution_policy.h> 171 * ... 172 * float vec1[3] = {1.0f, 2.0f, 5.0f}; 173 * float vec2[3] = {4.0f, 1.0f, 5.0f}; 174 * 175 * float init = 0.0f; 176 * thrust::plus<float> binary_op1; 177 * thrust::multiplies<float> binary_op2; 178 * 179 * float result = thrust::inner_product(thrust::host, vec1, vec1 + 3, vec2, init, binary_op1, binary_op2); 180 * 181 * // result == 31.0f 182 * \endcode 183 * 184 * \see http://www.sgi.com/tech/stl/inner_product.html 185 */ 186 template<typename DerivedPolicy, 187 typename InputIterator1, 188 typename InputIterator2, 189 typename OutputType, 190 typename BinaryFunction1, 191 typename BinaryFunction2> 192 __host__ __device__ 193 OutputType inner_product(const thrust::detail::execution_policy_base<DerivedPolicy> &exec, 194 InputIterator1 first1, 195 InputIterator1 last1, 196 InputIterator2 first2, 197 OutputType init, 198 BinaryFunction1 binary_op1, 199 BinaryFunction2 binary_op2); 200 201 202 /*! \p inner_product calculates an inner product of the ranges 203 * <tt>[first1, last1)</tt> and <tt>[first2, first2 + (last1 - first1))</tt>. 204 * 205 * This version of \p inner_product is identical to the first, except that is uses 206 * two user-supplied function objects instead of \c operator+ and \c operator*. 207 * 208 * Specifically, this version of \p inner_product computes the sum 209 * <tt>binary_op1( init, binary_op2(*first1, *first2) ), ... </tt> 210 * 211 * Unlike the C++ Standard Template Library function <tt>std::inner_product</tt>, 212 * this version offers no guarantee on order of execution. 213 * 214 * \param first1 The beginning of the first sequence. 215 * \param last1 The end of the first sequence. 216 * \param first2 The beginning of the second sequence. 217 * \param init Initial value of the result. 218 * \param binary_op1 Generalized addition operation. 219 * \param binary_op2 Generalized multiplication operation. 220 * \return The inner product of sequences <tt>[first1, last1)</tt> and <tt>[first2, last2)</tt>. 221 * 222 * \tparam InputIterator1 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>, 223 * and \p InputIterator1's \c value_type is convertible to \p BinaryFunction2's \c first_argument_type. 224 * \tparam InputIterator2 is a model of <a href="http://www.sgi.com/tech/stl/InputIterator.html">Input Iterator</a>. 225 * and \p InputIterator2's \c value_type is convertible to \p BinaryFunction2's \c second_argument_type. 226 * \tparam OutputType is a model of <a href="http://www.sgi.com/tech/stl/Assignable.html">Assignable</a>, 227 * and \p OutputType is convertible to \p BinaryFunction1's \c first_argument_type. 228 * \tparam BinaryFunction1 is a model of <a href="http://www.sgi.com/tech/stl/BinaryFunction.html">Binary Function</a>, 229 * and \p BinaryFunction1's \c return_type is convertible to \p OutputType. 230 * \tparam BinaryFunction2 is a model of <a href="http://www.sgi.com/tech/stl/BinaryFunction.html">Binary Function</a>, 231 * and \p BinaryFunction2's \c return_type is convertible to \p BinaryFunction1's \c second_argument_type. 232 * 233 * \code 234 * #include <thrust/inner_product.h> 235 * ... 236 * float vec1[3] = {1.0f, 2.0f, 5.0f}; 237 * float vec2[3] = {4.0f, 1.0f, 5.0f}; 238 * 239 * float init = 0.0f; 240 * thrust::plus<float> binary_op1; 241 * thrust::multiplies<float> binary_op2; 242 * 243 * float result = thrust::inner_product(vec1, vec1 + 3, vec2, init, binary_op1, binary_op2); 244 * 245 * // result == 31.0f 246 * \endcode 247 * 248 * \see http://www.sgi.com/tech/stl/inner_product.html 249 */ 250 template<typename InputIterator1, typename InputIterator2, typename OutputType, 251 typename BinaryFunction1, typename BinaryFunction2> 252 OutputType inner_product(InputIterator1 first1, InputIterator1 last1, 253 InputIterator2 first2, OutputType init, 254 BinaryFunction1 binary_op1, BinaryFunction2 binary_op2); 255 256 257 /*! \} // end transformed_reductions 258 * \} // end reductions 259 */ 260 261 } // end namespace thrust 262 263 #include <thrust/detail/inner_product.inl> 264 265