Skip to content

Instantly share code, notes, and snippets.

@aont
Last active August 29, 2015 14:07
Show Gist options
  • Select an option

  • Save aont/eeedc3c0d61d3fdb859f to your computer and use it in GitHub Desktop.

Select an option

Save aont/eeedc3c0d61d3fdb859f to your computer and use it in GitHub Desktop.
Compile Time sqrt(2)
#include <cstdio>
#include <cstdlib>
template<int x>
struct from_int
{
const static double value;
};
template<int x>
const double from_int<x>::value = x;
template<
bool flag,
typename T,
typename F
>
struct ternary;
template<
typename T,
typename F
>
struct ternary<true, T, F>
{
const static double value;
};
template<
typename T,
typename F
>
const double ternary<true, T, F>::value = T::value;
template<
typename T,
typename F
>
struct ternary<false, T, F>
{
const static double value;
};
template<
typename T,
typename F
>
const double ternary<false, T, F>::value = F::value;
namespace newton
{
template<typename X0, typename Y>
struct advance
{
const static double value;
};
template<typename X0, typename Y>
const double advance<X0, Y>::value =
X0::value - (X0::value*X0::value - Y::value) / (2*X0::value) ;
template<typename X0, typename Y>
struct is_converged
{
const static bool value;
};
template<typename X0, typename Y>
const bool is_converged<X0, Y>::value =
X0::value*X0::value<Y::value*(1+1e-15) &&
X0::value*X0::value>Y::value*(1-1e-15) ;
template<typename X0, typename Y>
struct solve_impl
{
typedef advance<X0, Y> adv_t;
const static double value;
};
template<typename X0, typename Y>
const double solve_impl<X0, Y>::value =
ternary<is_converged<X0, Y>::value, X0, solve_impl<adv_t, Y> >::value;
template<typename Y>
struct solve : public solve_impl<from_int<1>, Y> { };
}
int main()
{
typedef from_int<2> f2;
printf("sqrt(2)=%.16g\n", newton::solve<f2>::value);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment