Exemplo n.º 1
0
void Foam::pamgPolicy::calcChild()
{
    // Algorithm:
    // 1) Create temporary equation addressing using a double-pass algorithm.
    //    to create the offset table.
    // 2) Loop through all equations and for each equation find the best fit
    //    neighbour.  If all neighbours are grouped, add equation to best group

    // Get addressing
    const label nEqns = matrix_.lduAddr().size();

    const unallocLabelList& upperAddr = matrix_.lduAddr().upperAddr();
    const unallocLabelList& lowerAddr = matrix_.lduAddr().lowerAddr();

    // Get off-diagonal matrix coefficients
    const scalarField& upper = matrix_.upper();

    // For each equation calculate coeffs
    labelList cols(upperAddr.size() + lowerAddr.size());
    labelList rowOffsets(nEqns + 1);

    // Memory management
    {
        labelList nNbrs(nEqns, 0);

        forAll (upperAddr, coeffI)
        {
            nNbrs[upperAddr[coeffI]]++;
        }

        forAll (lowerAddr, coeffI)
        {
            nNbrs[lowerAddr[coeffI]]++;
        }

        rowOffsets[0] = 0;

        forAll (nNbrs, eqnI)
        {
            rowOffsets[eqnI + 1] = rowOffsets[eqnI] + nNbrs[eqnI];
        }

        // Reset the list to use as counter
        nNbrs = 0;

        forAll (upperAddr, coeffI)
        {
            cols
            [
                rowOffsets[upperAddr[coeffI]] + nNbrs[upperAddr[coeffI]]
            ] = coeffI;

            nNbrs[upperAddr[coeffI]]++;
        }
Foam::tmp<Foam::labelField> Foam::pairGAMGAgglomeration::agglomerate
(
    label& nCoarseCells,
    const lduAddressing& fineMatrixAddressing,
    const scalarField& faceWeights
)
{
    const label nFineCells = fineMatrixAddressing.size();

    const labelUList& upperAddr = fineMatrixAddressing.upperAddr();
    const labelUList& lowerAddr = fineMatrixAddressing.lowerAddr();

    // For each cell calculate faces
    labelList cellFaces(upperAddr.size() + lowerAddr.size());
    labelList cellFaceOffsets(nFineCells + 1);

    // memory management
    {
        labelList nNbrs(nFineCells, 0);

        forAll(upperAddr, facei)
        {
            nNbrs[upperAddr[facei]]++;
        }

        forAll(lowerAddr, facei)
        {
            nNbrs[lowerAddr[facei]]++;
        }

        cellFaceOffsets[0] = 0;
        forAll(nNbrs, celli)
        {
            cellFaceOffsets[celli+1] = cellFaceOffsets[celli] + nNbrs[celli];
        }

        // reset the whole list to use as counter
        nNbrs = 0;

        forAll(upperAddr, facei)
        {
            cellFaces
            [
                cellFaceOffsets[upperAddr[facei]] + nNbrs[upperAddr[facei]]
            ] = facei;

            nNbrs[upperAddr[facei]]++;
        }
void Foam::MGridGenGAMGAgglomeration::
makeCompactCellFaceAddressingAndFaceWeights
(
    const lduAddressing& fineAddressing,
    List<idxtype>& cellCells,
    List<idxtype>& cellCellOffsets,
    const scalarField& magSi,
    List<scalar>& faceWeights
)
{
    const label nFineCells = fineAddressing.size();
    const label nFineFaces = fineAddressing.upperAddr().size();

    const labelUList& upperAddr = fineAddressing.upperAddr();
    const labelUList& lowerAddr = fineAddressing.lowerAddr();

    // Number of neighbours for each cell
    labelList nNbrs(nFineCells, 0);

    forAll(upperAddr, facei)
    {
        nNbrs[upperAddr[facei]]++;
    }

    forAll(lowerAddr, facei)
    {
        nNbrs[lowerAddr[facei]]++;
    }

    // Set the sizes of the addressing and faceWeights arrays
    cellCellOffsets.setSize(nFineCells + 1);
    cellCells.setSize(2*nFineFaces);
    faceWeights.setSize(2*nFineFaces);


    cellCellOffsets[0] = 0;
    forAll(nNbrs, celli)
    {
        cellCellOffsets[celli+1] = cellCellOffsets[celli] + nNbrs[celli];
    }
Foam::labelListList Foam::GAMGProcAgglomeration::globalCellCells
(
    const lduMesh& mesh
)
{
    const lduAddressing& addr = mesh.lduAddr();
    lduInterfacePtrsList interfaces = mesh.interfaces();

    const label myProcID = Pstream::myProcNo(mesh.comm());

    globalIndex globalNumbering
    (
        addr.size(),
        Pstream::msgType(),
        mesh.comm(),
        Pstream::parRun()
    );

    labelList globalIndices
    (
        identity
        (
            globalNumbering.localSize(myProcID),
            globalNumbering.localStart(myProcID)
        )
    );

    // Get the interface cells
    PtrList<labelList> nbrGlobalCells(interfaces.size());
    {
        // Initialise transfer of restrict addressing on the interface
        forAll(interfaces, inti)
        {
            if (interfaces.set(inti))
            {
                interfaces[inti].initInternalFieldTransfer
                (
                    Pstream::commsTypes::nonBlocking,
                    globalIndices
                );
            }
        }

        if (Pstream::parRun())
        {
            Pstream::waitRequests();
        }

        forAll(interfaces, inti)
        {
            if (interfaces.set(inti))
            {
                nbrGlobalCells.set
                (
                    inti,
                    new labelList
                    (
                        interfaces[inti].internalFieldTransfer
                        (
                            Pstream::commsTypes::nonBlocking,
                            globalIndices
                        )
                    )
                );
            }
        }
    }


    // Scan the neighbour list to find out how many times the cell
    // appears as a neighbour of the face. Done this way to avoid guessing
    // and resizing list
    labelList nNbrs(addr.size(), 1);

    const labelUList& nbr = addr.upperAddr();
    const labelUList& own = addr.lowerAddr();

    {
        forAll(nbr, facei)
        {
            nNbrs[nbr[facei]]++;
            nNbrs[own[facei]]++;
        }

        forAll(interfaces, inti)
        {
            if (interfaces.set(inti))
            {
                const labelUList& faceCells = interfaces[inti].faceCells();

                forAll(faceCells, i)
                {
                    nNbrs[faceCells[i]]++;
                }
            }
        }
    }
Exemplo n.º 5
0
double getTPSAAtomContribs(const ROMol &mol, std::vector<double> &Vi,
                           bool force) {
  TEST_ASSERT(Vi.size() >= mol.getNumAtoms());
  double res = 0;
  if (!force && mol.hasProp(common_properties::_tpsaAtomContribs)) {
    mol.getProp(common_properties::_tpsaAtomContribs, Vi);
    mol.getProp(common_properties::_tpsa, res);
    return res;
  }
  unsigned int nAtoms = mol.getNumAtoms();
  std::vector<int> nNbrs(nAtoms, 0), nSing(nAtoms, 0), nDoub(nAtoms, 0),
      nTrip(nAtoms, 0), nArom(nAtoms, 0), nHs(nAtoms, 0);
  for (ROMol::ConstBondIterator bIt = mol.beginBonds(); bIt != mol.endBonds();
       ++bIt) {
    const Bond *bnd = (*bIt);
    if (bnd->getBeginAtom()->getAtomicNum() == 1) {
      nNbrs[bnd->getEndAtomIdx()] -= 1;
      nHs[bnd->getEndAtomIdx()] += 1;
    } else if (bnd->getEndAtom()->getAtomicNum() == 1) {
      nNbrs[bnd->getBeginAtomIdx()] -= 1;
      nHs[bnd->getBeginAtomIdx()] += 1;
    } else if (bnd->getIsAromatic()) {
      nArom[bnd->getBeginAtomIdx()] += 1;
      nArom[bnd->getEndAtomIdx()] += 1;
    } else {
      switch (bnd->getBondType()) {
        case Bond::SINGLE:
          nSing[bnd->getBeginAtomIdx()] += 1;
          nSing[bnd->getEndAtomIdx()] += 1;
          break;
        case Bond::DOUBLE:
          nDoub[bnd->getBeginAtomIdx()] += 1;
          nDoub[bnd->getEndAtomIdx()] += 1;
          break;
        case Bond::TRIPLE:
          nTrip[bnd->getBeginAtomIdx()] += 1;
          nTrip[bnd->getEndAtomIdx()] += 1;
          break;
        default:
          break;
      }
    }
  }

  for (unsigned int i = 0; i < nAtoms; ++i) {
    const Atom *atom = mol.getAtomWithIdx(i);
    int atNum = atom->getAtomicNum();
    if (atNum != 7 && atNum != 8) continue;
    nHs[i] += atom->getTotalNumHs();
    int chg = atom->getFormalCharge();
    bool in3Ring = mol.getRingInfo()->isAtomInRingOfSize(i, 3);
    nNbrs[i] += atom->getDegree();

    double tmp = -1;
    if (atNum == 7) {
      switch (nNbrs[i]) {
        case 1:
          if (nHs[i] == 0 && chg == 0 && nTrip[i] == 1)
            tmp = 23.79;
          else if (nHs[i] == 1 && chg == 0 && nDoub[i] == 1)
            tmp = 23.85;
          else if (nHs[i] == 2 && chg == 0 && nSing[i] == 1)
            tmp = 26.02;
          else if (nHs[i] == 2 && chg == 1 && nDoub[i] == 1)
            tmp = 25.59;
          else if (nHs[i] == 3 && chg == 1 && nSing[i] == 1)
            tmp = 27.64;
          break;
        case 2:
          if (nHs[i] == 0 && chg == 0 && nSing[i] == 1 && nDoub[i] == 1)
            tmp = 12.36;
          else if (nHs[i] == 0 && chg == 0 && nTrip[i] == 1 && nDoub[i] == 1)
            tmp = 13.60;
          else if (nHs[i] == 1 && chg == 0 && nSing[i] == 2 && in3Ring)
            tmp = 21.94;
          else if (nHs[i] == 1 && chg == 0 && nSing[i] == 2 && !in3Ring)
            tmp = 12.03;
          else if (nHs[i] == 0 && chg == 1 && nTrip[i] == 1 && nSing[i] == 1)
            tmp = 4.36;
          else if (nHs[i] == 1 && chg == 1 && nDoub[i] == 1 && nSing[i] == 1)
            tmp = 13.97;
          else if (nHs[i] == 2 && chg == 1 && nSing[i] == 2)
            tmp = 16.61;
          else if (nHs[i] == 0 && chg == 0 && nArom[i] == 2)
            tmp = 12.89;
          else if (nHs[i] == 1 && chg == 0 && nArom[i] == 2)
            tmp = 15.79;
          else if (nHs[i] == 1 && chg == 1 && nArom[i] == 2)
            tmp = 14.14;
          break;
        case 3:
          if (nHs[i] == 0 && chg == 0 && nSing[i] == 3 && in3Ring)
            tmp = 3.01;
          else if (nHs[i] == 0 && chg == 0 && nSing[i] == 3 && !in3Ring)
            tmp = 3.24;

          else if (nHs[i] == 0 && chg == 0 && nSing[i] == 1 && nDoub[i] == 2)
            tmp = 11.68;
          else if (nHs[i] == 0 && chg == 1 && nSing[i] == 2 && nDoub[i] == 1)
            tmp = 3.01;
          else if (nHs[i] == 1 && chg == 1 && nSing[i] == 3)
            tmp = 4.44;
          else if (nHs[i] == 0 && chg == 0 && nArom[i] == 3)
            tmp = 4.41;
          else if (nHs[i] == 0 && chg == 0 && nSing[i] == 1 && nArom[i] == 2)
            tmp = 4.93;
          else if (nHs[i] == 0 && chg == 0 && nDoub[i] == 1 && nArom[i] == 2)
            tmp = 8.39;
          else if (nHs[i] == 0 && chg == 1 && nArom[i] == 3)
            tmp = 4.10;
          else if (nHs[i] == 0 && chg == 1 && nSing[i] == 1 && nArom[i] == 2)
            tmp = 3.88;
          break;
        case 4:
          if (nHs[i] == 0 && nSing[i] == 4 && chg == 1) tmp = 0.0;
          break;
      }
      if (tmp < 0.0) {
        tmp = 30.5 - nNbrs[i] * 8.2 + nHs[i] * 1.5;
        if (tmp < 0) tmp = 0.0;
      }
    } else if (atNum == 8) {
      switch (nNbrs[i]) {
        case 1:
          if (nHs[i] == 0 && chg == 0 && nDoub[i] == 1)
            tmp = 17.07;
          else if (nHs[i] == 1 && chg == 0 && nSing[i] == 1)
            tmp = 20.23;
          else if (nHs[i] == 0 && chg == -1 && nSing[i] == 1)
            tmp = 23.06;
          break;
        case 2:
          if (nHs[i] == 0 && chg == 0 && nSing[i] == 2 && in3Ring)
            tmp = 12.53;
          else if (nHs[i] == 0 && chg == 0 && nSing[i] == 2 && !in3Ring)
            tmp = 9.23;
          else if (nHs[i] == 0 && chg == 0 && nArom[i] == 2)
            tmp = 13.14;
          break;
      }
      if (tmp < 0.0) {
        tmp = 28.5 - nNbrs[i] * 8.6 + nHs[i] * 1.5;
        if (tmp < 0) tmp = 0.0;
      }
    }
    Vi[i] = tmp;
    res += tmp;
  }

  mol.setProp(common_properties::_tpsaAtomContribs, Vi, true);
  mol.setProp(common_properties::_tpsa, res, true);
  return res;
}