Actions

icon Post
text/html Subscribe
text/html Unsubscribe

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[patch] vector-matrix multiply


  • To: VSIPL++ Developers List <vsipl++@xxxxxxxxxxxxxxxx>
  • Subject: [patch] vector-matrix multiply
  • From: Jules Bergmann <jules@xxxxxxxxxxxxxxxx>
  • Date: Fri, 23 Sep 2005 17:00:59 -0400

Rough implementation of vmmul. Tries to do the right thing with respect to dimension ordering of the matrix.

				-- Jules
Index: src/vsip/math.hpp
===================================================================
RCS file: /home/cvs/Repository/vpp/src/vsip/math.hpp,v
retrieving revision 1.11
diff -c -p -r1.11 math.hpp
*** src/vsip/math.hpp	19 Sep 2005 21:06:46 -0000	1.11
--- src/vsip/math.hpp	23 Sep 2005 20:58:09 -0000
***************
*** 30,35 ****
--- 30,36 ----
  #include <vsip/impl/reductions-idx.hpp>
  #include <vsip/impl/matvec.hpp>
  #include <vsip/impl/matvec-prod.hpp>
+ #include <vsip/impl/vmmul.hpp>
  
  
  
Index: src/vsip/impl/vmmul.hpp
===================================================================
RCS file: src/vsip/impl/vmmul.hpp
diff -N src/vsip/impl/vmmul.hpp
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- src/vsip/impl/vmmul.hpp	23 Sep 2005 20:58:09 -0000
***************
*** 0 ****
--- 1,167 ----
+ /* Copyright (c) 2005 by CodeSourcery, LLC.  All rights reserved. */
+ 
+ /** @file    vsip/impl/vmmul.hpp
+     @author  Jules Bergmann
+     @date    2005-08-15
+     @brief   VSIPL++ Library: vector-matrix multiply
+ 
+ */
+ 
+ #ifndef VSIP_IMPL_VMMUL_HPP
+ #define VSIP_IMPL_VMMUL_HPP
+ 
+ /***********************************************************************
+   Included Files
+ ***********************************************************************/
+ 
+ #include <vsip/impl/block-traits.hpp>
+ #include <vsip/vector.hpp>
+ #include <vsip/matrix.hpp>
+ #include <vsip/impl/promote.hpp>
+ 
+ 
+ 
+ /***********************************************************************
+   Declarations
+ ***********************************************************************/
+ 
+ namespace vsip
+ {
+ 
+ namespace impl
+ {
+ 
+ template <dimension_type Dim>
+ class Vmmul_class;
+ 
+ template <>
+ struct Vmmul_class<0>
+ {
+   template <typename T0,
+ 	     typename T1,
+ 	     typename T2,
+ 	     typename Block0,
+ 	     typename Block1,
+ 	     typename Block2>
+   static void exec(
+     const_Vector<T0, Block0> v,
+     const_Matrix<T1, Block1> m,
+     Matrix<T2, Block2>       res,
+     row2_type)
+   {
+     assert(v.size() == m.size(1));
+ 
+     // multiply rows of m by v (row-major)
+     for (index_type r=0; r<m.size(0); ++r)
+       res.row(r) = v * m.row(r);
+   }
+ 
+   template <typename T0,
+ 	     typename T1,
+ 	     typename T2,
+ 	     typename Block0,
+ 	     typename Block1,
+ 	     typename Block2>
+   static void exec(
+     const_Vector<T0, Block0> v,
+     const_Matrix<T1, Block1> m,
+     Matrix<T2, Block2>       res,
+     col2_type)
+   {
+     assert(v.size() == m.size(1));
+ 
+     // multiply rows of m by v (col-major)
+     for (index_type c=0; c<m.size(1); ++c)
+       res.col(c) = v.get(c) * m.col(c);
+   }
+ };
+ 
+ 
+ 
+ template <>
+ struct Vmmul_class<1>
+ {
+   template <typename T0,
+ 	    typename T1,
+ 	    typename T2,
+ 	    typename Block0,
+ 	    typename Block1,
+ 	    typename Block2>
+   static void exec(
+     const_Vector<T0, Block0> v,
+     const_Matrix<T1, Block1> m,
+     Matrix<T2, Block2>       res,
+     col2_type)
+   {
+     assert(v.size() == m.size(0));
+ 
+     // multiply cols of m by v (col-major)
+     for (index_type c=0; c<m.size(1); ++c)
+       res.col(c) = v * m.col(c);
+   }
+ 
+   template <typename T0,
+ 	    typename T1,
+ 	    typename T2,
+ 	    typename Block0,
+ 	    typename Block1,
+ 	    typename Block2>
+   static void exec(
+     const_Vector<T0, Block0> v,
+     const_Matrix<T1, Block1> m,
+     Matrix<T2, Block2>       res,
+     row2_type)
+   {
+     assert(v.size() == m.size(0));
+ 
+     // multiply cols of m by v (col-major)
+     for (index_type r=0; r<m.size(0); ++r)
+       res.row(r) = v.get(r) * m.row(r);
+   }
+ };
+ 
+ 
+ 
+ /// Traits class to determines return type for vmmul.
+ 
+ template <typename T0,
+ 	  typename T1,
+ 	  typename Block1>
+ struct Vmmul_traits
+ {
+   typedef typename vsip::Promotion<T0, T1>::type    value_type;
+   typedef typename Block_layout<Block1>::order_type order_type;
+   typedef Dense<2, value_type, order_type>          block_type;
+   typedef Matrix<value_type, block_type>            view_type;
+ };
+ 
+ } // namespace vsip::impl
+ 
+ 
+ 
+ /// Vector-matrix element-wise multiplication
+ 
+ template <dimension_type Dim,
+ 	  typename       T0,
+ 	  typename       T1,
+ 	  typename       Block0,
+ 	  typename       Block1>
+ typename vsip::impl::Vmmul_traits<T0, T1, Block1>::view_type
+ vmmul(
+   const_Vector<T0, Block0> v,
+   const_Matrix<T1, Block1> m)
+ VSIP_NOTHROW
+ {
+   typedef vsip::impl::Vmmul_traits<T0, T1, Block1> traits;
+   typedef typename traits::order_type order_type;
+ 
+   typename traits::view_type res(m.size(0), m.size(1));
+ 
+   vsip::impl::Vmmul_class<Dim>::exec(v, m, res, order_type());
+ 
+   return res;
+ }
+ 
+ } // namespace vsip
+ 
+ #endif // VSIP_IMPL_VMMUL_HPP
Index: tests/vmmul.cpp
===================================================================
RCS file: tests/vmmul.cpp
diff -N tests/vmmul.cpp
*** /dev/null	1 Jan 1970 00:00:00 -0000
--- tests/vmmul.cpp	23 Sep 2005 20:58:09 -0000
***************
*** 0 ****
--- 1,81 ----
+ /* Copyright (c) 2005 by CodeSourcery, LLC.  All rights reserved. */
+ 
+ /** @file    tests/vmmul.cpp
+     @author  Jules Bergmann
+     @date    2005-08-15
+     @brief   VSIPL++ Library: Unit tests for vector-matrix multiply.
+ */
+ 
+ /***********************************************************************
+   Included Files
+ ***********************************************************************/
+ 
+ 
+ #include <iostream>
+ #include <cassert>
+ #include <vsip/support.hpp>
+ #include <vsip/initfin.hpp>
+ #include <vsip/vector.hpp>
+ #include <vsip/selgen.hpp>
+ 
+ #include <vsip/impl/vmmul.hpp>
+ 
+ #include "test.hpp"
+ #include "plainblock.hpp"
+ 
+ using namespace std;
+ using namespace vsip;
+ 
+ 
+ 
+ /***********************************************************************
+   Definitions
+ ***********************************************************************/
+ 
+ template <dimension_type Dim,
+ 	  typename       OrderT,
+ 	  typename       T>
+ void
+ test_vmmul(
+   length_type rows,
+   length_type cols)
+ {
+   Matrix<T, Dense<2, T, OrderT> > m(rows, cols);
+   Vector<T> v(Dim == 0 ? cols : rows);
+ 
+   for (index_type r=0; r<rows; ++r)
+     for (index_type c=0; c<cols; ++c)
+       m(r, c) = T(r*cols+c);
+ 
+   v = ramp(T(), T(1), v.size());
+ 
+   Matrix<T> res = vmmul<Dim>(v, m);
+   
+   for (index_type r=0; r<rows; ++r)
+     for (index_type c=0; c<cols; ++c)
+       if (Dim == 0)
+ 	assert(equal(res(r, c), T(c * (r*cols+c))));
+       else
+ 	assert(equal(res(r, c), T(r * (r*cols+c))));
+ }
+ 
+ 
+ 
+ void
+ vmmul_cases()
+ {
+   test_vmmul<0, row2_type, float>(5, 7);
+   test_vmmul<0, col2_type, float>(5, 7);
+   test_vmmul<1, row2_type, float>(5, 7);
+   test_vmmul<1, col2_type, float>(5, 7);
+ }
+ 
+ 
+ 
+ int
+ main()
+ {
+   vsipl init;
+ 
+   vmmul_cases();
+ }