• Main Page
  • Namespaces
  • Data Structures
  • Files
  • File List
  • Globals

/data/development/ViennaCL/ViennaCL-1.1.2/viennacl/linalg/row_scaling.hpp

Go to the documentation of this file.
00001 /* =======================================================================
00002    Copyright (c) 2010, Institute for Microelectronics, TU Vienna.
00003    http://www.iue.tuwien.ac.at
00004                              -----------------
00005                      ViennaCL - The Vienna Computing Library
00006                              -----------------
00007                             
00008    authors:    Karl Rupp                          rupp@iue.tuwien.ac.at
00009                Florian Rudolf                     flo.rudy+viennacl@gmail.com
00010                Josef Weinbub                      weinbub@iue.tuwien.ac.at
00011 
00012    license:    MIT (X11), see file LICENSE in the ViennaCL base directory
00013 ======================================================================= */
00014 
00015 #ifndef _VIENNACL_ROW_SCALING_HPP_
00016 #define _VIENNACL_ROW_SCALING_HPP_
00017 
00022 #include <vector>
00023 #include <cmath>
00024 #include "viennacl/forwards.h"
00025 #include "viennacl/vector.hpp"
00026 #include "viennacl/compressed_matrix.hpp"
00027 #include "viennacl/tools/tools.hpp"
00028 
00029 #include <map>
00030 
00031 namespace viennacl
00032 {
00033   namespace linalg
00034   {
00035     
00038     class row_scaling_tag
00039     {
00040       public:
00045         row_scaling_tag(unsigned int p = 2) : norm_(p) {}
00046         
00048         unsigned int norm() const { return norm_; }
00049         
00050       private:
00051         unsigned int norm_;
00052     };
00053     
00054 
00057     template <typename MatrixType>
00058     class row_scaling
00059     {
00060       typedef typename MatrixType::value_type      ScalarType;
00061       
00062       public:
00068         row_scaling(MatrixType const & mat, row_scaling_tag const & tag) : system_matrix(mat), tag_(tag)
00069         {
00070           assert(mat.size1() == mat.size2());
00071           diag_M_inv.resize(mat.size1());  //resize without preserving values
00072           
00073           for (typename MatrixType::const_iterator1 row_it = system_matrix.begin1();
00074                 row_it != system_matrix.end1();
00075                 ++row_it)
00076           {
00077             diag_M_inv[row_it.index1()];
00078             for (typename MatrixType::const_iterator2 col_it = row_it.begin();
00079                   col_it != row_it.end();
00080                   ++col_it)
00081             {
00082               if (tag_.norm() == 1)
00083                 diag_M_inv[col_it.index1()] += std::fabs(*col_it);
00084               else
00085                 diag_M_inv[col_it.index1()] += (*col_it) * (*col_it);
00086             }
00087             if (diag_M_inv[row_it.index1()] == 0)
00088               throw "ViennaCL: Zero row encountered while setting up row scaling preconditioner!";
00089             
00090             if (tag_.norm() == 1)
00091               diag_M_inv[row_it.index1()] = static_cast<ScalarType>(1.0) / diag_M_inv[row_it.index1()];
00092             else
00093               diag_M_inv[row_it.index1()] = static_cast<ScalarType>(1.0) / std::sqrt(diag_M_inv[row_it.index1()]);
00094           }
00095         }
00096         
00097         
00099         template <typename VectorType>
00100         void apply(VectorType & vec) const
00101         {
00102           assert(vec.size() == diag_M_inv.size());
00103           for (size_t i=0; i<vec.size(); ++i)
00104           {
00105             vec[i] *= diag_M_inv[i];
00106           }
00107         }
00108         
00109       private:
00110         MatrixType const & system_matrix;
00111         row_scaling_tag const & tag_;
00112         std::vector<ScalarType> diag_M_inv;
00113     };
00114 
00115     
00120     template <typename ScalarType, unsigned int MAT_ALIGNMENT>
00121     class row_scaling< compressed_matrix<ScalarType, MAT_ALIGNMENT> >
00122     {
00123       typedef compressed_matrix<ScalarType, MAT_ALIGNMENT>   MatrixType;
00124       
00125       public:
00131         row_scaling(MatrixType const & mat, row_scaling_tag const & tag) : system_matrix(mat), tag_(tag), diag_M_inv(mat.size1())
00132         {
00133           assert(system_matrix.size1() == system_matrix.size2());
00134           
00135           init_gpu();
00136         }
00137         
00138         /*
00139         void init_cpu()
00140         {
00141           std::vector< std::map<unsigned int, ScalarType> > cpu_check;
00142           std::vector<ScalarType> diag_M_inv_cpu(system_matrix.size1());
00143           
00144           copy(system_matrix, cpu_check);
00145           viennacl::tools::const_sparse_matrix_adapter<ScalarType> cpu_check_adapter(cpu_check);
00146           
00147           for (typename viennacl::tools::const_sparse_matrix_adapter<ScalarType>::const_iterator1 row_it = cpu_check_adapter.begin1();
00148                 row_it != cpu_check_adapter.end1();
00149                 ++row_it)
00150           {
00151             diag_M_inv_cpu[row_it.index1()] = 0;
00152             for (typename viennacl::tools::const_sparse_matrix_adapter<ScalarType>::const_iterator2 col_it = row_it.begin();
00153                   col_it != row_it.end();
00154                   ++col_it)
00155             {
00156               if (tag_.norm() == 1)
00157                 diag_M_inv_cpu[col_it.index1()] += std::fabs(*col_it);
00158               else
00159                 diag_M_inv_cpu[col_it.index1()] += (*col_it) * (*col_it);
00160             }
00161             if (diag_M_inv_cpu[row_it.index1()] == 0)
00162               throw "ViennaCL: Zero row encountered while setting up row scaling preconditioner!";
00163             
00164             if (tag_.norm() == 1)
00165               diag_M_inv_cpu[row_it.index1()] = static_cast<ScalarType>(1.0) / diag_M_inv_cpu[row_it.index1()];
00166             else
00167               diag_M_inv_cpu[row_it.index1()] = static_cast<ScalarType>(1.0) / std::sqrt(diag_M_inv_cpu[row_it.index1()]);
00168           }
00169           
00170           diag_M_inv.resize(system_matrix.size1(), false);
00171           viennacl::fast_copy(diag_M_inv_cpu, diag_M_inv);
00172         } */
00173         
00174         void init_gpu()
00175         {
00176           if (tag_.norm() == 1)
00177           {
00178             viennacl::ocl::kernel & k = viennacl::ocl::get_kernel(
00179                                                 viennacl::linalg::kernels::compressed_matrix<ScalarType, MAT_ALIGNMENT>::program_name(),
00180                                                 "row_scaling_1");
00181 
00182             viennacl::ocl::enqueue( k(system_matrix.handle1(), system_matrix.handle2(), system_matrix.handle(), 
00183                                       diag_M_inv, static_cast<cl_uint>(diag_M_inv.size())) );        
00184           }
00185           else
00186           {
00187             viennacl::ocl::kernel & k = viennacl::ocl::get_kernel(
00188                                                 viennacl::linalg::kernels::compressed_matrix<ScalarType, MAT_ALIGNMENT>::program_name(),
00189                                                 "row_scaling_2");
00190 
00191             viennacl::ocl::enqueue( k(system_matrix.handle1(), system_matrix.handle2(), system_matrix.handle(), 
00192                                       diag_M_inv, static_cast<cl_uint>(diag_M_inv.size())) );        
00193           }
00194         }
00195         
00196         template <unsigned int ALIGNMENT>
00197         void apply(viennacl::vector<ScalarType, ALIGNMENT> & vec) const
00198         {
00199           assert(system_matrix.size1() == vec.size());
00200           
00201           //run kernel (reuse Jacobi kernel):
00202           viennacl::ocl::kernel & k = viennacl::ocl::get_kernel(viennacl::linalg::kernels::vector<ScalarType, ALIGNMENT>::program_name(),
00203                                                                 "diag_precond");
00204 
00205           viennacl::ocl::enqueue( k(diag_M_inv, vec, static_cast<cl_uint>(vec.size())) );        
00206         }
00207         
00208       private:
00209         MatrixType const & system_matrix;
00210         row_scaling_tag const & tag_;
00211         viennacl::vector<ScalarType> diag_M_inv;
00212     };
00213 
00214   }
00215 }
00216 
00217 
00218 
00219 
00220 #endif
00221 
00222 
00223 

Generated on Sat May 21 2011 20:36:50 for ViennaCL - The Vienna Computing Library by  doxygen 1.7.1