Domanda

Per qualche ragione, non riesco a utilizzare boost::format in un boost::lambda. Ecco una (si spera) compilabile semplificazione del mio codice:

#include <algorithm>
#include <iomanip>
#include <iostream>

#include <boost/assign/list_of.hpp>
#include <boost/format.hpp>
#include <boost/lambda/lambda.hpp>

namespace bl = boost::lambda;

int main()
{
    const std::vector<int> v = boost::assign::list_of(1)(2)(3);
    std::for_each(v.begin(), v.end(), bl::var(std::cout) << std::setw(10) << bl::_1);
    std::for_each(v.begin(), v.end(), bl::var(std::cout) << boost::format("%10d") % bl::_1);
}
  • Il primo std::for_each produce l'output previsto
  • Il secondo std::for_each emette solo spazi bianchi senza numero

Perché? Io non sono davvero familiarità con boost::lambda quindi potrei mancare l'ovvio qui.

Si prega di non suggerire risposte std::copy base:. Il mio codice reale non funziona su std::vector ma su boost::fusion::vector (e std::for_each è infatti un boost::fusion::for_each)

È stato utile?

Soluzione

Per qualche ragione, i vostri Esamina codice boost::format("%10d") % bl::_1 subito, piuttosto che su ogni invocazione del lambda.

Per evitare questo, è necessario avvolgere boost::format("%10d") in una chiamata a bl::var, proprio come avete fatto con std::cout.

Purtroppo, facendo questo richiede Boost.Lambda di dedurre il tipo di ritorno della chiamata a operator%, che non è in grado di fare. Pertanto, il tipo di ritorno deve essere specificato in modo esplicito, utilizzando bl::ret. Si noti che questo tipo di ritorno deve essere un riferimento, in modo che std::cout accede all'oggetto restituito direttamente piuttosto che una copia di esso.

Abbiamo quindi ottenere il codice seguente, che produce i risultati attesi:

std::for_each(v.begin(), v.end(), bl::var(std::cout) <<
    bl::ret<const boost::format &>(bl::var(boost::format("%10d")) % bl::_1));

Altri suggerimenti

La mia scommessa è che si sta eseguendo nel fatto che un formato utilizzato non è più utilizzabile.

boost::format f("...");

std::string s = f % ... ;
std::string s2 = f % other options...; // FAIL!  f has been changed by the above use!

In altre parole, utilizzando% su un formato in realtà sostituisce i dati della stringa con qualsiasi cosa% 'd in esso. La cosa più fresca è che il secondo uso sopra sarà silenziosamente non riuscire.

Lo so, sorta di contro-intuitivo, ma è quello che è.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top