web-dev-qa-db-fra.com

passage de vecteurs à une fonction, valeur vs référence C ++

Je code en C++. Si j'ai une fonction void foo(vector<int> test) et que je l'appelle dans mon programme, le vecteur sera-t-il passé par valeur ou par référence? Je ne suis pas sûr car je sais que les vecteurs et les tableaux sont similaires et qu'une fonction comme void bar(int test[]) passerait le test par référence (pointeur?) Au lieu de par valeur. Je suppose que je devrais passer le vecteur par pointeur/référence explicitement si je voulais éviter de passer par valeur mais je ne suis pas sûr.

71
Adam

Si je devais deviner, je dirais que vous êtes issu d'un Java arrière-plan. C'est C++, et les choses sont passées par valeur, sauf indication contraire de votre part, à l'aide de l'opérateur &notez que cet opérateur est également utilisé comme opérateur 'address-of', mais dans un contexte différent). Tout cela est bien documenté, mais je vais répéter quand même:

void foo(vector<int> bar); // by value
void foo(vector<int> &bar); // by reference (non-const, so modifyable inside foo
void foo(vector<int> const &bar); // by const-reference

Vous pouvez également choisir de passer un pointeur sur un vecteur (void foo(vector<int> *bar)), mais si vous savez ce que vous faites et si vous estimez que c'est vraiment la voie à suivre, ne le faites pas.

En outre, les vecteurs ne sont pas identiques aux tableaux! En interne, le vecteur garde en mémoire un tableau dont il gère la gestion de la mémoire, mais de nombreux autres conteneurs STL le font également. Vous ne pouvez pas transmettre de vecteur à une fonction qui attend un pointeur ou un tableau, ou inversement (vous pouvez accéder au (pointeur) du tableau sous-jacent et l'utiliser cependant). Les vecteurs sont des classes offrant de nombreuses fonctionnalités via ses fonctions de membre, tandis que les pointeurs et les tableaux sont des types intégrés. De plus, les vecteurs sont alloués dynamiquement (ce qui signifie que la taille peut être déterminée et modifiée au moment de l'exécution) alors que les tableaux de style C sont alloués de manière statique (sa taille est constante et doit être connue à la compilation), ce qui limite leur utilisation.

Je vous suggère de lire un peu plus sur le C++ en général (en particulier --- (array decay ), puis de regarder le programme suivant qui illustre la différence entre les tableaux et les pointeurs:

void foo1(int *arr) { cout << sizeof(arr) << '\n'; }
void foo2(int arr[]) { cout << sizeof(arr) << '\n'; }
void foo3(int arr[10]) { cout << sizeof(arr) << '\n'; }
void foo4(int (&arr)[10]) { cout << sizeof(arr) << '\n'; }

int main()
{
    int arr[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
    foo1(arr);
    foo2(arr);
    foo3(arr);
    foo4(arr);
}
98
JorenHeit

Un vector est fonctionnellement identique à un tableau. Mais pour le langage vector est un type et int est également un type. Pour un argument de fonction, un tableau de tout type (y compris vector[]) est traité comme un pointeur. Un vector<int> n'est pas identique à int[] (au compilateur). vector<int> n'est pas un tableau, ni une référence, ni un pointeur - il est passé par valeur et, par conséquent, il appellera copy-constructeur.

Donc, vous devez utiliser vector<int>& (de préférence avec const, si la fonction ne la modifie pas) pour le transmettre en tant que référence.

16
Ajay

void foo(vector<int> test)

le vecteur serait passé par valeur dans ceci.

Vous avez plus de moyens de passer des vecteurs en fonction du contexte: -

1) Passer par référence: - Ceci laissera la fonction foo changer le contenu du vecteur. Plus efficace que de passer par la valeur car la copie du vecteur est évitée.

2) Passer par const-reference: - Ceci est efficace aussi bien que fiable lorsque vous ne voulez pas que la fonction change le contenu du vecteur.

8
ravi

lorsque nous passons vecteur par valeur dans une fonction en tant qu'argument, cela crée simplement la copie du vecteur et aucun effet ne se produit sur le vecteur défini dans la fonction principale lorsque nous appelons cette fonction particulière. alors que lorsque nous passons vecteur par référence, quel que soit ce qui est écrit dans cette fonction particulière, chaque action va être exécutée sur le vecteur défini dans la fonction principale ou une autre fonction lorsque nous appelons cette fonction particulière.

1
Nishant Yadav