Twitter iPhone pliant OnePlus 11 PS5 Disney+ Orange Livebox Windows 11

Accéder à un membre d'un classe d'après son nom

2 réponses
Avatar
Laurent
Salut,

J'ai une classe CollectionParams qui contient notamment des membres
_Param_1, _Param_2, ..., _Param_N qui font partie de la classe Param. La
classe Param est une classe toute bête qui stocke une valeur et qui fournit
les accesseurs Set() et Get().

Je veux faire une fonction capable de créer une instance de CollectionParams
puis de modifier n'importe lequel de ses paramètres _Param_1, _Param_2,
..., _Param_N et que ce soit un argument de la fonction qui décide sur quel
_Param_i elle doit travailler.

grosso modo je veux faire :
MaCollectionParam = new CollectionParams(),
MaCollectionParam->_Param_i.Set(valeur),
mais que le _Param_i soit transmis comme argument de la fonction afin
qu'elle puisse travailler sur n'importe quel _Param_i de la même façon.

La difficulté est qu'au moment de l'appel de cette fonction l'instance de
CollectionParams n'est pas encore créée, je ne dispose donc pas d'un
pointeur sur le _Param_i qui m'intéresse pour le donner en argument. La
seule façon que je vois pour s'en sortir serait de pouvoir déduire un
pointeur de _Param_i connaissant simplement l'existence d'un membre de la
classe qui porte le nom "_Param_i". Est-ce possible ?

Merci de votre aide.

2 réponses

Avatar
Falk Tannhäuser
Laurent wrote:

Je veux faire une fonction capable de créer une instance de CollectionParams
puis de modifier n'importe lequel de ses paramètres _Param_1, _Param_2,
..., _Param_N et que ce soit un argument de la fonction qui décide sur quel
_Param_i elle doit travailler.

grosso modo je veux faire :
MaCollectionParam = new CollectionParams(),
MaCollectionParam->_Param_i.Set(valeur),
mais que le _Param_i soit transmis comme argument de la fonction afin
qu'elle puisse travailler sur n'importe quel _Param_i de la même façon.

La difficulté est qu'au moment de l'appel de cette fonction l'instance de
CollectionParams n'est pas encore créée, je ne dispose donc pas d'un
pointeur sur le _Param_i qui m'intéresse pour le donner en argument. La
seule façon que je vois pour s'en sortir serait de pouvoir déduire un
pointeur de _Param_i connaissant simplement l'existence d'un membre de la
classe qui porte le nom "_Param_i". Est-ce possible ?


Peut-être avec des fonctions membres template prenant en paramètre
un pointeur sur un membre de ta classe :


struct CollectionParams
{
int i;
double d;

template<typename MemberType>
void Set(MemberType CollectionParams::*mem_ptr, MemberType const& val)
{ this->*mem_ptr = val; }
};

int main()
{
CollectionParams cp;
cp.Set<int, &CollectionParams::i>(42); // Appel du 1er Set()
cp.Set(&CollectionParams::i, 42);
cp.Set(&CollectionParams::d, 6.55957);
std::cout << cp.i << ' ' << cp.d << 'n';
return 0;
}


Une autre possibilité serait de faire du pointeur sur le membre un
paramètre du template plutôt qu'un paramètre de la fonction :

struct CollectionParams
{
...
template<typename MemberType, MemberType CollectionParams::*MemPtr>
void Set(MemberType const& val)
{ this->*MemPtr = val; }
};

Cette fonction membre sera appelée ainsi :
cp.Set<int, &CollectionParams::i>(42);


Je ne sais pas si cela correspond à ce que tu veux faire ni s'il y a un moyen
plus simple au niveau de la conception ...

Falk

Avatar
drkm
Falk Tannhäuser writes:

int main()
{
CollectionParams cp;
cp.Set<int, &CollectionParams::i>(42); // Appel du 1er Set()
^^^^^^^^^^^^^^^^^^


Je suppose que tu parles ici de l'exemple que tu donnes plus loin ?

--drkm