コード例 #1
2
ファイル: ChiSquare.c プロジェクト: AlexandreMertens/MoMEMta
static real ChiSquare(creal x, cint df)
{
  real y;

  if( df <= 0 ) return -999;

  if( x <= 0 ) return 0;
  if( x > 1000*df ) return 1;

  if( df > 1000 ) {
    if( x < 2 ) return 0;
    y = 2./(9*df);
    y = (powx(x/df, 1/3.) - (1 - y))/sqrtx(y);
    if( y > 5 ) return 1;
    if( y < -18.8055 ) return 0;
    return Normal(y);
  }

  y = .5*x;

  if( df & 1 ) {
    creal sqrty = sqrtx(y);
    real h = Erf(sqrty);
    count i;

    if( df == 1 ) return h;

    y = sqrty*expx(-y)/.8862269254527579825931;
    for( i = 3; i < df; i += 2 ) {
      h -= y;
      y *= x/i;
    }
    y = h - y;
  }
  else {
    real term = expx(-y), sum = term;
    count i;

    for( i = 1; i < df/2; ++i )
      sum += term *= y/i;
    y = 1 - sum;
  }

  return Max(0., y);
}
コード例 #2
0
ファイル: Camera.cpp プロジェクト: seclorum/ziiWakeBreaker
void Camera::Update()
{
    Vector3 f = m_center - m_eye;
    //normalize it
    //int test = XTOF(f.z);
    int mag = sqrtx( (int32)(MULX(f.x,f.x) + (int32)MULX(f.y,f.y) + (int32)MULX(f.z,f.z)) );

    int n = DIVX(ITOX(1),mag);

    f.x = MULX(f.x,n);
    f.y = MULX(f.y,n);
    f.z = MULX(f.z,n);

    //update direction
    m_dir = f;


    Vector3 s = f ^ m_up,
            u = s ^ f;

    int matrix[16] = { s.x, u.x, -f.x, 0,
                       s.y, u.y, -f.y, 0,
                       s.z, u.z, -f.z, 0,
                       0,  0,   0,  ITOX(1)
                     };


    glMultMatrixx(matrix);

    glTranslatex(-m_eye.x,-m_eye.y,-m_eye.z);

}
コード例 #3
0
static inline void BFGS(cThis *t, ccount n, real *hessian,
  creal *gnew, creal *g, real *p, creal dx)
{
  Vector(real, y, NDIM);
  real c;
  count i, j;

  for( i = 0; i < n; ++i )
    y[i] = gnew[i] - g[i];
  c = dx*Dot(n, y, p);
  if( c < 1e-10 ) return;
  RenormalizeCholesky(t, n, hessian, y, 1/c);

  c = Dot(n, g, p);
  if( c >= 0 ) return;
  c = 1/sqrtx(-c);
  for( i = 0; i < n; ++i )
    y[i] = c*g[i];
  UpdateCholesky(t, n, hessian, y, p);

  for( i = 0; i < n - 1; ++i )
    for( j = i + 1; j < n; ++j )
      Hessian(i, j) = Hessian(j, i);
}
コード例 #4
0
static inline real Length(ccount n, creal *vec)
{
  return sqrtx(Dot(n, vec, vec));
}
コード例 #5
0
static Point LineSearch(This *t, ccount nfree, ccount *ifree,
  creal *p, creal *xini, real fini, real *x,
  real step, creal range, creal grad,
  creal ftol, creal xtol, creal gtol)
{
  real tol = ftol, tol2 = tol + tol;
  Point cur = {0, fini};

  XCopy(x, xini);

  /* don't even try if
     a) we'd walk backwards,
     b) the range to explore is too small,
     c) the gradient is positive, i.e. we'd move uphill */

  if( step > 0 && range > tol2 && grad <= 0 ) {
    creal eps = RTEPS*fabsx(range) + ftol;
    creal mingrad = -1e-4*grad, maxgrad = -gtol*grad;

    real end = range + eps;
    real maxstep = range - eps/(1 + RTEPS);

    Point min = cur, v = cur, w = cur;
    Point a = cur, b = {end, 0};
    real a1, b1 = end;

    /* distmin: distance along p from xini to the minimum,
       u: second-lowest point,
       v: third-lowest point,
       a, b: interval in which the minimum is sought. */

    real distmin = 0, dist, mid, q, r, s;
    count i;
    int shift;
    bool first;

    for( first = true; ; first = false ) {
      if( step >= maxstep ) {
        step = maxstep;
        maxstep = maxstep*(1 + .75*RTEPS) + .75*tol;
      }

      cur.dx = (fabsx(step) >= tol) ? step : (step > 0) ? tol : -tol;
      dist = distmin + cur.dx;
      for( i = 0; i < nfree; ++i ) {
        ccount dim = ifree[i];
        x[dim] = xini[dim] + dist*p[i];
      }
      cur.f = Sample(t, x);

      if( cur.f <= min.f ) {
        v = w;
        w = min;
        min.f = cur.f;
        distmin = dist;

        /* shift everything to the new minimum position */
        maxstep -= cur.dx;
        v.dx -= cur.dx;
        w.dx -= cur.dx;
        a.dx -= cur.dx;
        b.dx -= cur.dx;
        if( cur.dx < 0 ) b = w;
        else a = w;

        tol = RTEPS*fabsx(distmin) + ftol;
        tol2 = tol + tol;
      }
      else {
        if( cur.dx < 0 ) a = cur;
        else b = cur;
        if( cur.f <= w.f || w.dx == 0 ) v = w, w = cur;
        else if( cur.f <= v.f || v.dx == 0 || v.dx == w.dx ) v = cur;
      }

      if( distmin + b.dx <= xtol ) break;
      if( min.f < fini &&
          a.f - min.f <= fabsx(a.dx)*maxgrad &&
          (fabsx(distmin - range) > tol || maxstep < b.dx) ) break;

      mid = .5*(a.dx + b.dx);
      if( fabsx(mid) <= tol2 - .5*(b.dx - a.dx) ) break;

      r = q = s = 0;
      if( fabsx(end) > tol ) {
        if( first ) {
          creal s1 = w.dx*grad;
          creal s2 = w.f - min.f;
          s = (s1 - ((distmin == 0) ? 0 : 2*s2))*w.dx;
          q = 2*(s2 - s1);
        }
        else {
          creal s1 = w.dx*(v.f - min.f);
          creal s2 = v.dx*(w.f - min.f);
          s = s1*w.dx - s2*v.dx;
          q = 2*(s2 - s1);
        }
        if( q > 0 ) s = -s;
        q = fabsx(q);
        r = end;
        if( step != b1 || b.dx <= maxstep ) end = step;
      }

      if( distmin == a.dx ) step = mid;
      else if( b.dx > maxstep ) step = (step < b.dx) ? -4*a.dx : maxstep;
      else {
        real num = a.dx, den = b.dx;
        if( fabsx(b.dx) <= tol || (w.dx > 0 && fabsx(a.dx) > tol) )
          num = b.dx, den = a.dx;
        num /= -den;
        step = (num < 1) ? .5*den*sqrtx(num) : 5/11.*den*(.1 + 1/num);
      }

      if( step > 0 ) a1 = a.dx, b1 = step;
      else a1 = step, b1 = b.dx;
      if( fabsx(s) < fabsx(.5*q*r) && s > q*a1 && s < q*b1 ) {
        step = s/q;
        if( step - a.dx < tol2 || b.dx - step < tol2 )
          step = (mid > 0) ? tol : -tol;
      }
      else end = (mid > 0) ? b.dx : a.dx;
    }

    first = true;
    if( fabsx(distmin - range) < tol ) {
      distmin = range;
      if( maxstep > b.dx ) first = false;
    }

    for( cur.dx = distmin, cur.f = min.f, shift = -1; ;
         cur.dx = Max(ldexp(distmin, shift), ftol), shift <<= 1 ) {
      for( i = 0; i < nfree; ++i ) {
        ccount dim = ifree[i];
        x[dim] = xini[dim] + cur.dx*p[i];
      }
      if( !first ) cur.f = Sample(t, x);

      if( cur.dx + b.dx <= xtol ) {
        cur.dx = 0;
        break;
      }
      if( fini - cur.f > cur.dx*mingrad ) break;
      if( cur.dx <= ftol ) {
        cur.dx = 0;
        break;
      }
      first = false;
    }
  }

  return cur;
}