le “rendement” de mot-clé pour le C++, Comment Retourner un Itérateur de ma Fonction?

Considérons le code suivant.

std::vector<result_data> do_processing() 
{
    pqxx::result input_data = get_data_from_database();
    return process_data(input_data);
}

std::vector<result_data> process_data(pqxx::result const & input_data)
{
    std::vector<result_data> ret;
    pqxx::result::const_iterator row;
    for (row = input_data.begin(); row != inpupt_data.end(); ++row) 
    {
        //somehow populate output vector
    }
    return ret;
}

Tandis que je pensais à savoir si ou non je pouvais attendre de la Valeur de Retour d'Optimisation (RVO) pour arriver, j'ai trouvé cette réponse par Jerry Cercueil [c'est moi qui souligne]:

Au moins de l'OMI, il est généralement une mauvaise idée, mais pas pour des raisons d'efficacité. C'est une mauvaise idée parce que la fonction en question doit généralement être écrit comme un algorithme générique qui produit sa sortie via un itérateur. Presque n'importe quel code qui accepte ou renvoie d'un conteneur au lieu d'opérer sur les itérateurs doit être considérée comme suspecte.

Ne vous méprenez pas: il y a des fois il est logique de passer autour de la collection de comme des objets (par exemple, des chaînes de caractères), mais pour l'exemple cité, j'avais envisager l'adoption ou le retour de l'vecteur une mauvaise idée.

Avoir un Python de fond, j'aime les Générateurs de beaucoup. En fait, si on Python, j'aurais écrit au-dessus de fonctionner comme un Générateur, c'est à dire pour éviter la nécessité de traiter l'ensemble des données avant toute autre chose qui pourrait arriver. Par exemple, comme ceci:

def process_data(input_data):
    for item in input_data:
        # somehow process items
        yield result_data

Si j'ai correctement interprété Jerry Cercueils remarque, c'est ce qu'il a suggéré, n'est-ce pas? Si oui, comment puis-je mettre en œuvre cette en C++?

  • Il suffit de retourner le vecteur, c'est très bien. (N)RVO seront plus susceptibles de prendre soin de cela, et en C++11 sémantique de déplacement va faire quand (N)RVO ne le fait pas. Aussi, return process_data(get_data_from_database());. Malheureusement, C++ n'ont pas le yield fonctionnalité. 🙁
  • "Presque tout le code qui accepte ou retourne un conteneur au lieu d'opérer sur les itérateurs doit être considérée comme suspecte." Je dirais qu'avec cette. C'est certainement de bon conseil, mais le désir de rendre le code indépendant du type de conteneur est souvent erronée et ne sont pas interchangeables, sauf dans la syntaxe...
InformationsquelleAutor moooeeeep | 2012-08-10