2
votes

Comme, une fonction virtuelle peut-on rendre une variable virtuelle en c ++

lorsqu'un pointeur de classe de base pointe vers l'objet de sa classe dérivée et si une fonction est surchargée, nous utilisons une fonction virtuelle pour résoudre le problème. Afin que nous puissions accéder à la propre fonction de la classe dérivée en utilisant le pointeur. Comme ça, je pensais que s'il y avait un moyen qui puisse être appliqué sur le mot-clé virtuel dans la variable, afin que nous puissions accéder à la dernière version d'une variable dans la classe dérivée en utilisant le pointeur.

#include <iostream>
using namespace std;
class base
{
public:
int x;//but what about this , if we add virtual keyword here.
    //it will give error if trying to do so .
    //but can you tell me what can i do if i want to make use of it as virtual function
    //if not please tell me why
virtual void display(void) //to call the recent version of display function we make use of virtual here
{
    cout << "base\n";
}
};
class derived : public base
{
public:
int x;
void display(void)
{
    cout << "derived\n";
}
};
int main(void)
{
    base *p;
    base ob1;
    derived ob2;
    p=&ob2;
    p->x=100;//here i want to set 100 to the x of derived class not that x which has been inherited
            //But it sets to the x of base class which i dont wanted
    p->display();//here we can access the latest version of display function in derived class
    return 0;
}

S'il vous plaît Aucun organisme ne me demande pourquoi je veux le faire. Je n'ai aucune intention de le faire dans mon vrai code. j'ai demandé la curiosité.


4 commentaires

pas vraiment, mais vous pouvez déclarer la variable normalement et déclarer des opérateurs pour accéder à la variable dans votre classe si cela aide, et vous pouvez rendre les opérateurs virtuels


Vous pouvez créer un accesseur virtuel qui renvoie une référence. Vous ne pouvez pas rendre tous les accès variables virtuels par défaut.


Que signifierait avoir un membre de données virtuel? En quoi serait-il différent d'un membre de données régulier?


@SanderDeDycker Je suppose que cela pourrait aider à la façon dont les données sont stockées en mémoire si cela pose un problème


3 Réponses :


3
votes

Vous ne pouvez pas remplacer les variables membres avec le mot-clé virtual . Vous pouvez cependant avoir des getters et des setters virtuels qui font référence à différentes variables membres dans la base et les classes dérivées pour obtenir un effet similaire:

class base {
public:
    virtual int getX() {
        return x;
    }
    virtual void setX(int x) {
        this->x = x;
    }
private:
    int x;
}

class derived : public base {
public:
    int getX() {
        return x;
    }
    void setX(int x) {
        this->x = x;
    }
private:
    int x;
}


2 commentaires

Vous avez masqué et non remplacé getX et setX


@Caleth en effet. Trop de temps à Java. L'édition de Caleth devrait le corriger.



5
votes

Non, vous ne pouvez pas utiliser virtual pour les champs, uniquement pour les méthodes.

Cependant, vous pouvez simuler cela en créant une fonction qui renvoie une référence à un champ:

class Base
{
private:
    int x;

public:
    virtual int& X() { return x; }
};

class Derived : public Base
{
private:
    int x;

public:
    virtual int& X() override { return x; }
};

int main()
{
    Derived d;
    Base* b = &d;

    b->X() = 100; // will set d's x
}


0 commentaires

2
votes

Les autres réponses sont tout à fait correctes mais vous pouvez également utiliser la syntaxe beaucoup plus simple:

class derived : public base {
    public:
    operator int() override { return x * 5; };
}

si vous avez une seule variable que vous souhaitez virtualiser dans votre classe. p >

La deuxième déclaration est uniquement pour éviter d'utiliser une référence lorsque vous avez juste besoin de la valeur, tandis que lors de l'attribution de la référence est automatiquement choisie pour vous.

Vous pouvez remplacer ces opérateurs à volonté à partir des classes dérivées base.

class base {
public:
    virtual operator int&() { return x; };
    virtual operator int() { return x; };
protected:
    int x;
};


0 commentaires