0
votes

Utilisation de fonctions surchargées avec comportement polymorphe

Je suis en train de mettre en œuvre une classe de moteur de travail générique qui exécute des tâches spécifiques au champ. Tous les champs doivent être dérivés d'une classe de base si un comportement polymorphe sera utilisé. J'ai créé des fonctions surchargées avec des champs de type spécifiques aux champs dérivés, i.e work_engine :: Const A_field & AF) code> dans le code ci-dessous. J'ai supposé que chaque fois qu'un champ vient (le type de classe de base), la fonction appropriée sera appelée automatiquement. Cependant, j'ai l'erreur ci-dessous (fait référence à // ligne magique forte>): xxx pré>

J'ai utilisé cette approche en C #, mais je ne le connais pas en C ++. En utilisant des fonctionnalités C ++ 11 et ultérieures, je voudrais mettre en œuvre la même approche, car il s'agit de code de nettoyage que d'utiliser des déclarations si-d'autre avec des opérations de distribution. D'autre part, peut-être que je fais des erreurs primitives, je voudrais donc séparer mes questions en deux éléments: p>

  1. Quelle est la bonne façon d'atteindre mon intention? Li>
  2. Quelle est l'origine de l'erreur que j'ai rencontrée? Li> ol>

    Merci d'avance pour tous vos commentaires, P>

    Header1.h, y compris les définitions de la classe, est ci-dessous: p>

    #include <iostream>
    #include <Header1.h>
    
    int main()
    {
        work_engine engine;
        engine.fields.push_back(a_field());
        engine.fields.push_back(b_field());
        engine.run_all();
    }
    


3 commentaires

Est-ce que cela répond à votre question? vecteurs et polymorphisme en C ++


Pas en réalité, ma question est plus sur la coulée implicite à la classe de béton à l'intérieur de la Lambda l'expression. // ligne magique


C'est sur vos problèmes. En C ++, une liste d'instances de type concret, pas une liste de références de type polymorphe. La seconde moitié est que vous avez besoin du modèle de visiteur, manuellement, via une variante ou en écrivant vous-même des machines vous-même.


3 Réponses :


0
votes

Tout d'abord: vous avez besoin d'un std :: Liste comme détaillé dans cette question .

Deuxièmement, la rédaction de la rédaction doit être faite explicitement et vous ne pouvez pas choisir la surcharge de fonction appropriée au moment de l'exécution automatiquement.


une solution pourrait Soyez d'utiliser une fonction virtuelle (pure) sur base_field xxx

là, vous devez soit faire work_engine :: exécuter public ou en faire un ami de a_field (ou b_field respectivement).


L'alternative serait d'utiliser le type de vérification du type à l'exécution. Si vous avez un base_field * base , vous pouvez vérifier le type comme celui-ci: xxx

C'est juste un contour de base, mais j'espère que cela aide. < / p>


0 commentaires

0
votes
std::vector<std::variant<a_field, b_field>> fields;
//...
void run_all() {
    for_each(fields.begin(), fields.end(), [&](auto&& el) { std::visit( el, [&](auto&& x){ this->run(x); } ); });
}

0 commentaires

0
votes

Je vois à l'aide de valeurs au lieu des pointeurs Cause de la tranchée d'objet: j'ai changé de valeurs avec des pointeurs, Shared_ptr à Moderne C ++. La seconde, j'ai déplacé la fonction de course dans chaque champ, la fonction spécifique au champ est donc encapsulée avec le champ associé.

#pragma once
#include <algorithm>
#include <list>

// abstract class of base fields 
class base_field
{
public:
    base_field() {}
    virtual ~base_field() {}
    virtual void run() = 0;
};

// custom a field
class a_field : public base_field
{
public:
    a_field() : base_field(){}
    virtual void run() override{}
};

// custom b field
class b_field : public base_field
{
public:
    b_field() : base_field() {}
    virtual void run() override {}
};

class work_engine
{
public:
    std::list<std::shared_ptr<base_field>> fields;
private:

public:
    void run_all()
    {
        for_each(fields.begin(), fields.end(), [&](auto& el) { el->run(); });
    }
};


0 commentaires