コード例 #1
0
ファイル: fmod_test.cpp プロジェクト: danstowell/stan
TEST(AgradFvar, fmod) {
  using stan::agrad::fvar;
  using std::fmod;
  using std::floor;

  fvar<double> x(2.0);
  fvar<double> y(3.0);
  x.d_ = 1.0;
  y.d_ = 2.0;

  fvar<double> a = fmod(x, y);
  EXPECT_FLOAT_EQ(fmod(2.0, 3.0), a.val_);
  EXPECT_FLOAT_EQ(1.0 * 1.0 + 2.0 * -floor(2.0 / 3.0), a.d_);

  double z = 4.0;
  double w = 3.0;

  fvar<double> e = fmod(x, z);
  EXPECT_FLOAT_EQ(fmod(2.0, 4.0), e.val_);
  EXPECT_FLOAT_EQ(1.0 / 4.0, e.d_);

  fvar<double> f = fmod(w, x);
  EXPECT_FLOAT_EQ(fmod(3.0, 2.0), f.val_);
  EXPECT_FLOAT_EQ(1.0 * -floor(3.0 / 2.0), f.d_);
 }
コード例 #2
0
ファイル: floor_test.cpp プロジェクト: HerraHuu/stan
TEST(AgradFwdFloor,FvarFvarDouble) {
  using stan::agrad::fvar;
  using std::floor;

  fvar<fvar<double> > x;
  x.val_.val_ = 1.5;
  x.val_.d_ = 2.0;

  fvar<fvar<double> > a = floor(x);

  EXPECT_FLOAT_EQ(floor(1.5), a.val_.val_);
  EXPECT_FLOAT_EQ(0, a.val_.d_);
  EXPECT_FLOAT_EQ(0, a.d_.val_);
  EXPECT_FLOAT_EQ(0, a.d_.d_);

  fvar<fvar<double> > y;
  y.val_.val_ = 1.5;
  y.d_.val_ = 2.0;

  a = floor(y);
  EXPECT_FLOAT_EQ(floor(1.5), a.val_.val_);
  EXPECT_FLOAT_EQ(0, a.val_.d_);
  EXPECT_FLOAT_EQ(0, a.d_.val_);
  EXPECT_FLOAT_EQ(0, a.d_.d_);
}
コード例 #3
0
ファイル: floor_test.cpp プロジェクト: HerraHuu/stan
TEST(AgradFwdFloor,FvarFvarVar_2ndDeriv) {
  using stan::agrad::fvar;
  using stan::agrad::var;
  using std::floor;

  fvar<fvar<var> > x;
  x.val_.val_ = 1.5;
  x.val_.d_ = 2.0;

  fvar<fvar<var> > a = floor(x);

  AVEC p = createAVEC(x.val_.val_);
  VEC g;
  a.val_.d_.grad(p,g);
  EXPECT_FLOAT_EQ(0.0, g[0]);

  fvar<fvar<var> > y;
  y.val_.val_ = 1.5;
  y.d_.val_ = 2.0;

  fvar<fvar<var> > b = floor(y);

  AVEC q = createAVEC(y.val_.val_);
  VEC r;
  b.d_.val_.grad(q,r);
  EXPECT_FLOAT_EQ(0.0, r[0]);
}
コード例 #4
0
ファイル: converter_policies.hpp プロジェクト: EricAlex/PDAL
  static source_type nearbyint ( argument_type s )
  {
    // Algorithm contributed by Guillaume Melquiond

#if !defined(BOOST_NO_STDC_NAMESPACE)
    using std::floor ;
    using std::ceil  ;
#endif

    // only works inside the range not at the boundaries
    S prev = floor(s);
    S next = ceil(s);

    S rt = (s - prev) - (next - s); // remainder type

    S const zero(0.0);
    S const two(2.0);

    if ( rt < zero )
      return prev;
    else if ( rt > zero )
      return next;
    else
    {
      bool is_prev_even = two * floor(prev / two) == prev ;
      return ( is_prev_even ? prev : next ) ;
    }
  }
コード例 #5
0
TEST(AgradFwdFdim,Fvar) {
  using stan::agrad::fvar;
  using stan::math::fdim;
  using std::isnan;
  using std::floor;

  fvar<double> x(2.0,1.0);
  fvar<double> y(-3.0,2.0);

  fvar<double> a = fdim(x, y);
  EXPECT_FLOAT_EQ(fdim(2.0, -3.0), a.val_);
  EXPECT_FLOAT_EQ(1.0 * 1.0 + 2.0 * -floor(2.0 / -3.0), a.d_);

  fvar<double> b = fdim(2 * x, y);
  EXPECT_FLOAT_EQ(fdim(2 * 2.0, -3.0), b.val_);
  EXPECT_FLOAT_EQ(2 * 1.0 * 1.0 + 2.0 * -floor(4.0 / -3.0), b.d_);

  fvar<double> c = fdim(y, x);
  EXPECT_FLOAT_EQ(fdim(-3.0, 2.0), c.val_);
  EXPECT_FLOAT_EQ(0.0, c.d_);

  fvar<double> d = fdim(x, x);
  EXPECT_FLOAT_EQ(fdim(2.0, 2.0), d.val_);
  EXPECT_FLOAT_EQ(0.0, d.d_);

  double z = 1.0;

  fvar<double> e = fdim(x, z);
  EXPECT_FLOAT_EQ(fdim(2.0, 1.0), e.val_);
  EXPECT_FLOAT_EQ(1.0, e.d_);

  fvar<double> f = fdim(z, x);
  EXPECT_FLOAT_EQ(fdim(1.0, 2.0), f.val_);
  EXPECT_FLOAT_EQ(0.0, f.d_);
 }
コード例 #6
0
ファイル: terrain.cpp プロジェクト: jonatanolofsson/cpgl
    void Terrain::get_height(Vector3f& position, Vector2f& direction) {
        using std::floor;
        using std::ceil;
        static const float x_scale = 1.0;
        static const float z_scale = 1.0;
        float x = position.x() * x_scale; // Scale 1.0
        float z = position.z() * z_scale; // Scale 1.0

        float y1, y2, y3, dydx, dydz, height;

        y1 = object->vertexArray[(int(x) + (int(z) + 1) * ttex.width)*3 + 1]; // Lower left
        y2 = object->vertexArray[((int(x)+1) + int(z) * ttex.width)*3 + 1]; // Upper right
        float dx = x-floor(x);
        float dz = z-floor(z);
        if(dx + dz > 1) { // Lower triangle
            y3 = object->vertexArray[((int(x)+1) + (int(z)+1) * ttex.width)*3 + 1];

            dydx = (y3 - y1)/x_scale;
            dydz = (y3 - y2)/z_scale;
            height = y3 - (1-dx)*dydx - (1-dz)*dydz;
        } else {
            y3 = object->vertexArray[(int(x) + int(z) * ttex.width)*3 + 1];

            dydx = (y2 - y3)/x_scale;
            dydz = (y1 - y3)/z_scale;
            height = y3 + dx * dydx + dz * dydz;
        }
        direction << dydx, dydz;
        position[1] = height;
    }
コード例 #7
0
void find_grid(AxisAlignedBox3 bbox, float reso,vector<unsigned int> *no_planes){
	/*This function finds the number of x, y and z planes that can fit in a given bounding box. The resolution(scaling factor) needed for the grid is specified as reso. This function fills up the no_planes vector by the number of x,y and z planes which will be able to fit in the bounding box. Assuming that th vector that will be passed to this function will be already initialized to length three. Since the bounding box is not to be treated too seriously to the point of one extra sample in one dimension, we will not specify two different fields for x direction size in no_planes.*/
	Vector3 lengths= bbox.getExtent();
	cout<<no_planes->size()<<endl;
	assert(no_planes->size()==3);

	(*no_planes)[0] = (unsigned int)floor(lengths[0]/(dist_x*reso));
	(*no_planes)[1] = (unsigned int)floor(lengths[1]/(dist_y*reso));
	(*no_planes)[2] = (unsigned int)floor(lengths[2]/(dist_z*reso));

	return;
}
コード例 #8
0
ファイル: bitmap.cpp プロジェクト: Aeon/voronoi
float Bitmap::getIntensity( float x, float y ) {
	using std::floor;

	// from wikipedia 
	unsigned char *iMPtr = intensityMap + (unsigned int)floor(y) * file->w + (unsigned int)floor(x);
	float fX = x - floor(x), fY = y - floor(y);
	
	return 
		(float)(*(iMPtr)) * (1 - fX) * (1 - fY) + 
		(float)(*(iMPtr + 1)) * fX * (1 - fY) +
		(float)(*(iMPtr + file->w)) * (1 - fX) * fY +
		(float)(*(iMPtr + file->w + 1)) * fX * fY;
}
コード例 #9
0
ファイル: fmod.hpp プロジェクト: javaosos/stan
 inline
 fvar<T>
 fmod(const double x1, const fvar<T>& x2) {
   using std::fmod;
   using std::floor;
   return fvar<T>(fmod(x1, x2.val_), -x2.d_ * floor(x1 / x2.val_));
 }
コード例 #10
0
      static source_type nearbyint ( argument_type s )
      {
#if !defined(BOOST_NO_STDC_NAMESPACE)
          using std::floor;
#endif
          return Double( floor(s.v) );
      }
コード例 #11
0
ファイル: floor_test.cpp プロジェクト: HerraHuu/stan
TEST(AgradFwdFloor,FvarVar_1stDeriv) {
  using stan::agrad::fvar;
  using stan::agrad::var;
  using std::floor;

  fvar<var> x(1.5,1.3);
  fvar<var> a = floor(x);

  EXPECT_FLOAT_EQ(floor(1.5), a.val_.val());
  EXPECT_FLOAT_EQ(0, a.d_.val());

  AVEC y = createAVEC(x.val_);
  VEC g;
  a.val_.grad(y,g);
  EXPECT_FLOAT_EQ(0, g[0]);
}
コード例 #12
0
ファイル: alexlib.cpp プロジェクト: agude/Project-Euler
bool IsPrime(const int64_t& INPUT_NUM) {
    using std::sqrt;
    using std::floor;
    // We hard code in a few cases, then test in general
    if (INPUT_NUM < 2) {  // 0, 1 and negative are not prime
        return false;
    } else if (INPUT_NUM < 4) {  // 3 is prime
        return true;
    } else if (INPUT_NUM % 2 == 0) {  // even numbers are not prime
        return false;
    } else if (INPUT_NUM < 9) {  // 6, 8 has been removed above
        return true;
    } else if (INPUT_NUM % 3 == 0) {  // numbers divisible by 3 are not prime
        return false;
    } else {
        const double FLOOR_ROOT = floor(sqrt(INPUT_NUM));
        const int R = static_cast<int>(FLOOR_ROOT);
        int f = 5;

        while (f <= R) {
            if (INPUT_NUM % f == 0) {
                return false;
            } else if (INPUT_NUM % (f + 2) == 0) {
                return false;
            } else {
                f += 6;
            }
        }
        return true;
    }
}
コード例 #13
0
  result_type operator()(Engine& eng)
  {
#ifndef BOOST_NO_STDC_NAMESPACE
    using std::log;
    using std::floor;
#endif
    return IntType(floor(log(RealType(1)-eng()) / _log_p)) + IntType(1);
  }
コード例 #14
0
ファイル: fmod.hpp プロジェクト: javaosos/stan
 inline
 fvar<T>
 fmod(const fvar<T>& x1, const fvar<T>& x2) {
   using std::fmod;
   using std::floor;
   return fvar<T>(fmod(x1.val_, x2.val_), 
                  x1.d_ - x2.d_ * floor(x1.val_ / x2.val_));
 }
コード例 #15
0
ファイル: fmod.hpp プロジェクト: danstowell/stan
 inline
 fvar<typename stan::return_type<T1,T2>::type>
 fmod(const T1& x1, const fvar<T2>& x2) {
   using std::fmod;
   using std::floor;
   return fvar<typename stan::return_type<T1,T2>::type>(
     fmod(x1, x2.val_), -x2.d_ * floor(x1 / x2.val_));
 }
コード例 #16
0
inline double cdf_dlaplace(double x, double p, double mu,
                           bool& throw_warning) {
#ifdef IEEE_754
  if (ISNAN(x) || ISNAN(p) || ISNAN(mu))
    return x+p+mu;
#endif
  if (p <= 0.0 || p >= 1.0) {
    throw_warning = true;
    return NAN;
  }
  if (x < 0.0) {
    // pow(p, -floor(x-mu))/(1.0+p);
    return exp( (log(p) * -floor(x-mu)) - log1p(p) );
  } else {
    // 1.0 - (pow(p, floor(x-mu)+1.0)/(1.0+p))
    return 1.0 - exp( log(p) * (floor(x-mu)+1.0) - log1p(p) );
  }
} 
コード例 #17
0
ファイル: converter_policies.hpp プロジェクト: EricAlex/PDAL
  static source_type nearbyint ( argument_type s )
  {
#if !defined(BOOST_NO_STDC_NAMESPACE)
    using std::floor ;
    using std::ceil  ;
#endif

    return s < static_cast<S>(0) ? ceil(s) : floor(s) ;
  }
コード例 #18
0
ファイル: fdim.hpp プロジェクト: mcobzarenco/unet
 inline
 fvar<T>
 fdim(const double x1, const fvar<T>& x2) {
   using stan::math::fdim;
   using std::floor;
   if(x1 < x2.val_)
     return fvar<T>(fdim(x1, x2.val_), 0);
   else 
     return fvar<T>(fdim(x1, x2.val_), x2.d_ * -floor(x1 / x2.val_));         
 }
コード例 #19
0
/** Calculates cubically interpolated value of the four given pixel values.
 * The pixel values should be interpolated values from sampley, from four
 * horizontally adjacent vertical lines. The parameters a, b, c and d
 * should be in fixed point format with 8-bit decimal part.
 * If we are calculating a pixel, whose x-coordinate in source image is
 * i, these vertical  lines from where a, b, c and d are calculated, should be
 * floor(i) - 1, floor(i), floor(i) + 1, floor(i) + 2, respectively.
 * Parameter len should be set to i.
 * Returns the interpolated value in 8-bit format, ready to be written
 * to output buffer.
 */
inline static int samplex(const int a, const int b, const int c, const int d, const double len) {
    double lenf = len - floor(len);
    int sum = 0;
    sum += (int)(a * (((-1.0 / 3.0) * lenf + 4.0 / 5.0) * lenf - 7.0 / 15.0) * lenf);
    sum += (int)(b * (((lenf - 9.0 / 5.0) * lenf - 1.0 / 5.0) * lenf + 1.0));
    sum += (int)(c * ((((1 - lenf) - 9.0 / 5.0) * (1 - lenf) - 1.0 / 5.0) * (1 - lenf) + 1.0));
    sum += (int)(d * (((-1.0 / 3.0) * (1 - lenf) + 4.0 / 5.0) * (1 - lenf) - 7.0 / 15.0) * (1 - lenf));
    //if (sum < 0) sum = 0;
    //if (sum > 255 * 256) sum = 255 * 256;
    return sum / 256;
}
コード例 #20
0
ファイル: fdim.hpp プロジェクト: mcobzarenco/unet
 inline
 fvar<T>
 fdim(const fvar<T>& x1, const fvar<T>& x2) {
   using stan::math::fdim;
   using std::floor;
   if(x1.val_ < x2.val_)
     return fvar<T>(fdim(x1.val_, x2.val_), 0);
   else 
     return fvar<T>(fdim(x1.val_, x2.val_),
                    x1.d_ - x2.d_ * floor(x1.val_ / x2.val_));
 }
コード例 #21
0
ファイル: bitmap.cpp プロジェクト: Aeon/voronoi
void Bitmap::getColour( float x, float y, unsigned char &r, unsigned char &g, unsigned char &b ) {
	using std::floor;

	float fX = x - floor(x), fY = y - floor(y);
	float f00 = (1 - fX) * (1 - fY),
		f10 = fX * (1 - fY),
		f01 = (1 - fX) * fY,
		f11 = fX * fY;

	unsigned char *dataPtr = file->data + (((unsigned int)floor(y) * file->w + (unsigned int)floor(x)) * 4);
	r = floor((float)(*(dataPtr)) * f00 + 
		(float)(*(dataPtr + 4)) * f10 +
		(float)(*(dataPtr + file->w * 4)) * f01 +
		(float)(*(dataPtr + file->w * 4 + 4)) * f11);

	dataPtr++;
	g = floor((float)(*(dataPtr)) * f00 + 
		(float)(*(dataPtr + 4)) * f10 +
		(float)(*(dataPtr + file->w * 4)) * f01 +
		(float)(*(dataPtr + file->w * 4 + 4)) * f11);

	dataPtr++;
	b = floor((float)(*(dataPtr)) * f00 + 
		(float)(*(dataPtr + 4)) * f10 +
		(float)(*(dataPtr + file->w * 4)) * f01 +
		(float)(*(dataPtr + file->w * 4 + 4)) * f11);
}
コード例 #22
0
unsigned long long detail::BinomialCoefficient::operator()(unsigned n, unsigned k)const
  {
  if(k == 0)
    return 1;

  if(n == 0)
    return 0;

  double product = 1;
  for(unsigned i = 1; i <= k; i++)
    product *= (double(n - (k - i)) / i);
  return (unsigned long long)(floor(product + 0.5));
  }
コード例 #23
0
ファイル: sinc.cpp プロジェクト: Heathcode/nesicide
//------------------------------------------------------------------------
// operator()(float) -
//  evaluate sinc at x, using our table and linear interpolation.
//------------------------------------------------------------------------
float
sinc::operator()(float x) const
{
    using std::abs;
    using std::floor;

    x = abs(x*convfactor_);

    const size_t ix1 = (size_t)floor(x), ix2 = ix1 + 1;
    const float v1 = fetchval(tbl_,ix1), v2 = fetchval(tbl_,ix2);

    return v1 + (x - ix1)*(v2-v1);
}
コード例 #24
0
  static source_type nearbyint ( argument_type s )
  {
    // Algorithm contributed by Guillaume Melquiond
    
#if !defined(BOOST_NO_STDC_NAMESPACE)
    using std::floor ;
    using std::ceil  ;
#endif    

    // only works inside the range not at the boundaries
    S a = floor(s); 
    S b = ceil(s);  
    
    S c = (s - a) - (b - s); // the "good" subtraction
    
    if ( c < static_cast<S>(0.0) ) 
      return a;
    else if ( c >  static_cast<S>(0.0) )
      return b;
    else 
      return 2 * floor(b / static_cast<S>(2.0)); // needs to behave sanely
  }
コード例 #25
0
    void next()
    {
      using std::sqrt;
      using std::floor;

      // In order to get the edges from the generator in sorted order, one
      // effective (but slow) procedure would be to use a
      // bernoulli_distribution for each legal (src, tgt) pair.  Because of the
      // O(n^2) cost of that, a geometric distribution is used.  The geometric
      // distribution tells how many times the bernoulli_distribution would
      // need to be run until it returns true.  Thus, this distribution can be
      // used to step through the edges which are actually present.  Everything
      // beyond "tgt += increment" is done to effectively convert linear
      // indexing (the partial sums of the geometric distribution output) into
      // graph edges.
      assert (src != (std::numeric_limits<vertices_size_type>::max)());
      vertices_size_type increment = rand_vertex(*gen);
      tgt += increment;
      if (is_undirected) {
    // Update src and tgt based on position of tgt
    // Basically, we want the greatest src_increment such that (in \bbQ):
    // src_increment * (src + allow_self_loops + src_increment - 1/2) <= tgt
    // The result of the LHS of this, evaluated with the computed
    // src_increment, is then subtracted from tgt
    double src_minus_half = (src + allow_self_loops) - 0.5;
    double disc = src_minus_half * src_minus_half + 2 * tgt;
    double src_increment_fp = floor(sqrt(disc) - src_minus_half);
    vertices_size_type src_increment = vertices_size_type(src_increment_fp);
    if (src + src_increment >= n) {
      src = n;
    } else {
      tgt -= (src + allow_self_loops) * src_increment + 
         src_increment * (src_increment - 1) / 2;
      src += src_increment;
    }
      } else {
    // Number of out edge positions possible from each vertex in this graph
    vertices_size_type possible_out_edges = n - (allow_self_loops ? 0 : 1);
    src += (std::min)(n - src, tgt / possible_out_edges);
    tgt %= possible_out_edges;
      }
      // Set end of graph code so (src, tgt) will be the same as for the end
      // sorted_erdos_renyi_iterator
      if (src >= n) {src = (std::numeric_limits<vertices_size_type>::max)(); tgt = 0;}
      // Copy (src, tgt) into current
      current.first = src;
      current.second = tgt;
      // Adjust for (src, src) edge being forbidden
      if (!allow_self_loops && tgt >= src) ++current.second;
    }
コード例 #26
0
ファイル: floor_test.cpp プロジェクト: HerraHuu/stan
TEST(AgradFwdFloor,FvarFvarVar_3rdDeriv) {
  using stan::agrad::fvar;
  using stan::agrad::var;

  fvar<fvar<var> > x;
  x.val_.val_ = 0.5;
  x.val_.d_ = 1.0;

  fvar<fvar<var> > a = floor(x);

  AVEC p = createAVEC(x.val_.val_);
  VEC g;
  a.d_.d_.grad(p,g);
  EXPECT_FLOAT_EQ(0, g[0]);
}
コード例 #27
0
int vectester (Vector zerovec)
{
  using std::abs;
  using std::acos;
  using std::asin;
  using std::atan;
  using std::floor;
  using std::pow;
  using std::sin;
  using std::sqrt;
  using std::tan;

  typedef typename Vector::value_type Scalar;

  Vector random_vec = zerovec;

  Vector error_vec = zerovec;

  std::srand(12345); // Fixed seed for reproduceability of failures

  // Avoid divide by zero errors or acos(x>1) NaNs later
  for (unsigned int i=0; i != random_vec.size(); ++i)
    random_vec.raw_at(i) = .25 + (static_cast<Scalar>(std::rand())/RAND_MAX/2);

  int returnval = 0;

  one_test(2*random_vec - random_vec - random_vec);

  one_test(3*random_vec - random_vec*3);

  one_test((random_vec + random_vec)/2 - random_vec);

  one_test(sqrt(random_vec) * sqrt(random_vec) - random_vec);
  one_test(random_vec*random_vec - pow(random_vec,2));
  one_test(sqrt(random_vec) - pow(random_vec,Scalar(.5)));

  one_test(random_vec - sin(asin(random_vec)));
  one_test(random_vec - tan(atan(random_vec)));

  one_test(floor(random_vec / 2));
  one_test(abs(random_vec) - random_vec);

  return returnval;
}
コード例 #28
0
RealType generate_canonical_impl(URNG& g, boost::mpl::false_ /*is_integral*/)
{
    using std::pow;
    using std::floor;
    BOOST_ASSERT((g.min)() == 0);
    BOOST_ASSERT((g.max)() == 1);
    std::size_t digits = std::numeric_limits<RealType>::digits;
    std::size_t engine_bits = detail::generator_bits<URNG>::value();
    std::size_t b = (std::min)(bits, digits);
    RealType R = pow(RealType(2), RealType(engine_bits));
    RealType mult = R;
    RealType limit = pow(RealType(2), RealType(b));
    RealType S = RealType(g() - (g.min)());
    while(mult < limit) {
        RealType inc(floor((RealType(g()) - RealType((g.min)())) * R));
        S += inc * mult;
        mult *= R;
    }
    return S / mult;
}
コード例 #29
0
ファイル: 1074.cpp プロジェクト: karan007/acmicpc-codes
 void print_real_number(const string& s,int N)
 {
      static const int MAXLENGTH=200;
      static const int MAXN=100;
      int position_of_e=std::string::npos;
      if (s.find("e")!=std::string::npos) position_of_e=s.find("e");
      if (s.find("E")!=std::string::npos) position_of_e=s.find("E");
      
      string simple_real_number_part;
      int value_of_e;
      if (position_of_e!=std::string::npos)
      {
         simple_real_number_part=s.substr(0,position_of_e);
         stringstream
         in(s.substr(position_of_e+1,s.length()-(position_of_e+1)));
         double get;
         in>>get;
         if (get>MAXLENGTH) value_of_e=MAXLENGTH;
         else if (get<-MAXLENGTH) value_of_e=-MAXLENGTH;
         else value_of_e=floor(get+0.5);
      }
コード例 #30
0
ファイル: converter_test.cpp プロジェクト: Albermg7/boost
void test_round_even()
{
  cout << "Testing 'RoundEven' tie-breaking\n";

  double min = boost::numeric::bounds<double>::lowest();
  double max = boost::numeric::bounds<double>::highest();

#if !defined(BOOST_NO_STDC_NAMESPACE)
  using std::floor ;
  using std::ceil ;
#endif
  test_round_even(min, floor(min));
  test_round_even(max, ceil (max));
  test_round_even(2.0, 2.0);
  test_round_even(2.3, 2.0);
  test_round_even(2.5, 2.0);
  test_round_even(2.7, 3.0);
  test_round_even(3.0, 3.0);
  test_round_even(3.3, 3.0);
  test_round_even(3.5, 4.0);
  test_round_even(3.7, 4.0);
}