web-dev-qa-db-fra.com

Utilisez le mot clé auto dans C ++ STL

J'ai vu du code qui utilise un vecteur,

vector<int>s;
s.Push_back(11);
s.Push_back(22);
s.Push_back(33);
s.Push_back(55);
for (vector<int>::iterator it = s.begin(); it!=s.end(); it++) {
    cout << *it << endl;
}

C'est la même chose que

for (auto it = s.begin(); it != s.end(); it++) {
    cout << *it << endl;
}

Dans quelle mesure l'utilisation du mot-clé auto est-elle sûre? Et si le type de vecteur est float? string?

34
dato datuashvili

Le mot clé auto demande simplement au compilateur de déduire le type de la variable de l'initialisation.

Même un compilateur pré-C++ 0x sait quel est le type d'une expression (d'initialisation), et le plus souvent, vous pouvez voir ce type dans les messages d'erreur.

#include <vector>
#include <iostream>
using namespace std;

int main()
{
    vector<int>s;
    s.Push_back(11);
    s.Push_back(22);
    s.Push_back(33);
    s.Push_back(55);
    for (int it=s.begin();it!=s.end();it++){
        cout<<*it<<endl;
    }
}

Line 12: error: cannot convert '__gnu_debug::_Safe_iterator<__gnu_cxx::__normal_iterator<int*, __gnu_norm::vector<int, std::allocator<int> > >, __gnu_debug_def::vector<int, std::allocator<int> > >' to 'int' in initialization

Le mot-clé auto vous permet simplement de profiter de cette connaissance - si vous (le compilateur) connaissez le bon type, choisissez simplement pour moi!

44
UncleBens

Ce sont des informations supplémentaires et ce n'est pas une réponse.

En C++ 11, vous pouvez écrire:

for (auto& it : s) {
    cout << it << endl;
}

au lieu de

for (auto it = s.begin(); it != s.end(); it++) {
    cout << *it << endl;
}

Cela a la même signification.

pdate: Voir aussi le commentaire de @ Alnitak.

37
user1234567

Le mot-clé auto obtient le type de l'expression à droite de =. Par conséquent, cela fonctionnera avec n'importe quel type, la seule exigence est d'initialiser la variable automatique lors de sa déclaration afin que le compilateur puisse déduire le type.

Exemples:

auto a = 0.0f;  // a is float
auto b = std::vector<int>();  // b is std::vector<int>()

MyType foo()  { return MyType(); }

auto c = foo();  // c is MyType
13
Karel Petranek

auto mot-clé est destiné à être utilisé dans une telle situation, il est absolument sûr. Mais malheureusement, il n'est disponible qu'en C++ 0x, vous aurez donc des problèmes de portabilité.

3

C'est un nouvel élément dans la langue avec laquelle je pense que nous allons avoir du mal pour les années à venir. L'auto du début présente non seulement un problème de lisibilité, à partir de maintenant, lorsque vous le rencontrerez, vous devrez consacrer beaucoup de temps à essayer de comprendre ce que c'est (tout comme le temps que le stagiaire a nommé toutes les variables xyz :)), mais vous passerez également beaucoup de temps à nettoyer des programmeurs facilement excitables, comme celui qui a répondu avant moi. Exemple ci-dessus, je peux parier 1000 $, sera écrit "pour (auto it: s)", pas "pour (auto & it: s)", par conséquent, invoquer la sémantique de mouvement où vous la listez en l'attendant, modifiant votre collection en dessous.

Un autre exemple du problème est votre question elle-même. Vous ne savez clairement pas grand-chose sur les itérateurs stl et vous essayez de combler cet écart en utilisant la magie de "auto", par conséquent, vous créez le code qui pourrait être problématique plus tard

2
a o

Si vous voulez un code lisible par tous les programmeurs (c ++, Java et autres), utilisez l'ancien formulaire d'origine au lieu de nouvelles fonctionnalités cryptographiques

atp::ta::DataDrawArrayInfo* ddai;
for(size_t i = 0; i < m_dataDraw->m_dataDrawArrayInfoList.size(); i++) {
    ddai = m_dataDraw->m_dataDrawArrayInfoList[i];
    //...
}
0
user11310689