All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
scalar.cpp
Go to the documentation of this file.
/* =========================================================================
Copyright (c) 2010-2016, Institute for Microelectronics,
Institute for Analysis and Scientific Computing,
TU Wien.
Portions of this software are copyright by UChicago Argonne, LLC.
-----------------
ViennaCL - The Vienna Computing Library
-----------------
Project Head: Karl Rupp rupp@iue.tuwien.ac.at
(A list of authors and contributors can be found in the PDF manual)
License: MIT (X11), see file LICENSE in the base directory
============================================================================= */
//
// *** System
//
#include <iostream>
#include <algorithm>
#include <cmath>
//
// *** ViennaCL
//
#include "viennacl/scalar.hpp"
//
// -------------------------------------------------------------
//
template<typename ScalarType>
ScalarType diff(ScalarType & s1, viennacl::scalar<ScalarType> & s2)
{
viennacl::backend::finish();
if (std::fabs(s1 - s2) > 0)
return (s1 - s2) / std::max(std::fabs(s1), std::fabs(s2));
return 0;
}
//
// -------------------------------------------------------------
//
template< typename NumericT, typename Epsilon >
int test(Epsilon const& epsilon)
{
int retval = EXIT_SUCCESS;
NumericT s1 = NumericT(3.1415926);
NumericT s2 = NumericT(2.71763);
NumericT s3 = NumericT(42);
viennacl::scalar<NumericT> vcl_s1;
viennacl::scalar<NumericT> vcl_s2;
viennacl::scalar<NumericT> vcl_s3 = 1.0;
vcl_s1 = s1;
if ( std::fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: vcl_s1 = s1;" << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
vcl_s2 = s2;
if ( std::fabs(diff(s2, vcl_s2)) > epsilon )
{
std::cout << "# Error at operation: vcl_s2 = s2;" << std::endl;
std::cout << " diff: " << fabs(diff(s2, vcl_s2)) << std::endl;
retval = EXIT_FAILURE;
}
vcl_s3 = s3;
if ( std::fabs(diff(s3, vcl_s3)) > epsilon )
{
std::cout << "# Error at operation: vcl_s3 = s3;" << std::endl;
std::cout << " diff: " << s3 - vcl_s3 << std::endl;
retval = EXIT_FAILURE;
}
NumericT tmp = s2;
s2 = s1;
s1 = tmp;
viennacl::linalg::swap(vcl_s1, vcl_s2);
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: swap " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2;
vcl_s1 += vcl_s2;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: += " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 *= s3;
vcl_s1 *= vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: *= " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2;
vcl_s1 -= vcl_s2;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: -= " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 /= s3;
vcl_s1 /= vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: /= " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = vcl_s1;
s1 = s2 + s3;
vcl_s1 = vcl_s2 + vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 + s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 + s3;
vcl_s1 += vcl_s2 + vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 + s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 + s3;
vcl_s1 -= vcl_s2 + vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 + s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = s2 - s3;
vcl_s1 = vcl_s2 - vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 - s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 - s3;
vcl_s1 += vcl_s2 - vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 - s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 - s3;
vcl_s1 -= vcl_s2 - vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 - s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = s2 * s3;
vcl_s1 = vcl_s2 * vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 * s3;
vcl_s1 += vcl_s2 * vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 * s3;
vcl_s1 -= vcl_s2 * vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = s2 / s3;
vcl_s1 = vcl_s2 / vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 / s3;
vcl_s1 += vcl_s2 / vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 / s3;
vcl_s1 -= vcl_s2 / vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
// addition with factors, =
vcl_s1 = s1;
s1 = s2 * s2 + s3 * s3;
vcl_s1 = vcl_s2 * s2 + vcl_s3 * s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 * s2 + s3 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
vcl_s1 = vcl_s2 * vcl_s2 + vcl_s3 * vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 * s2 + s3 * s3, second test " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = s2 * s2 + s3 / s3;
vcl_s1 = vcl_s2 * s2 + vcl_s3 / s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 * s2 + s3 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
vcl_s1 = vcl_s2 * vcl_s2 + vcl_s3 / vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 * s2 + s3 / s3, second test " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = s2 / s2 + s3 * s3;
vcl_s1 = vcl_s2 / s2 + vcl_s3 * s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 / s2 + s3 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
vcl_s1 = vcl_s2 / vcl_s2 + vcl_s3 * vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 / s2 + s3 * s3, second test " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 = s2 / s2 + s3 / s3;
vcl_s1 = vcl_s2 / s2 + vcl_s3 / s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 / s2 + s3 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
vcl_s1 = vcl_s2 / vcl_s2 + vcl_s3 / vcl_s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 = s2 / s2 + s3 / s3, second test " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
// addition with factors, +=
vcl_s1 = s1;
s1 += s2 * s2 + s3 * s3;
vcl_s1 += vcl_s2 * s2 + vcl_s3 * s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 * s2 + s3 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 * s2 + s3 / s3;
vcl_s1 += vcl_s2 * s2 + vcl_s3 / s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 * s2 + s3 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 / s2 + s3 * s3;
vcl_s1 += vcl_s2 / s2 + vcl_s3 * s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 / s2 + s3 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 += s2 / s2 + s3 / s3;
vcl_s1 += vcl_s2 / s2 + vcl_s3 / s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 += s2 / s2 + s3 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
// addition with factors, -=
vcl_s1 = s1;
s1 -= s2 * s2 + s3 * s3;
vcl_s1 -= vcl_s2 * s2 + vcl_s3 * s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 * s2 + s3 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 * s2 + s3 / s3;
vcl_s1 -= vcl_s2 * s2 + vcl_s3 / s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 * s2 + s3 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 / s2 + s3 * s3;
vcl_s1 -= vcl_s2 / s2 + vcl_s3 * s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 / s2 + s3 * s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
s1 -= s2 / s2 + s3 / s3;
vcl_s1 -= vcl_s2 / s2 + vcl_s3 / s3;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: s1 -= s2 / s2 + s3 / s3 " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
// lenghty expression:
s1 = s2 + s3 * s2 - s3 / s1;
vcl_s1 = vcl_s2 + vcl_s3 * vcl_s2 - vcl_s3 / vcl_s1;
if ( fabs(diff(s1, vcl_s1)) > epsilon )
{
std::cout << "# Error at operation: + * - / " << std::endl;
std::cout << " diff: " << fabs(diff(s1, vcl_s1)) << std::endl;
retval = EXIT_FAILURE;
}
return retval;
}
//
// -------------------------------------------------------------
//
int main()
{
std::cout << std::endl;
std::cout << "----------------------------------------------" << std::endl;
std::cout << "----------------------------------------------" << std::endl;
std::cout << "## Test :: Scalar" << std::endl;
std::cout << "----------------------------------------------" << std::endl;
std::cout << "----------------------------------------------" << std::endl;
std::cout << std::endl;
int retval = EXIT_SUCCESS;
std::cout << std::endl;
std::cout << "----------------------------------------------" << std::endl;
std::cout << std::endl;
{
typedef float NumericT;
NumericT epsilon = NumericT(1.0E-5);
std::cout << "# Testing setup:" << std::endl;
std::cout << " eps: " << epsilon << std::endl;
std::cout << " numeric: float" << std::endl;
retval = test<NumericT>(epsilon);
if ( retval == EXIT_SUCCESS )
std::cout << "# Test passed" << std::endl;
else
return retval;
}
std::cout << std::endl;
std::cout << "----------------------------------------------" << std::endl;
std::cout << std::endl;
#ifdef VIENNACL_WITH_OPENCL
if ( viennacl::ocl::current_device().double_support() )
#endif
{
{
typedef double NumericT;
NumericT epsilon = 1.0E-10;
std::cout << "# Testing setup:" << std::endl;
std::cout << " eps: " << epsilon << std::endl;
std::cout << " numeric: double" << std::endl;
retval = test<NumericT>(epsilon);
if ( retval == EXIT_SUCCESS )
std::cout << "# Test passed" << std::endl;
else
return retval;
}
std::cout << std::endl;
}
std::cout << std::endl;
std::cout << "------- Test completed --------" << std::endl;
std::cout << std::endl;
return retval;
}
//
// -------------------------------------------------------------
//
viennacl::scalar
This class represents a single scalar value on the GPU and behaves mostly like a built-in scalar type...
Definition: forwards.h:227
viennacl::backend::finish
void finish()
Synchronizes the execution. finish() will only return after all compute kernels (CUDA, OpenCL) have completed.
Definition: memory.hpp:54
s2
viennacl::scalar< int > s2
Definition: global_variables.cpp:58
s1
viennacl::scalar< float > s1
Definition: global_variables.cpp:57
viennacl::linalg::detail::max
T max(const T &lhs, const T &rhs)
Maximum.
Definition: util.hpp:59
main
int main()
Definition: scalar.cpp:407
viennacl::ocl::current_device
viennacl::ocl::device const & current_device()
Convenience function for returning the active device in the current context.
Definition: backend.hpp:351
NumericT
float NumericT
Definition: bisect.cpp:40
viennacl::linalg::swap
viennacl::enable_if< viennacl::is_scalar< S1 >::value &&viennacl::is_scalar< S2 >::value >::type swap(S1 &s1, S2 &s2)
Swaps the contents of two scalars.
Definition: scalar_operations.hpp:213
viennacl::ocl::device::double_support
bool double_support() const
ViennaCL convenience function: Returns true if the device supports double precision.
Definition: device.hpp:956
test
int test(Epsilon const &epsilon)
Definition: scalar.cpp:50
diff
ScalarType diff(ScalarType &s1, viennacl::scalar< ScalarType > &s2)
Definition: scalar.cpp:39
ScalarType
float ScalarType
Definition: fft_1d.cpp:42
scalar.hpp
Implementation of the ViennaCL scalar class.