CoarseAverage
is defined on two levels of BoxLayout<\code>, the fine and the
* coarse. A CoarseAverage
object is used to average a BoxLayoutData<\code>
* defined at the fine level to one defined at the coarse level. This algorithm only works on
* BoxLayoutData<\code>s with BoxedArray
components.
* Given a BoxLayoutData<\code> at the fine level, this algorithm first averages it to
* its coarsened version defined at the coarse level, then copies the coarsened version to any
* BoxLayoutData<\code> defined at same level. A copier should be used to cache the copy
* relation between the two levels (which has not beenimplemented yet).
* Please refer to the Chombo design document for the details of this algorithm.
* Usage: a CoarseAverage
object must be declared local.
* @see BoxTools.BoxLayout, BoxTools.BoxLayoutData, BoxTools.LayoutIterator, BoxTools.BoxedArray
* and BoxTools.DataIndex.
* @see Chombo Specification
* @version 1.1
* Modified on Jul 09, 2004. change of syntax of foreach, see BoxTools/foreachLoopTest.ti.
* @author Tong Wen, LBNL
* @since 1.0
*/
template public class CoarseAverage{
private int single m_refRatio=1;
//private int single m_nComp;
private static final int SPACE_DIM=BoxTools.Util.SPACE_DIM;
public template BoxLayoutData > local single m_fineData_c;
private BoxLayout single local m_fineLayout_c;
private BoxLayout single local m_fineLayout;
private double m_denominator=1;
private LayoutIterator local m_fineLayoutItr;
private RectDomain m_localRegion;
private template Copier > local single m_copier;
private boolean single m_copierConstructed=false;
Timer tmr=new Timer();
public CoarseAverage(){}
public CoarseAverage(BoxLayout single local a_fineLayout, int single a_refRatio){
define(a_fineLayout, a_refRatio);
}
public final local void define(BoxLayout single local a_fineLayout, int single a_refRatio){
m_refRatio=a_refRatio;
m_fineLayout=a_fineLayout;
m_fineLayout_c=a_fineLayout.coarsen(a_refRatio);
m_fineLayoutItr=new LayoutIterator(a_fineLayout);
m_fineData_c=new template BoxLayoutData >(m_fineLayout_c,0);
m_denominator=m_refRatio;
for (int i=1;i.all(0):Point.all(m_refRatio-1)];
else
m_localRegion=[Point.all(0):Point.all(m_refRatio-1):m_fineLayoutItr.Access().stride()];
m_fineLayoutItr.Reset();
}
final local void averageToCoarse(template BoxLayoutData > local single a_fineData){
DataIndex local DI;
T [SPACE_DIM d] local TiArray_c, TiArray_f;
T sum;
//Point point, point_c, point_f; /* for change in the syntax of foreach */
Point point_f;
m_fineLayoutItr.reset();
int i=0;
while (!m_fineLayoutItr.isEnded()){
DI=m_fineLayoutItr.getDataIndex();
TiArray_c=m_fineData_c[DI].getLocalArray();
TiArray_f=a_fineData[DI].getLocalArray();
tmr.start();
foreach (point_c in TiArray_c.domain()) {
sum-=sum;
point_f=point_c*m_refRatio;
//foreach (point in m_localRegion) inline sum+=TiArray_f[point_f+point];
foreach (point in m_localRegion) sum+=TiArray_f[point_f+point]; //July 13, 2004
TiArray_c[point_c]=sum/m_denominator;
}
tmr.stop();
m_fineLayoutItr.advance();i++;
}
Util.countCopy+=tmr.millis();tmr.reset();
Util.countNum+=i;
}
public final local void averageToCoarse(template BoxLayoutData > local single a_coarseData, template BoxLayoutData > local single a_fineData){
averageToCoarse(a_coarseData, a_fineData,true);
}
public final local void averageToCoarse(template BoxLayoutData > local single a_coarseData, template BoxLayoutData > local single a_fineData, boolean single a_copierON){
if (m_fineLayout==(BoxLayout single)a_fineData.boxLayout()) {
averageToCoarse(a_fineData);
if (a_copierON){
if (!m_copierConstructed){
m_copier=new template Copier > (a_coarseData.boxLayout(),m_fineLayout_c);
m_copierConstructed=true;
}
m_copier.copy(a_coarseData, m_fineData_c);
}
else
a_coarseData.copy(m_fineData_c, false);
}
else
Util.printErrMsg("CoarseAverage::averageToCoarse(): the layout of fine data is wrong!");
}
/*public final local template BoxLayoutData > local single
averageToLocalCoarse(template BoxLayoutData > local single a_fineData){
if (m_fineLayout==(BoxLayout single)a_fineData.boxLayout()) {
averageToCoarse(a_fineData);
coarseData=new template BoxLayoutData >(m_fineLayout_c,0);
coarseData<<=m_fineData_c;
return coarseData;
}
else{
Util.printErrMsg("CoarseAverage::averageToLocalCoarse(): the layout of fine data is wrong!");
return null;
}
}*/
}