Commit 4d4a65f9 authored by GILLES Sebastien's avatar GILLES Sebastien
Browse files

#531 Make FindIfCondition for numbering subsets more generic.

parent b660aeff
......@@ -272,6 +272,8 @@
BE64623A1AEE1AEF00D5162A /* GlobalVector.hpp in Headers */ = {isa = PBXBuildFile; fileRef = BE6462371AEE1AEF00D5162A /* GlobalVector.hpp */; };
BE64623B1AEE1AEF00D5162A /* GlobalVector.hxx in Headers */ = {isa = PBXBuildFile; fileRef = BE6462381AEE1AEF00D5162A /* GlobalVector.hxx */; };
BE699CFD1AF2539E009CBF44 /* ScalarDivVectorial.cpp in Sources */ = {isa = PBXBuildFile; fileRef = BE699CFA1AF2539E009CBF44 /* ScalarDivVectorial.cpp */; };
BE6AAE6B1AF7590F00D420CB /* NumberingSubset.hpp in Headers */ = {isa = PBXBuildFile; fileRef = BE6AAE681AF7590F00D420CB /* NumberingSubset.hpp */; };
BE6AAE6C1AF7590F00D420CB /* NumberingSubset.hxx in Headers */ = {isa = PBXBuildFile; fileRef = BE6AAE691AF7590F00D420CB /* NumberingSubset.hxx */; };
BE6AE0CB1AE631C6006DF2BA /* VariationalFormulation.cpp in Sources */ = {isa = PBXBuildFile; fileRef = BE6AE0C81AE631C6006DF2BA /* VariationalFormulation.cpp */; };
BE6BE4E31A665A90009AC2F3 /* IOFormat.cpp in Sources */ = {isa = PBXBuildFile; fileRef = BE6BE4E01A665A90009AC2F3 /* IOFormat.cpp */; };
BE6C215F19AF2FDB00CC674B /* libUtilities.a in Frameworks */ = {isa = PBXBuildFile; fileRef = BEA8A379177AD4FE009436C9 /* libUtilities.a */; };
......@@ -2012,6 +2014,8 @@
BE6789B219E6DCBA002CAC33 /* Orientation.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Orientation.hpp; sourceTree = "<group>"; };
BE6789B319E6DCBA002CAC33 /* Orientation.hxx */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Orientation.hxx; sourceTree = "<group>"; };
BE699CFA1AF2539E009CBF44 /* ScalarDivVectorial.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ScalarDivVectorial.cpp; sourceTree = "<group>"; };
BE6AAE681AF7590F00D420CB /* NumberingSubset.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = NumberingSubset.hpp; sourceTree = "<group>"; };
BE6AAE691AF7590F00D420CB /* NumberingSubset.hxx */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = NumberingSubset.hxx; sourceTree = "<group>"; };
BE6AE0C81AE631C6006DF2BA /* VariationalFormulation.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = VariationalFormulation.cpp; sourceTree = "<group>"; };
BE6AE0C91AE631C6006DF2BA /* VariationalFormulation.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = VariationalFormulation.hpp; sourceTree = "<group>"; };
BE6AE0CA1AE631C6006DF2BA /* VariationalFormulation.hxx */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = VariationalFormulation.hxx; sourceTree = "<group>"; };
......@@ -3628,6 +3632,8 @@
BE6462261AEE199900D5162A /* NumberingSubsetManager.cpp */,
BE6462271AEE199900D5162A /* NumberingSubsetManager.hpp */,
BE6462281AEE199900D5162A /* NumberingSubsetManager.hxx */,
BE6AAE681AF7590F00D420CB /* NumberingSubset.hpp */,
BE6AAE691AF7590F00D420CB /* NumberingSubset.hxx */,
);
path = Private;
sourceTree = "<group>";
......@@ -5135,6 +5141,7 @@
BE90DEDE1A24903700CCAFDE /* Fluid.hpp in Headers */,
BE90DED71A24903700CCAFDE /* TransientParameters.hxx in Headers */,
BE90DED81A24903700CCAFDE /* Transient.hpp in Headers */,
BE6AAE6B1AF7590F00D420CB /* NumberingSubset.hpp in Headers */,
BE2E0CCB1ABAFBA800B543E8 /* Mesh.hpp in Headers */,
BE90DED61A24903700CCAFDE /* TransientParameters.hpp in Headers */,
BE4053EB1AC172580024D5F9 /* FEltSpace.hpp in Headers */,
......@@ -5171,6 +5178,7 @@
BE4054201AC1C16A0024D5F9 /* Unknown.hpp in Headers */,
BEF282811A850DEC00857342 /* InitialCondition.hpp in Headers */,
BEDAC3DC1AD8108E00AA2156 /* NumberingSubset.hpp in Headers */,
BE6AAE6C1AF7590F00D420CB /* NumberingSubset.hxx in Headers */,
BE90DEE01A24903700CCAFDE /* Force.hpp in Headers */,
BE40541B1AC1C14D0024D5F9 /* Unknown.hxx in Headers */,
BE42A43B1A5D650E00B3FF6B /* InitTimeKeepLog.hpp in Headers */,
......
......@@ -42,48 +42,5 @@ namespace HappyHeart
}
namespace GlobalMatrixNS
{
bool EqualByNumberingSubset::operator()(const GlobalMatrix& lhs, const GlobalMatrix& rhs) const noexcept
{
return lhs.GetRowNumberingSubset() == rhs.GetRowNumberingSubset()
&& lhs.GetColNumberingSubset() == rhs.GetColNumberingSubset();
}
bool LessByNumberingSubset::operator()(const GlobalMatrix& lhs, const GlobalMatrix& rhs) const noexcept
{
const auto& lhs_row_subset = lhs.GetRowNumberingSubset();
const auto& rhs_row_subset = rhs.GetRowNumberingSubset();
if (lhs_row_subset == rhs_row_subset)
{
return lhs.GetColNumberingSubset() < rhs.GetColNumberingSubset();
}
return lhs_row_subset < rhs_row_subset;
}
FindIfCondition::FindIfCondition(const NumberingSubset& row_numbering_subset,
const NumberingSubset& col_numbering_subset)
: row_numbering_subset_(row_numbering_subset),
col_numbering_subset_(col_numbering_subset)
{ }
bool FindIfCondition::operator()(const GlobalMatrix::unique_ptr& rhs) const noexcept
{
assert(!(!rhs));
return rhs->GetRowNumberingSubset() == row_numbering_subset_
&& rhs->GetColNumberingSubset() == col_numbering_subset_;
}
} // namespace GlobalMatrixNS
} // namespace HappyHeart
......@@ -138,109 +138,6 @@ namespace HappyHeart
*/
using GlobalMatrixWithCoefficient = std::pair<GlobalMatrix&, double>;
namespace GlobalMatrixNS
{
/*!
* \brief Returns true when two GlobalMatrices share the same numbering subsets.
*
* This is intended to be used in containers in which at most one GlobalMatrix with (row_numbering_subset,
* col_numbering_subset) may be found.
*
* It is a struct with a functor for possible use in STL algorithm.
*/
struct EqualByNumberingSubset
{
//! Prototype to compare direcly objects.
bool operator()(const GlobalMatrix& lhs, const GlobalMatrix& rhs) const noexcept;
//! Prototype to compare objects shielded by unique_ptr.
bool operator()(GlobalMatrix::unique_ptr lhs, GlobalMatrix::unique_ptr rhs) const noexcept;
};
/*!
* \brief Yields the unary condition required to find with std::find_if a GlobalMatrix in a list provided
* its numbering subsets are given.
*
* To find the GlobalMatrix in global_matrix_list_ with row_ns and col_ns the syntax is:
*
* \code
* auto it = std::find_if(global_matrix_list_.cbegin(),
* global_matrix_list_.cend(),
* GlobalMatrixNS::FindIfCondition(row_ns, col_ns));
* \endcode
*/
class FindIfCondition
{
public:
//! Constructor.
FindIfCondition(const NumberingSubset& row_numbering_subset,
const NumberingSubset& col_numbering_subset);
//! Destructor.
~FindIfCondition() = default;
//! Copy constructor.
FindIfCondition(const FindIfCondition&) = default; // required by gcc; clang makes do with only move one.
//! Move constructor.
FindIfCondition(FindIfCondition&&) = default;
//! Copy affectation.
FindIfCondition& operator=(const FindIfCondition&) = delete;
//! Move affectation.
FindIfCondition& operator=(FindIfCondition&&) = delete;
//! Prototype to compare objects shielded by unique_ptr.
bool operator()(const GlobalMatrix::unique_ptr& rhs) const noexcept;
private:
//! Numbering subset used to describe rows.
const NumberingSubset& row_numbering_subset_;
//! Numbering subset used to describe columns.
const NumberingSubset& col_numbering_subset_;
};
/*!
* \brief operator< for the numbering subsets.
*
* Row subset are compared first, and in case of equality columns ones are looked at.
*
* This is intended to be used in containers in which at most one GlobalMatrix with (row_numbering_subset,
* col_numbering_subset) may be found.
*
* It is a struct with a functor for possible use in STL algorithm.
*/
struct LessByNumberingSubset
{
//! Prototype to compare direcly objects.
bool operator()(const GlobalMatrix& lhs, const GlobalMatrix& rhs) const noexcept;
};
} // namespace GlobalMatrixNS
} // namespace HappyHeart
......
......@@ -25,25 +25,7 @@ namespace HappyHeart
return col_numbering_subset_;
}
namespace GlobalMatrixNS
{
inline bool EqualByNumberingSubset
::operator()(GlobalMatrix::unique_ptr lhs, GlobalMatrix::unique_ptr rhs) const noexcept
{
assert(!(!lhs));
assert(!(!rhs));
return operator()(*lhs, *rhs);
}
} // namespace GlobalMatrixNS
} // namespace HappyHeart
......
......@@ -33,30 +33,8 @@ namespace HappyHeart
using Parent = GlobalVector::Parent;
Swap(static_cast<Parent&>(A), static_cast<Parent&>(B));
Swap(static_cast<Parent&>(A), static_cast<Parent&>(B));
}
namespace GlobalVectorNS
{
FindIfCondition::FindIfCondition(const NumberingSubset& numbering_subset)
: numbering_subset_(numbering_subset)
{ }
bool FindIfCondition::operator()(const GlobalVector::unique_ptr& rhs) const noexcept
{
assert(!(!rhs));
return rhs->GetNumberingSubset() == numbering_subset_;
}
} // namespace GlobalVectorNS
} // namespace HappyHeart
......@@ -127,62 +127,6 @@ namespace HappyHeart
*/
using GlobalVectorWithCoefficient = std::pair<GlobalVector&, double>;
namespace GlobalVectorNS
{
/*!
* \brief Yields the unary condition required to find with std::find_if a GlobalVector in a list provided
* its numbering subsets are given.
*
* To find the GlobalVector in global_matrix_list_ with numbering subset ns the syntax is:
*
* \code
* auto it = std::find_if(global_matrix_list_.cbegin(),
* global_matrix_list_.cend(),
* GlobalVectorNS::FindIfCondition(ns));
* \endcode
*/
class FindIfCondition
{
public:
//! Constructor.
FindIfCondition(const NumberingSubset& numbering_subset);
//! Destructor.
~FindIfCondition() = default;
//! Copy constructor.
FindIfCondition(const FindIfCondition&) = default; // required by gcc; clang makes do with only move one.
//! Move constructor.
FindIfCondition(FindIfCondition&&) = default;
//! Copy affectation.
FindIfCondition& operator=(const FindIfCondition&) = delete;
//! Move affectation.
FindIfCondition& operator=(FindIfCondition&&) = delete;
//! Prototype to compare objects shielded by unique_ptr.
bool operator()(const GlobalVector::unique_ptr& rhs) const noexcept;
private:
//! Numbering subset used to describe the vector..
const NumberingSubset& numbering_subset_;
};
} // namespace GlobalVectorNS
} // namespace HappyHeart
......
......@@ -14,6 +14,8 @@
# include "Utilities/UniqueId/UniqueId.hpp"
# include "Core/Private/NumberingSubset.hpp"
namespace HappyHeart
{
......@@ -30,6 +32,11 @@ namespace HappyHeart
} // namespace Private
/*!
* \brief Complete!
*
* \todo #9 Explain numbering subset here!
*/
class NumberingSubset : public Crtp::UniqueId<NumberingSubset, UniqueIdNS::AssignationMode::manual>
{
......@@ -68,19 +75,17 @@ namespace HappyHeart
//! Destructor.
~NumberingSubset() = default;
private:
//! Copy constructor.
NumberingSubset(const NumberingSubset&) = default;
NumberingSubset(const NumberingSubset&) = delete;
//! Move constructor.
NumberingSubset(NumberingSubset&&) = default;
NumberingSubset(NumberingSubset&&) = delete;
//! Copy affectation.
NumberingSubset& operator=(const NumberingSubset&) = default;
NumberingSubset& operator=(const NumberingSubset&) = delete;
//! Move affectation.
NumberingSubset& operator=(NumberingSubset&&) = default;
NumberingSubset& operator=(NumberingSubset&&) = delete;
///@}
......@@ -95,6 +100,119 @@ namespace HappyHeart
namespace NumberingSubsetNS
{
/*!
* \brief Yields the unary condition required to find with std::find_if an object \a T in a list provided
* its numbering subset is given.
*
* \tparam T Type of the object being compared; T (or the underlying object - see after) is expected to
* contain a method with prototype const NumberingSubset& GetNumberingSubset() const;
* T may be a pointer type, as in the example below.
*
* To find the GlobalVector in global_vector_list_ of GlobalVector::unique_ptr with numbering subset ns the syntax is:
*
* \code
* auto it = std::find_if(global_vector_list_.cbegin(),
* global_vector_list_.cend(),
* NumberingSubsetNS::FindIfCondition<GlobalVector::unique_ptr>(ns));
* \endcode
*
*/
template<class T>
class FindIfCondition
{
public:
//! Constructor.
FindIfCondition(const NumberingSubset& numbering_subset);
//! Destructor.
~FindIfCondition() = default;
//! Copy constructor.
FindIfCondition(const FindIfCondition&) = default; // required by gcc; clang makes do with only move one.
//! Move constructor.
FindIfCondition(FindIfCondition&&) = default;
//! Copy affectation.
FindIfCondition& operator=(const FindIfCondition&) = delete;
//! Move affectation.
FindIfCondition& operator=(FindIfCondition&&) = delete;
//! Prototype to compare objects shielded by unique_ptr.
bool operator()(const T& rhs) const noexcept;
private:
//! Numbering subset used to describe the vector..
const NumberingSubset& numbering_subset_;
};
/*!
* \brief Yields the unary condition required to find with std::find_if an object \a T in a list provided
* its pair of numbering subsets are given.
*
* \tparam T Type of the object being compared; T (or the underlying object - see after) is expected to
* contain methods with prototype const NumberingSubset& GetRowNumberingSubset() const and
* const NumberingSubset& GetColNumberingSubset() const.
*
* T may be a pointer type, as in the example below.
*
* To find the GlobalMatrix in global_matrix_list_ of GlobaMatrix::unique_ptr with numbering subset ns the syntax is:
*
* \code
* auto it = std::find_if(global_matrix_list_.cbegin(),
* global_matrix_list_.cend(),
* NumberingSubsetNS::FindIfCondition<GlobalMatrix::unique_ptr>(ns));
* \endcode
*
*/
template<class T>
class FindIfConditionForPair
{
public:
//! Constructor.
FindIfConditionForPair(const NumberingSubset& row_numbering_subset,
const NumberingSubset& col_numbering_subset);
//! Destructor.
~FindIfConditionForPair() = default;
//! Copy constructor.
FindIfConditionForPair(const FindIfConditionForPair&) = default; // required by gcc; clang makes do with only move one.
//! Move constructor.
FindIfConditionForPair(FindIfConditionForPair&&) = default;
//! Copy affectation.
FindIfConditionForPair& operator=(const FindIfConditionForPair&) = delete;
//! Move affectation.
FindIfConditionForPair& operator=(FindIfConditionForPair&&) = delete;
//! Prototype to compare objects shielded by unique_ptr.
bool operator()(const T& rhs) const noexcept;
private:
//! Numbering subset used reespectively to describe the rows and columns.
std::pair<const NumberingSubset&, const NumberingSubset&> numbering_subset_pair_;
};
} // namespace NumberingSubsetNS
} // namespace HappyHeart
......
......@@ -12,6 +12,7 @@
namespace HappyHeart
{
inline bool operator==(const NumberingSubset& lhs, const NumberingSubset& rhs)
{
......@@ -29,9 +30,45 @@ namespace HappyHeart
{
return !(operator==(lhs, rhs));
}
namespace NumberingSubsetNS
{
template<class T>
FindIfCondition<T>::FindIfCondition(const NumberingSubset& numbering_subset)
: numbering_subset_(numbering_subset)
{ }
template<class T>
bool FindIfCondition<T>::operator()(const T& rhs) const noexcept
{
return Private::FetchNumberingSubset(rhs) == numbering_subset_;
}
template<class T>
FindIfConditionForPair<T>::FindIfConditionForPair(const NumberingSubset& row_numbering_subset,
const NumberingSubset& col_numbering_subset)
: numbering_subset_pair_(std::make_pair(std::cref(row_numbering_subset), std::cref(col_numbering_subset)))
{ }
template<class T>
bool FindIfConditionForPair<T>::operator()(const T& rhs) const noexcept
{
assert(!(!rhs));
return Private::FetchNumberingSubsetPair(rhs) == numbering_subset_pair_;
}
} // namespace NumberingSubsetNS
} // namespace HappyHeart
......
//
// NumberingSubset.hpp
// HappyHeart
//
// Created by Sebastien Gilles on 04/05/15.
// Copyright (c) 2015 Inria. All rights reserved.
//
#ifndef __HappyHeart__NumberingSubset__HPP
# define __HappyHeart__NumberingSubset__HPP
# include <memory>
# include <vector>
# include "Utilities/Miscellaneous.hpp"
namespace HappyHeart
{
// ============================
// Forward declarations.
// ============================
class NumberingSubset;
// ============================
// End of forward declarations.
// ============================
namespace NumberingSubsetNS
{
namespace Private
{
/*!
* \brief Returns the requested numbering subset from \a object when T is a pointer or smart pointer.
*
*/
template<class T>
std::enable_if_t
<
Utilities::IsSharedPtr<T>() || Utilities::IsUniquePtr<T>() || std::is_pointer<T>(),
const NumberingSubset&
>
FetchNumberingSubset(const T& object) noexcept;
/*!
* \brief Returns the requested numbering subset from \a object when T is not a pointer or smart pointer.
*
* \internal The dispatch is static: all is known at compile-time.
*/
template<class T>
std::enable_if_t
<
!(Utilities::IsSharedPtr<T>() || Utilities::IsUniquePtr<T>() || std::is_pointer<T>()),
const NumberingSubset&
>
FetchNumberingSubset(const T& object) noexcept;