예제 #1
0
파일: eigen.c 프로젝트: BRAINSia/teem
/*
** NOTE: assumes that eval and roots have come from
** ell_3m2sub_eigenvalues_d(m)
*/
void
_ell_3m2sub_evecs_d(double evec[9], double eval[3], int roots,
                    const double m[9]) {
  double n[4];
  static const char me[]="_ell_3m2sub_evecs_d";

  if (ell_cubic_root_three == roots) {
    /* set off-diagonal entries once */
    n[1] = m[1];
    n[2] = m[3];
    /* find first evec */
    n[0] = m[0] - eval[0];
    n[3] = m[3] - eval[0];
    ell_2m_1d_nullspace_d(evec + 3*0, n);
    (evec + 3*0)[2] = 0;
    /* find second evec */
    n[0] = m[0] - eval[1];
    n[3] = m[3] - eval[1];
    ell_2m_1d_nullspace_d(evec + 3*1, n);
    (evec + 3*1)[2] = 0;
    _ell_22v_enforce_orthogonality(evec + 3*0, evec + 3*1);
    /* make right-handed */
    ELL_3V_CROSS(evec + 3*2, evec + 3*0, evec + 3*1);
  } else if (ell_cubic_root_single_double == roots) {
    /* can pick any 2D basis */
    ELL_3V_SET(evec + 3*0, 1, 0, 0);
    ELL_3V_SET(evec + 3*1, 0, 1, 0);
    ELL_3V_SET(evec + 3*2, 0, 0, 1);
  } else {
    /* ell_cubic_root_single == roots, if assumptions are met */
    ELL_3V_SET(evec + 3*0, AIR_NAN, AIR_NAN, 0);
    ELL_3V_SET(evec + 3*1, AIR_NAN, AIR_NAN, 0);
    ELL_3V_SET(evec + 3*2, 0, 0, 1);
  }
  if (!ELL_3M_EXISTS(evec)) {
    fprintf(stderr, "%s: given m = \n", me);
    ell_3m_print_d(stderr, m);
    fprintf(stderr, "%s: got roots = %s (%d) and evecs = \n", me,
            airEnumStr(ell_cubic_root, roots), roots);
    ell_3m_print_d(stderr, evec);
  }
  return;
}
예제 #2
0
static
tenFiberContext *
_tenFiberContextCommonNew(const Nrrd *vol, int useDwi,
                          double thresh, double soft, double valueMin,
                          int ten1method, int ten2method) {
  char me[]="_tenFiberContextCommonNew", err[BIFF_STRLEN];
  tenFiberContext *tfx;
  gageKind *kind;

  if (!( tfx = (tenFiberContext *)calloc(1, sizeof(tenFiberContext)) )) {
    sprintf(err, "%s: couldn't allocate new context", me);
    biffAdd(TEN, err); return NULL;
  }

  if (useDwi) {
    Nrrd *ngrad=NULL, *nbmat=NULL;
    double bval=0;
    unsigned int *skip, skipNum;

    tfx->useDwi = AIR_TRUE;
    /* default fiber type */
    tfx->fiberType = tenDwiFiberTypeUnknown;
    
    if (tenDWMRIKeyValueParse(&ngrad, &nbmat, &bval, &skip, &skipNum, vol)) {
      sprintf(err, "%s: trouble parsing DWI info", me );
      biffAdd(TEN, err); return NULL;
    }
    if (skipNum) {
      sprintf(err, "%s: sorry, can't do DWI skipping here", me);
      biffAdd(TEN, err); return NULL;
    }
    kind = tenDwiGageKindNew();
    if (tenDwiGageKindSet(kind,
                          thresh, soft, bval, valueMin,
                          ngrad, NULL,
                          ten1method, ten2method, 42)) {
      sprintf(err, "%s: trouble setting DWI kind", me);
      biffAdd(TEN, err); return NULL;
    }
  } else {
    /* it should be a tensor volume */
    tfx->useDwi = AIR_FALSE;
    /* default fiber type */
    tfx->fiberType = tenFiberTypeUnknown;
    if (tenTensorCheck(vol, nrrdTypeUnknown, AIR_TRUE, AIR_TRUE)) {
      sprintf(err, "%s: didn't get a tensor volume", me);
      biffAdd(TEN, err); return NULL;
    }
    kind = tenGageKind;
  }

  if ( !(tfx->gtx = gageContextNew())
       || !(tfx->pvl = gagePerVolumeNew(tfx->gtx, vol, kind))
       || (gagePerVolumeAttach(tfx->gtx, tfx->pvl)) ) {
    sprintf(err, "%s: gage trouble", me);
    biffMove(TEN, err, GAGE); free(tfx); return NULL;
  }

  tfx->nin = vol;
  tfx->ksp = nrrdKernelSpecNew();
  if (nrrdKernelSpecParse(tfx->ksp, tenDefFiberKernel)) {
    sprintf(err, "%s: couldn't parse tenDefFiberKernel \"%s\"",
            me,  tenDefFiberKernel);
    biffMove(TEN, err, NRRD); return NULL;
  }
  if (tenFiberKernelSet(tfx, tfx->ksp->kernel, tfx->ksp->parm)) {
    sprintf(err, "%s: couldn't set default kernel", me);
    biffAdd(TEN, err); return NULL;
  }
  /* looks to GK like GK says that we must set some stop criterion */
  tfx->intg = tenDefFiberIntg;
  tfx->anisoStopType = tenDefFiberAnisoStopType;
  tfx->anisoSpeedType = tenAnisoUnknown;
  tfx->stop = 0;
  tfx->anisoThresh = tenDefFiberAnisoThresh;
  /* so I'm not using the normal default mechanism, shoot me */
  tfx->anisoSpeedFunc[0] = 0;
  tfx->anisoSpeedFunc[1] = 0;
  tfx->anisoSpeedFunc[2] = 0;
  tfx->maxNumSteps = tenDefFiberMaxNumSteps;
  tfx->minNumSteps = 0;
  tfx->useIndexSpace = tenDefFiberUseIndexSpace;
  tfx->verbose = 0;
  tfx->stepSize = tenDefFiberStepSize;
  tfx->maxHalfLen = tenDefFiberMaxHalfLen;
  tfx->minWholeLen = 0.0;
  tfx->confThresh = 0.5; /* why do I even bother setting these- they'll
                            only get read if the right tenFiberStopSet has
                            been called, in which case they'll be set... */
  tfx->minRadius = 1;    /* above lament applies here as well */
  tfx->minFraction = 0.5; /* and here */
  tfx->wPunct = tenDefFiberWPunct;

  GAGE_QUERY_RESET(tfx->query);
  tfx->mframe[0] = vol->measurementFrame[0][0];
  tfx->mframe[1] = vol->measurementFrame[1][0];
  tfx->mframe[2] = vol->measurementFrame[2][0];
  tfx->mframe[3] = vol->measurementFrame[0][1];
  tfx->mframe[4] = vol->measurementFrame[1][1];
  tfx->mframe[5] = vol->measurementFrame[2][1];
  tfx->mframe[6] = vol->measurementFrame[0][2];
  tfx->mframe[7] = vol->measurementFrame[1][2];
  tfx->mframe[8] = vol->measurementFrame[2][2];
  if (ELL_3M_EXISTS(tfx->mframe)) {
    tfx->mframeUse = AIR_TRUE;
    ELL_3M_TRANSPOSE(tfx->mframeT, tfx->mframe);
  } else {
    tfx->mframeUse = AIR_FALSE;
  }

  tfx->gageAnisoStop = NULL;
  tfx->gageAnisoSpeed = NULL;
  tfx->ten2AnisoStop = AIR_NAN;
  /* ... don't really see the point of initializing the ten2 stuff here;
     its properly done in tenFiberTraceSet() ... */
  tfx->radius = AIR_NAN;

  return tfx;
}