0
votes

Héritage multiple et accéder aux éléments ambigus

J'essaie de faire quelques astuces d'information de type d'exécution à travers plusieurs héritages et modèles, mais je frappe un problème avec l'ambiguïté.

Premier, un exemple très fondamental de ce dont je parle: < Pré> xxx

Comme les commentaires suggèrent, je peux être particulièrement méchant et ignorer complètement le type. Cette méchanceté me mènera directement à Developer Hell et ne me laissera pas utiliser le pointeur que je souhaite quand même, je vais donc bien avoir une base de std :: Shared_ptr . Mais le second (et légèrement plus proche de la réalité) montre que ce compromis n'est pas suffisant: xxx

dans cet exemple, j'utilise B :: global_val comme une sorte d'informations de type d'exécution sur un type donné . Lorsque le programme est exécuté, je reçois la sortie suivante (j'ai ajouté des commentaires supplémentaires, pour plus de clarté): xxx

Il semble que le tableau V veut uniquement pointer sur le < code> x -Base de mon d et C classes. Comment puis-je vous assurer que le d et c runtime_val pointera sur les feuilles de l'arbre de héritage et non la base?

ps J'ai essayé de faire la classe de base x purement virtuel, mais pas de chance là-bas.


10 commentaires

Vous recherchez un héritage virtuel?


Mon compilateur accepte le make_shared, avec juste ce changement: structure C: publique B / *, public a * / {};


Devrait-il b et c partager un A ou avoir leur propre comme?


Vous avez fait des efforts pour expliquer "le problème" dans les détails, mais j'ai des problèmes de comprendre ce que vous voulez réellement atteindre. Ce n'est pas la faute des compilateurs qu'il y a une ambiguïté, souhaitez-vous en choisir un ou que vous souhaitez avoir un seul A sous-instance?


Si vous voulez un seul héritage virtuel. Pour le moment, il existe une ambiguïté due à C héritant d'une fois d'une fois (une fois indirectement).


@ Ancely Honnelle_463035818 J'essaie de faire un moyen facile de "enregistrer" les classes dans un système de type d'exécution ( A ) de manière simple. Ajout d'une fonction virtuelle à A qui renvoie simplement la valeur ne fonctionne pas non plus. Par "facile", je veux dire quand vous voulez une nouvelle classe x - "qui arrive dans ma base de code), disons classe E vous écrivez simplement struct e : public x, public a et il génère automatiquement un numéro pour E


Je soupçonnais cela déjà avant, je pense que vous confondez "héritage virtuel" avec "la classe de base a une méthode virtuelle", ce sont deux choses complètement différentes. Il semble vraiment que l'héritage virtuel est ce que vous recherchez


Je vais le regarder <3


@ AncelyknownAs_463035818 L'héritage virtuel a résolu le problème, merci!


Heureux de vous aider, bien que notez que les réponses améliorent mieux les réponses, mettre la solution dans le quesiton rend le quesiton difficile à comprendre pour les futurs lecteurs et partiellement invalident déjà des réponses. Vous pouvez répondre à votre propre question dans une réponse si vous aimez


3 Réponses :


0
votes

Ceci semble faux:

struct B : public A { };
struct C : public B/*, public A*/ { };


5 commentaires

Alors demandant à C d'être aussi un problème. Pas si vous vouliez que ce soit comme ça. Dans ce cas, il y en a deux comme chez C, un à l'intérieur de B et un à l'intérieur de C.


Ouais, mais pratiquement, je ne l'ai jamais vu en fait besoin, dans un certain nombre de projets différents.


Vous avez raison, c'est une construction rare, je ne l'ai pas encore vue aussi moi-même.


"D'ici, la vraie question est la suivante: avez-vous besoin de plusieurs instances comme base?" - oui je fais en fait


@Asgergitz ayant d hériter A deux fois via deux chemins différents et chaque d instance comportant deux A Subbjects n'est pas nécessairement le même. Vous comprendrez la différence, une fois que vous avez lu sur l'héritage virtuel. Je pense que ce que vous voulez vraiment est le premier alors que ce dernier vous crée un problème



2
votes
struct A          {};
struct B  : A     {};
struct B2 : A     {};
struct C  : B, B2 {};

std::shared_ptr<A> p1 = std::static_pointer_cast<B >(std::make_shared<C>());
std::shared_ptr<A> p2 = std::static_pointer_cast<B2>(std::make_shared<C>());

0 commentaires

0
votes

Dans les commentaires, @ anciennementknknows-463035818 fournissait la réponse: Ceci est essentiellement "le problème de diamant", solvable via héritage virtuel: xxx


0 commentaires