web-dev-qa-db-fra.com

C / C ++ Struct vs Class

Une fois ma classe C++ terminée, il me semblait que les structures/classes étaient pratiquement identiques, à quelques différences mineures près.

Je n'ai jamais programmé en C auparavant; mais je sais qu'il a des structures. En C, est-il possible d'hériter d'autres structures et de définir un modificateur public/privé?

Si vous pouvez faire cela en C normal, pourquoi avons-nous besoin du C++ dans le monde? Qu'est-ce qui différencie les classes d'une structure?

103
anon235370

En C++, les structures et les classes sont à peu près les mêmes; la seule différence est que, lorsque les modificateurs d'accès (pour les variables membres, les méthodes et les classes de base) des classes sont définis par défaut sur privé, les modificateurs d'accès des structures sont définis par défaut sur public.

Cependant, en C, une structure est simplement une collection agrégée de données (publiques) et ne possède aucune autre fonctionnalité de type classe: aucune méthode, aucun constructeur, aucune classe de base, etc. Bien que C++ ait hérité du mot-clé, il a étendu la sémantique. Cependant, c’est la raison pour laquelle les choses sont définies par défaut sur public dans une structure - une structure écrite comme une structure C se comporte comme telle.)

Bien qu'il soit possible de simuler des OOP en C, par exemple, définir des fonctions qui prennent toutes un pointeur sur une structure comme premier paramètre, ou occasionnellement contraignant les structures avec les mêmes premiers champs à être des "sous/superclasses" - il est toujours verrouillé, et ne fait pas vraiment partie du langage.

139

Autre que les différences dans l'accès par défaut (public/privé), il n'y a pas de différence.

Cependant, certaines boutiques utilisant du code en C et C++ utiliseront "class/struct" pour indiquer celles qui peuvent être utilisées en C et C++ (struct) et qui ne sont que C++ (classe). En d'autres termes, dans ce style, toutes les structures doivent fonctionner avec C et C++. C'est en quelque sorte la raison pour laquelle il y a bien longtemps une différence, à l'époque où le C++ était encore appelé "C avec classes".

Notez que les unions C fonctionnent avec C++, mais pas l'inverse. Par exemple

union WorksWithCppOnly{
    WorksWithCppOnly():a(0){}
    friend class FloatAccessor;
    int a;
private:
    float b;
};

Et également

typedef union friend{
    int a;
    float b;
} class;

ne fonctionne qu'en C

14
Lance Diduck

Je vais ajouter quelque chose aux réponses existantes car le C++ moderne est devenu chose courante et officielle Principes directeurs ont été créés pour aider avec des questions telles que celles-ci.

Voici une section pertinente des lignes directrices:

C.2: Utilisez la classe si la classe a un invariant; utilisez struct si les membres de données peuvent varier indépendamment

Un invariant est une condition logique pour les membres d'un objet qu'un constructeur doit établir pour que les fonctions de membre public puissent l'assumer. Une fois l'invariant établi (généralement par un constructeur), chaque fonction membre peut être appelée pour l'objet. Un invariant peut être déclaré de manière informelle (par exemple, dans un commentaire) ou plus formellement en utilisant Expects.

Si tous les membres de données peuvent varier indépendamment les uns des autres, aucun invariant n'est possible.

Si une classe contient des données privées, un utilisateur ne peut pas initialiser complètement un objet sans utiliser de constructeur. Par conséquent, le créateur de classe fournira un constructeur et devra en préciser le sens. Cela signifie effectivement que le définisseur doit définir un invariant.

Application de la loi

Recherchez les structures avec toutes les données privées et les classes avec des membres publics.

Les exemples de code donnés:

struct Pair {  // the members can vary independently
    string name;
    int volume;
};

// but

class Date {
public:
    // validate that {yy, mm, dd} is a valid date and initialize
    Date(int yy, Month mm, char dd);
    // ...
private:
    int y;
    Month m;
    char d;    // day
};

Classes fonctionnent bien pour les membres qui sont, par exemple, dérivés les uns des autres ou interdépendants. Ils peuvent également aider à vérifier la santé mentale lors de l'instanciation. Structs'utilise bien pour avoir des "poches de données", où rien de spécial ne se passe vraiment, mais les membres ont logiquement du sens d'être regroupés.

À partir de là, il est logique que classes existe pour prendre en charge l’encapsulation et d’autres concepts de codage connexes, pour lesquels structs ne sont tout simplement pas très utiles.

6
Dave

Il n'est pas possible de définir des fonctions membres ou de tirer des structures les unes des autres en C.

De plus, C++ n'est pas seulement C + "dériver des structs". Les modèles, les références, les espaces de noms définis par l'utilisateur et la surcharge des opérateurs n'existent pas en C.

Une différence supplémentaire en C++: lorsque vous héritez d'une classe de struct sans spécificateur d'accès, il devient un héritage public alors que, dans le cas d'une classe, il s'agit d'un héritage privé.

3
MarsRover

C++ utilise principalement les structures pour 1) la compatibilité ascendante avec les types C et 2) POD. Les structures C n'ont pas de méthodes, d'héritage ou de visibilité.

1
Chris Hafey