10
votes

Quelle est la différence? Pointeur sur un tableau VS régulier

Je connais Java et essaye de m'enseigner C / C ++. Je vole des programmes d'études d'une classe qui accueille leurs matériaux ici . Malheureusement, je ne peux pas demander à l'enseignant depuis que je ne suis pas dans la classe. Ma préoccupation est avec la section sous "Tableaux déclarés dynamiquement":

si vous vouloir pouvoir modifier la taille de votre tableau au moment de l'exécution, puis déclarer Tableaux dynamiques. Celles-ci sont faites avec les pointeurs et le nouvel opérateur. Pour le Principes de base sur les pointeurs, lisez les pointeurs section.

allouer la mémoire en utilisant de nouveaux, puis Vous accédez au tableau de la même manière Vous seriez un tableau statique. Par exemple,

int * arayptr = nouveau int [10]; pour (int i = 0; i <10; i ++) { Arrayptr [i] = i; }

L'image de la mémoire est identique à la Array statique, mais vous pouvez changer le taille si vous avez besoin de. Ne t'oublie pas doit distribuer la mémoire avant allouant une nouvelle mémoire (ou vous allez avoir une fuite de mémoire).

Supprimer [] ArrayPtr; // les [] est nécessaire lors de la suppression des pointeurs de tableau arrayptr = nouveau int [50]; . . .

quand vous êtes complètement fait avec le Array, vous devez supprimer sa mémoire:

Supprimer [] ArrayPTR;

Les tableaux multi-dimensions dynamiques sont fait de la même manière à Java. Tu aura des pointeurs aux indicateurs. Pour un Exemple, voir un

Ma compréhension est qu'un tableau en C est simplement une référence à l'adresse de la mémoire du premier élément de la matrice.

donc, quelle est la différence entre int * pointerarray = neuf int [10]; et int ossature [10]; si tout?

J'ai fait des tests qui semblent indiquer qu'ils font exactement la même chose. Est le site Web erroné ou ai-je lu ce mal? xxx

sortie: xxx

J'ai essayé de "dynamiquement Reformalisation "Mon tableau de pointeur comme décrit sur le site, mais mon nouveau tableau de pointeur (plus grand) se termine rempli de 0 qui n'est pas très utile.

c c++

17 commentaires

POINTERARRAY + 5 - Il est faux du fait de la taille de Int est plus qu'un octet


Êtes-vous sûr qu'il n'y a pas de faute de frappe dans le code? Il me semble que les résultats des 4 premiers Cout devraient tous être 5.


@IVAN: Non, c'est parfait. Dans l'arithmétique du pointeur, la taille du type de données que le pointeur pointe est disponible en interne. Donc, Pointerarray + 5 augmentera par 5 * Tailleof (INT), c'est-à-dire que, il vous donnera le 5ème élément du tableau que pointeparArray pointe.


@IVAN: Pourquoi cela devrait-il être faux? Lors de la réalisation de l'arithmétique sur un pointeur t * , + 5 signifie + 5 * taille de taille (t) .


@James T: Pensez à utiliser std :: vecteur si vous le pouvez, beaucoup plus facile.


Il est mentionné dans le texte cité mais vous avez toujours oublié de libérer votre mémoire avec Suppr [] Pointerarray .


Urgh, ce n'est pas C ++, c'est la torture. En C ++, nous avons la classe de la classe pour les tableaux dynamiques. Il y a une école de pensée qui croit que le but lors de l'enseignement C ++ est de maximiser le nombre de bugs que les étudiants peuvent faire par la suite, en leur enseignant uniquement le pire moyen de tout faire. Étant donné que le matériau que vous avez trouvé suit cette philosophie, le meilleur que vous puissiez faire si vous souhaitez apprendre C ++ est en train de fuir. Ensuite, achetez un livre sur C ++


@Sriram votre droit il y a une faute de frappe, je viens de re-ran le code


Je ne comprends tout simplement pas pourquoi ces tutoriels sont enfermés pour gâcher l'image de C ++. En C ++, une bien meilleure alternative de std :: vecteur est disponible, ils parlent toujours de créer des tableaux dynamiques utilisant nouveau [] .


Je pense que c'est une question légitime. @James T est un débutant à C / C ++ et apprend. La question est également marquée comme devoirs.


@Sriram: Ce n'est pas la légitimité de la question que nous interrogeons. Nous disons que le matériel pédagogique qu'il a trouvé suce et va perdre son temps et lui demander de réapprendre beaucoup de choses correctement .


Dupliqué possible de pointeur vs tableau en C, différence non triviale


@jalf Une des choses que je trouve excitant à propos de C ++ est que je peux traiter de mémoire directement. Avoir tout résumé à des choses comme des vecteurs est très utile, mais n'aide pas mon objectif ultime de comprendre comment tout fonctionne à un niveau bas. J'utilise C ++ comme terrain d'entente avant de m'attaquer à l'assemblage. Alors oui, ce genre de choses pourrait décourager certains, mais pour moi, c'est la raison pour laquelle j'apprends C ++. Cela dépend du public. Peut-être que je peux désassembler C ++ pour obtenir un assemblage presque lisible.


@James: Il ne s'agit pas de vous décourager, il s'agit d'apprendre des choses dans un ordre sensible. Je ne dis pas que vous ne devriez pas apprendre à faire face à la gestion de la mémoire manuelle, cela ne devrait pas être enseigné tant que l'élève ne comporte pas de bonne compréhension de nombreux autres fondamentaux de la langue. C ++ est une langue complexe et quel que soit ce que vous voulez utiliser, vous devez créer les bons modèles mentaux de la manière dont cela fonctionne et comment il devrait être utilisé. Malheureusement, de nombreux enseignants y pensent comme "C avec des extras"


@jalf ah ok. Le site Web visait à introduire un étudiant qui comporte une compréhension de Java dans le monde de C ++. De ce que je comprends, Java est basé sur C ++. Peut-être que ces concepts fondamentaux de C ++ sont supposés avoir été enseignés en Java? En tout cas, je vais essayer de trouver un bon livre sur C ++ comme vous l'avez suggéré. Merci pour le conseil!


@James: Cela dépend de la façon dont vous le définissez. Je dirais que Java et C ++ sont basés sur la notion de "C avec des classes". Et l'une des choses qui trébuchent souvent les programmeurs Java augmente est l'hypothèse que cela signifie que C ++ peut être considéré comme un prédécesseur direct de Java. Ce n'est pas (En cas de doute, considérez que Java 1.0 est sorti en 1995, tandis que C ++ était normalisé à la fin de 1998). Iow. Certains des premiers travaux sur C ++ ont clairement influencé Java, mais la plupart de ce qui définit C ++ aujourd'hui est venu plus tard et n'avait donc aucune incidence sur Java. Pensez à eux comme des langues frères frères et soeurs (avec un ancêtre commun) à la place


@jalf Merci pour la clarification.


9 Réponses :


3
votes

alloué de manière dynamique: xxx

[BTW, il s'agit d'un pointeur sur un tableau de 10 INTS, pas un tableau de pointeur]

statiquement attribué (éventuellement sur la pile ): xxx

sinon ils sont les mêmes.


0 commentaires

0
votes

La principale différence est que certaines opérations autorisées sur des pointeurs ne sont pas autorisées sur des tableaux.


0 commentaires

16
votes

intora [10]; code> déclare la taille de la matrice statiquement, cela signifie qu'il est fixé - qui est la seule différence majeure. Il peut également être attribué à l'intérieur du cadre de pile de la fonction, c'est-à-dire sur la pile du programme. Vous n'avez pas besoin de vous inquiéter de l'utilisation de Suppr [] code> sur ce type de tableau, en fait, vous pouvez planter le programme si vous Supprimer CODE> IT.

Lorsque vous utilisez. Opérateur Nouveau code>, vous allouez de la mémoire dynamiquement qui pourrait être plus lente em> et la mémoire provient généralement du tas em> plutôt que la pile du programme (mais pas toujours) . C'est mieux dans la plupart des cas, car vous êtes plus limité dans l'espace de la pile que l'espace de tas. Cependant, vous devez surveiller les fuites de mémoire et Suppr [] code> vos affaires lorsque vous n'en avez plus besoin. P>

sur votre tableau étant rempli de zéros, quelle est votre classe Le matériel ne dit pas est que vous devez le faire: P>

int *arr = new int[20]; // old array
//do magic here and decide that we need a bigger array
int *bigger = new int[50]; // allocate a bigger array
for (int i = 0; i < 20; i++) bigger[i] = arr[i]; // copy the elements from the old array into the new array
delete[] arr;
arr = bigger;


4 commentaires

La partie magique ici est donc le "arr = plus grand;"? Sinon, je pouvais simplement copier tout pour plus grand et utiliser plus grand au lieu d'ARR (si vous n'utilisez pas les pointeurs).


Sinon, tout est cristallin clair. Excellente réponse. Merci!


Oui, la partie magique est la réassuite du pointeur. Vous pouvez utiliser l'ancien nom avec une taille plus grande!


Le code dans la réponse est manquant d'initialisation des données de réseau. Éléments de plus grand [20] à plus grand [49] sont ininitialisés et contiendront des valeurs aléatoires. Pour résoudre le problème, vous devez utiliser: plus grand = neuf int [50] (); (note la parenthèse supplémentaire) et pour une matrice allouée de pile: int initialisé [20] = {} ;



0
votes

D'une part:

delete[] ar;


0 commentaires

0
votes

Il y a une différence mais pas dans la zone que vous indiquez. * Pointerarray pointera au début d'un bloc de mémoire de taille 10 octets. Donc, array . La seule différence sera celle où elle est stockée en mémoire. POINTERARRAY est attribué de manière dynamique la mémoire (à exécutant ) et est donc ira sur le tas, tandis que tableau [10] sera attribué à < code> compilation-temps et ira à la pile.


0 commentaires

0
votes

Il est vrai que vous pouvez obtenir la plupart des fonctionnalités de la matrice en utilisant un pointeur sur son premier élément. Mais le compilateur sait qu'un tableau statique est composé de plusieurs éléments et la différence la plus notable est le résultat de l'opérateur .

tailleOf (pointerarray) = Tailleof int *

Tailleof (tableau) = 10 * Taille de l'int


0 commentaires

8
votes

Ma compréhension est qu'un tableau en C est simplement une référence à l'adresse de la mémoire du premier élément de la matrice.

Alors, quelle est la différence entre int * pointerarray = nouveau int [10]; et intora [10]; Si tout?

Ce que vous mentionnez est la raison de beaucoup de confusion dans le débutant de tout C / C.

En C / C ++, un correspond de tableau à un bloc de mémoire suffisamment grande pour contenir tous ses éléments. Ceci est associé à la syntaxe [] , comme dans votre exemple: xxx

une fonctionnalité de C / C ++ est que vous pouvez faire référence à un tableau en utilisant un pointeur sur son type. Pour cette raison, vous êtes autorisé à écrire: xxx

qui est identique à: xxx

et cela permet de Éléments d'accès d'accès à la manière habituelle: array_pointer [3] , Mais vous ne pouvez pas traiter tableau comme un pointeur, comme faire des arithmétiques du pointeur sur celui-ci (c.-à-d. Array ++ échoue de manière misérable).

qui dit, il est également vrai que vous pouvez gérer des tableaux sans gérer Utilisation de la syntaxe [] et simplement allouer des tableaux à l'aide de MALLOC , puis utilisez-les avec des pointeurs bruts. Cela rend la "beauté" de C / C ++.

Reprise: une distinction doit être faite entre le pointeur et la mémoire qu'il pointe de (le tableau réel):

  1. [] syntaxe dans les déclarations (c.-à- array int [10]; ) fait référence aux deux aspects à la fois (il vous donne, à dire , un pointeur et un tableau);

  2. Lors de la déclaration d'une variable de pointeur (c'est-à-dire <, int * p; ), vous venez d'obtenir le pointeur;

  3. Lors de l'évaluation d'une expression (c.-à-d. int i = p [4]; ou tableau [4]; ), le [] [] signifie simplement la déséroférance d'un pointeur.

    En dehors de cela, la seule différence entre int * pointerarray = nouveau int [10]; et int ossature [10]; est que ce premier est alloué de manière dynamique, ce dernier sur la pile.


2 commentaires

Quelle est la différence entre INT * A et INT * A [10]


@Surajjain int * a est un pointeur sur un int, tandis que int * a [10] est un tableau (de taille 10) des pointeurs à int.



3
votes

Le problème avec la compréhension des tableaux C / C ++ lors de la sortie de Java est que C / C ++ distingue la variable de matrice et la mémoire utilisée pour stocker le contenu de la matrice. Les deux concepts sont importants et distincts. En Java, vous avez vraiment une référence à un objet qui est un tableau.

Vous devez également comprendre que C / C ++ a deux façons d'attribuer la mémoire. La mémoire peut être attribuée à l'aide ou à la pile. Java n'a pas cette distinction.

en C et C ++, une variable de matrice est un pointeur sur le premier élément du tableau. Une variable de matrice peut exister sur le tas ou la pile, et la mémoire peut donc contenir son contenu. Et ils peuvent être la différence. Vos exemples sont des tableaux int , de sorte que vous pouvez envisager la variable de matrice d'être un int * .

Il y a deux différences entre int * pointerarray = neuf int [10]; et intora [10]; :

La première différence est que la mémoire contenant le contenu du premier tableau est allouée sur le tas . Le deuxième tableau est plus délicat. Si Array est une variable locale dans une fonction, son contenu est attribué sur la pile, mais s'il s'agit d'une variable de membre d'une classe, son contenu est attribué partout où l'objet contenant est attribué (tas ou empilement ).

La deuxième différence est que, comme vous l'avez réalisé, le premier tableau est dynamique: sa taille peut être déterminée au moment de l'exécution. Le deuxième tableau est corrigé: le compilateur doit pouvoir déterminer sa taille au moment de la compilation.


0 commentaires

2
votes

Premièrement, je chercherais un autre endroit pour apprendre C ++. La page que vous citez est très déroutant et a peu à voir avec la façon dont un programme réellement en C ++. En C ++, la plupart du temps, vous utiliseriez std :: vecteur pour un tableau, Pas les solutions complexes proposées sur la page que vous citez. En pratique, Vous n'utilisez jamais opérateur nouveau [] (un tableau neuf ).

En fait, std :: vecteur est de quelque manière que ce soit comme arraylist que simple tableaux en Java; Contrairement à un tableau en Java, vous pouvez simplement développer le vecteur En insérant des éléments dedans, de préférence à la fin. Et il soutient itérateurs, bien que les itérateurs C ++ soient considérablement différents de Java Itérateurs. D'autre part, vous pouvez y accéder à l'aide du [] opérateur, comme un tableau normal.

Les tableaux décrits sur la page que vous citez sont généralement appelés style C tableaux. En C ++, leur utilisation est principalement limitée aux objets avec statique. la durée de vie, bien qu'elles apparaissent occasionnellement dans des classes. Dans tous les cas, ils ne sont jamais alloués de manière dynamique.


0 commentaires