File BenchmarksContainer.cpp
File List > benchmark > BenchmarksContainer.cpp
Go to the documentation of this file
#include "BenchmarksContainer.h"
BenchmarksContainer::BenchmarksContainer(std::filesystem::path objFolder, std::filesystem::path outputFolderPath) : outputFolderPath(outputFolderPath){
for (const auto& entry : std::filesystem::directory_iterator(objFolder))
{
auto ext = entry.path().extension();
if (ext == ".obj" || ext == ".ply")
{
inputFilesPaths.push_back(entry.path());
}
}
}
void BenchmarksContainer::addBenchmark(std::string benchName, std::shared_ptr<ISurfaceReconstructor> reconstructor, const std::vector<std::shared_ptr<Metric>>& metrics) {
auto runner = [this, reconstructor, metrics, benchName](benchmark::State& state) {
reconstructionBenchmark(state, *reconstructor, metrics, benchName);
};
pipelines.push_back(Pipeline{benchName, runner });
}
void BenchmarksContainer::run(benchmark::BenchmarkReporter* reporter, std::shared_ptr<ISurfaceSampler> sampler) {
ObjSerializer obj_serializer;
PlySerializer ply_serializer;
std::vector<Vector3D<double>> vertices;
std::vector<Face> faces;
for (size_t i = 0; i < inputFilesPaths.size(); ++i)
{
benchmark::ClearRegisteredBenchmarks();
faces.clear();
vertices.clear();
std::ifstream inputfile(inputFilesPaths[i]);
if (inputFilesPaths[i].extension() == ".obj")
{
obj_serializer.deserialize(vertices, faces, inputfile);
}
else if (inputFilesPaths[i].extension() == ".ply")
{
ply_serializer.deserialize(vertices, faces, inputfile);
}
inputfile.close();
originalMesh = Mesh(vertices, faces);
if (faces.empty())
{
// input file = nuage de points
cloud = PointCloud(vertices);
std::cout << "IF = cloud : vertices = "<< vertices.size() << std::endl;
std::cout << "IF = cloud : faces = " << faces.size() << std::endl;
std::cout << "IF = cloud : cloud = " << cloud.size() << std::endl;
}
else
{
// input file = maillage
cloud = sampler->sample(originalMesh);
}
auto filename = inputFilesPaths[i].stem().string();
std::filesystem::path pointcloudOutputPath = outputFolderPath / ("Cloud_" + filename + ".obj");
std::ofstream pointcloudOutput(pointcloudOutputPath);
std::vector<Face> empty;
obj_serializer.serialize(
cloud.getPoints(),
empty,
pointcloudOutput
);
pointcloudOutput.close();
std::cout << "Lancement des benchmarks sur le fichier :\n -" << inputFilesPaths[i].filename() << std::endl;
for (const auto& pipeline : pipelines)
{
benchmark::RegisterBenchmark(
(pipeline.name + "_" + inputFilesPaths[i].filename().string()).c_str(),
pipeline.runner
)->Arg(i)->Iterations(10);
}
benchmark::RunSpecifiedBenchmarks(reporter);
}
}
void BenchmarksContainer::reconstructionBenchmark(benchmark::State& state, ISurfaceReconstructor& reconstructor, const std::vector<std::shared_ptr<Metric>>& metrics, const std::string& pipelineName) {
state.counters["NbPointsObject"] = cloud.getPoints().size();
std::ifstream inputfile(inputFilesPaths[state.range(0)]);
ObjSerializer serializer;
std::vector<double> texturesCoord;
if (!inputfile)
{
std::cerr << "reconstructionBenchmark : Error while opening the file : " << inputFilesPaths[state.range(0)].string() << std::endl;
return;
}
bool saved = false;
MemoryPeak memory;
std::vector<double> metricsResults(metrics.size(), 0.0);
for (auto _ : state)
{
state.PauseTiming();
if (cloud.getPoints().size() < 5 && dynamic_cast<PoissonSurface*>(&reconstructor)) {
state.SkipWithMessage("Nombre de points insuffisants (<5) pour l'algorithme de Poisson, passage au prochain algorithme...");
break;
}
memory.start();
state.ResumeTiming();
Mesh reconstructed = reconstructor.reconstruct(cloud);
memory.stop();
benchmark::DoNotOptimize(cloud);
benchmark::DoNotOptimize(reconstructed);
state.PauseTiming();
if (reconstructed.vertexCount() == 0) {
state.SkipWithMessage("La reconstruction est vide, passage au prochain algorithme...");
break;
}
if (!saved) {
memory.compute(originalMesh, reconstructed, state);
for (size_t i = 0; i < metrics.size(); ++i) {
if (metrics[i]->getName() == "Heatmap") {
reconstructed = VertexToFace::addMidEdgeVertices(reconstructed);
texturesCoord = VertexToFace::compute(originalMesh, reconstructed);
}
metrics[i]->compute(originalMesh, reconstructed, state);
}
auto filename = inputFilesPaths[state.range(0)].stem().string();
std::filesystem::path reconstructedOutputPath = outputFolderPath / (pipelineName + "_Mesh_" + filename + ".obj");
std::ofstream reconstructedOutput(reconstructedOutputPath);
serializer.serialize(
reconstructed.getVertices(),
reconstructed.getFaces(),
texturesCoord,
reconstructedOutput
);
saved = true;
}
state.ResumeTiming();
}
}