Commit 35c0ced8 authored by Quentin Khan's avatar Quentin Khan

First balance commit

parent 8f41770a
#ifndef _COSTZONES_HPP_
#define _COSTZONES_HPP_
template<typename OctreeClass, typename CellClass>
class CostZones {
unsigned long long _currentCost = 0;
unsigned long long _totalCost = 0;
std::vector< std::pair< int, CellClass*> > _emptyzone;
std::vector< std::vector< std::pair<int, CellClass*> > > _zones;
typename OctreeClass::Iterator _it;
int _nbZones;
enum ChildrenSide {LEFT, RIGHT};
public:
CostZones(OctreeClass* tree, int nbZones) :
_zones(1, _emptyzone),
_it(tree),
_nbZones(nbZones)
{}
std::vector< std::vector< std::pair<int, CellClass*> > >& getZones() {return _zones;}
void run() {
_totalCost = 0;
int nbRootChildren = 0;
// Compute tree total cost;
_it.gotoBottomLeft();
do {
_it.gotoLeft();
nbRootChildren = 0; // waste of ressources only toplevel _iteration is kept
do {
_totalCost += _it.getCurrentCell()->getCost();
nbRootChildren++;
} while(_it.moveRight());
} while(_it.moveUp());
_it.gotoLeft();
// Compute costzones, we have to do the first level manualy
for ( int i = 0; i < nbRootChildren; i++ ) {
costzones();
_it.moveRight();
}
}
private:
/**
* Counts the children to the left and to the right of the cell currently
* pointed to by the iterator _it. You must check by yourself whether the
* cell is a leaf or not.
*/
void countLeftRightChildren(int& nbLeftChildren, int& nbRightChildren) {
FCostCell** children = _it.getCurrentChildren();
// Left children
for ( int childIdx = 0; childIdx < 4; childIdx++) {
if ( children[childIdx] ) {
++ nbLeftChildren;
}
}
// Right children
for ( int childIdx = 4; childIdx < 8; childIdx++) {
if ( children[childIdx] ) {
++ nbRightChildren;
}
}
}
void callCostZonesOnChildren(ChildrenSide side, int nbLeftChildren, int nbRightChildren) {
int startIdx = (side == LEFT ? 0 : 4);
int endIdx = (side == LEFT ? 4 : 8);
int nbChildren = (side == LEFT ? nbLeftChildren : nbRightChildren);
_it.moveDown();
// move to the first right child
if ( side == RIGHT ) {
if ( nbRightChildren == 0)
return;
}
_it.moveUp();
}
void costzones() {
// Current position is a leaf
CellClass* cell = _it.getCurrentCell();
if (cell->_visited) {
std::cerr << "Error : cell revisited..." << _it.level()
<< ": " << cell->getCoordinate() << std::endl;
return;
}
else
cell->_visited = true;
int cellCost = cell->getCost();
int nbLeftChildren = 0;
int nbRightChildren = 0;
#if 0
std::cout << "lvl " << std::setw(2) << _it.level() << " |"
<< "cellidx " << std::setw(4)
<< cell->getMortonIndex() << " : "
<< cell->getCoordinate() << " "
<< ( _it.canProgressToDown() ? "internal" : "leaf") << " "
<< std::endl;
#endif
// When not on a leaf, apply to left children first
if ( _it.canProgressToDown() ) {
FCostCell** children = _it.getCurrentChildren();
// Count left children
for ( int childIdx = 0; childIdx < 4; childIdx++) {
if ( children[childIdx] ) {
++ nbLeftChildren;
}
}
_it.moveDown();
// Apply costzones to left children
for ( int childIdx = 0; childIdx < nbLeftChildren; childIdx++ ) {
costzones();
// avoid changing tree
if(childIdx < nbLeftChildren -1)
_it.moveRight();
}
_it.moveUp();
}
if ( cellCost != 0) {
// Add the current cell
if ( _currentCost + cellCost < _zones.size() * _totalCost / _nbZones + 1 ) {
_currentCost += cellCost;
_zones.back().push_back({_it.level(), cell});
} else {
_zones.push_back(std::vector< std::pair<int, CellClass*> >(1, {_it.level(), cell}));
}
}
// When not on a leaf, apply to right children
if ( _it.canProgressToDown() ) {
FCostCell** children = _it.getCurrentChildren();
// Count right children
for ( int childIdx = 4; childIdx < 8; childIdx++) {
if ( children[childIdx] ) {
++ nbRightChildren;
}
}
if ( nbRightChildren == 0)
return;
// Move to the first right child
_it.moveDown();
for ( int childIdx = 0; childIdx < nbLeftChildren; childIdx++) {
_it.moveRight();
}
// Apply costzones to the right children
for ( int childIdx = 0; childIdx < nbRightChildren; childIdx++) {
costzones();
// avoid changing tree
if(childIdx < nbRightChildren -1)
_it.moveRight();
}
_it.moveUp();
}
}
};
#endif
This diff is collapsed.
This diff is collapsed.
#include <fstream>
#include <memory>
#include <string>
#include <sys/ioctl.h>
#include "Utils/FMath.hpp"
#include "Utils/FParameters.hpp"
#include "Utils/FParameterNames.hpp"
#include "Files/FFmaGenericLoader.hpp"
#include "Core/FFmmAlgorithm.hpp"
#include "Containers/FOctree.hpp"
#include "Components/FBasicCell.hpp"
#include "Components/FSimpleLeaf.hpp"
#include "Components/FBasicParticleContainer.hpp"
#include "Kernels/P2P/FP2PParticleContainerIndexed.hpp"
#include "FChebBalanceSymKernel.hpp"
#include "loadFMAAndRunFMMArgs.hpp"
#include "CostZones.hpp"
typedef FCostCell CellClass;
typedef FBasicParticleContainer<0> ContainerClass;
typedef FSimpleLeaf< ContainerClass > LeafClass;
typedef FOctree< CellClass, ContainerClass, LeafClass > OctreeClass;
typedef FInterpMatrixKernelR MatrixKernelClass;
typedef FChebBalanceSymKernel<CellClass,
ContainerClass,
MatrixKernelClass,
5,
OctreeClass> KernelClass;
const FReal epsilon = 1e-4;
int main(int argc, char** argv)
{
loadFMAAndRunFMMArgs args(argc, argv);
FFmaGenericLoader loader(args.inFileName().c_str());
OctreeClass tree(args.treeHeight(),
args.subTreeHeight(),
loader.getBoxWidth(),
loader.getCenterOfBox());
FReal physicalValue;
FPoint particlePosition;
// insertion
for ( int idxPart = 0 ; idxPart < loader.getNumberOfParticles() ; ++idxPart ) {
loader.fillParticle(&particlePosition, &physicalValue);
tree.insert(particlePosition);
}
KernelClass kernel(&tree, epsilon);
FFmmAlgorithm<OctreeClass, CellClass, ContainerClass, KernelClass, LeafClass >
algo(&tree, &kernel);
algo.execute();
kernel.printResults(std::cout);
OctreeClass::Iterator it(&tree);
CostZones<OctreeClass, CellClass> costzones(&tree, args.zoneCount());
costzones.run();
auto zones = costzones.getZones();
// GCC versions before 5.0 have not implemented move constructors to streams
std::vector<std::unique_ptr<std::ofstream>> outfiles;
for ( int i = 0; i < args.treeHeight(); i++ ) {
std::unique_ptr<std::ofstream> out(
new std::ofstream( args.outFileName()
+ "_"
+ std::to_string(args.zoneCount())
+ "z"
+ "."
+ std::to_string(i)
+ args.outFileExt()));
*out << "x,y,z,zone" << std::endl;
outfiles.push_back(std::move(out));
}
int zoneIdx = 0;
for ( auto zone : zones) {
for ( auto cell : zone) {
*(outfiles[cell.first]) << cell.second->getCoordinate().getX() << ",";
*(outfiles[cell.first]) << cell.second->getCoordinate().getY() << ",";
*(outfiles[cell.first]) << cell.second->getCoordinate().getZ() << ",";
*(outfiles[cell.first]) << zoneIdx << "," << cell.first << std::endl;
}
zoneIdx++;
}
return EXIT_SUCCESS;
}
#ifndef _LOADFMAANDRUNFMMARGS_HPP_
#define _LOADFMAANDRUNFMMARGS_HPP_
#include "tclap++11/CmdLine.h"
#include "tclap++11/LinuxOutput.hpp"
#include "tclap++11/CompletionVisitor.h"
class loadFMAAndRunFMMArgs {
using vs = std::vector<std::string>;
const int _treeHeightInit = 5;
const int _subTreeHeightInit = 1;
const int _zoneCountInit = 4;
const std::string _inFileNameInit = "";
const std::string _outFileNameInit = "balancetest";
const std::string _outFileNameExtInit = "csv";
TCLAP::CmdLine
_cmd { "Loads an FMA file into a tree and runs a pseudo FMM algorithm "
"through it to compute load balancing.", ' ', "0.0"};
TCLAP::LinuxOutput _cmdFormat;
TCLAP::BashCompletion::Visitor _compVistor;
TCLAP::SwitchArg
_compArg { "",
"completion",
"Show completion arguments",
_cmd, false, &_compVistor};
TCLAP::ValueArg <int>
_subTreeHeight { "", vs{"subtree-height", "sth"},
"Subtree height.", false, _subTreeHeightInit, "sub-tree height", _cmd};
TCLAP::ValueArg <int>
_treeHeight { "H", vs{"tree-height", "th"},
"Tree height.", true, _treeHeightInit, "tree height", _cmd};
TCLAP::ValueArg <int>
_zoneCount { "z", vs{"zone-count"},
"Number of zones to create", true, _zoneCountInit, "zone count", _cmd};
TCLAP::ValueArg <std::string>
_outFileExt { "x", "output-file-extension",
"Output files extension. One file is created for each level in the"
" tree. Each file has a 'basename.$i.extension' extension where $i"
" is the level. Default value is " + _outFileNameExtInit + ".",
false, _outFileNameExtInit, "suffix", _cmd};
TCLAP::ValueArg <std::string>
_outFileName { "o", "output-file-basename",
"Output files' basename. One file is created for each level in "
"the tree. Each file has a level-in-tree based extension.",
false, _outFileNameInit, "basename", _cmd};
TCLAP::ValueArg <std::string>
_inFileName { "f", "input-file",
"Input file name.", true, _inFileNameInit, "filename", _cmd};
public:
int treeHeight() {return _treeHeight.getValue();}
int subTreeHeight() {return _subTreeHeight.getValue();}
int zoneCount() {return _zoneCount.getValue();}
std::string inFileName() {return _inFileName.getValue();}
std::string outFileName() {return _outFileName.getValue();}
std::string outFileExt() {
std::string ext = _outFileExt.getValue();
if ( ext.at(0) != '.' )
return '.' + ext;
return ext;
}
loadFMAAndRunFMMArgs(int argc, char** argv)
: _compVistor(argc, argv, &_cmd, {
{ &_inFileName,{TCLAP::BashCompletion::FILE, "!*.fma" }},
{&_outFileExt, {"csv"}}}
){
int columns = 80;
struct winsize w;
if (ioctl(0, TIOCGWINSZ, &w) == 0)
columns = w.ws_col;
_compArg.setHideDesc(true);
_cmdFormat.setTextWidth(columns);
_cmd.setOutput(&_cmdFormat);
_cmd.parse(argc,argv);
}
};
#endif
from paraview import *
reader = GetActiveSource()
# SVReader(DetectNumericColumns = True, FieldDelimiterCharacters = ",", HaveHeaders = True, FileName = "/home/qkhan/work/scalfmm/Build/20k10z.4.csv")
#classRef = CSVReader()
#if not isinstance(reader, classRef.__class__):
# exit(-1)
filename = reader.FileName[0]
print filename
nbZones = int(filename.split('.')[0].split('_')[-1][0:-1])
selection = SelectionQuerySource(FieldType = "ROW", QueryString = "zone >= 0")
extractor = ExtractSelection(Input = reader, Selection = selection)
points = TableToPoints(Input = extractor, XColumn = "x", YColumn = "y", ZColumn = "z")
repr = GetRepresentation()
repr.ColorArrayName = 'zone'
repr.LookupTable = AssignLookupTable(points.PointData['zone'], "Cool to Warm")
Show()
#for i in range(nbZones):
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment