コード例 #1
0
/* This function runs the AC noise analysis.  It saves its results in
   the 'xn' vector. */
void acsolver::solve_noise (void) {
  int N = countNodes ();
  int M = countVoltageSources ();

  // save usual AC results
  tvector<nr_complex_t> xsave = *x;

  // create the Cy matrix
  createNoiseMatrix ();
  // create noise result vector if necessary
  if (xn == NULL) xn = new tvector<nr_double_t> (N + M);

  // temporary result vector for transimpedances
  tvector<nr_complex_t> zn = tvector<nr_complex_t> (N + M);

  // create the MNA matrix once again and LU decompose the adjoint matrix
  createMatrix ();
  A->transpose ();
  eqnAlgo = ALGO_LU_FACTORIZATION_CROUT;
  runMNA ();

  // ensure skipping LU decomposition
  updateMatrix = 0;
  convHelper = CONV_None;
  eqnAlgo = ALGO_LU_SUBSTITUTION_CROUT;

  // compute noise voltage for each node (and voltage source)
  for (int i = 0; i < N + M; i++) {
    z->set (0); z->set (i, -1); // modify right hand side appropriately
    runMNA ();                  // solve
    zn = *x;                    // save transimpedance vector

    // compute actual noise voltage
    xn->set (i, sqrt (real (scalar (zn * (*C), conj (zn)))));
  }

  // restore usual AC results
  *x = xsave;
}
コード例 #2
0
ファイル: nasolver.cpp プロジェクト: NextGenIntelligence/qucs
int nasolver<nr_type_t>::solve_once (void)
{
    qucs::exception * e;
    int error = 0, d;

    // run the calculation function for each circuit
    calculate ();

    // generate A matrix and z vector
    createMatrix ();

    // solve equation system
    try_running ()
    {
        runMNA ();
    }
    // appropriate exception handling
    catch_exception ()
    {
    case EXCEPTION_PIVOT:
    case EXCEPTION_WRONG_VOLTAGE:
        e = new qucs::exception (EXCEPTION_NA_FAILED);
        d = top_exception()->getData ();
        pop_exception ();
        if (d >= countNodes ())
        {
            d -= countNodes ();
            e->setText ("voltage source `%s' conflicts with some other voltage "
                        "source", findVoltageSource(d)->getName ());
        }
        else
        {
            e->setText ("circuit admittance matrix in %s solver is singular at "
                        "node `%s' connected to [%s]", desc.c_str(), nlist->get (d).c_str(),
                        nlist->getNodeString (d).c_str());
        }
        throw_exception (e);
        error++;
        break;
    case EXCEPTION_SINGULAR:
        do
        {
            d = top_exception()->getData ();
            pop_exception ();
            if (d < countNodes ())
            {
                logprint (LOG_ERROR, "WARNING: %s: inserted virtual resistance at "
                          "node `%s' connected to [%s]\n", getName (), nlist->get (d).c_str(),
                          nlist->getNodeString (d).c_str());
            }
        }
        while (top_exception() != NULL &&
                top_exception()->getCode () == EXCEPTION_SINGULAR);
        break;
    default:
        estack.print ();
        break;
    }

    // save results into circuits
    if (!error) saveSolution ();
    return error;
}