2010-11-19 8 views
8
class Filter{ 
private: 
    string contents; 
    bool Server(void); 
public: 
    void handle(void *, size_t, size_t, void *); 
    }; 

Ich habe eine Klasse Header wie folgt. Ich möchte curl WRITEFUNCTION innerhalb der Funktion Server aufrufen, die mit handle in den String-Inhalt schreiben würde. obwohl es hält mir den FehlerCurl WRITEFUNCTION und Klassen

error: invalid use of member (did you forget the ‘&’ ?) 

die Linie darauf durch Fehler giveng ist, dass die CURLOPT_WRITEFUNCTION .... Meine curl Anfrage ungefähr so ​​aussieht ...

curl_easy_setopt(curl,CURLOPT_URL, address.c_str()); 
curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,handle); 
curl_easy_perform(curl); 

, die ihre nicht in der Lage bedeutet, Zugriff auf den Griff() .. Wie kann ich das beheben?

Antwort

2
unter Verwendung einen Zeiger auf die Instanz von Filter als letztes Argument übergeben
string temp; 

curl_easy_setopt(curl,CURLOPT_WRITEFUNCTION,handle); 
curl_easy_setopt(curl,CURLOPT_WRITEDATA,&temp); 

size_t Filter::handle(void *ptr, size_t size, size_t nmemb, string stream) 
{ 
    string temp(static_cast<const char*>(ptr), size * nmemb); 
    stream = temp; 
    return size*nmemb; 
} 

das ist, wie ich es bekam .. zu arbeiten dies wird die Website in dem temporären benannte Zeichenfolge zu speichern.

+1

Dies erzeugt eine lokale std :: string temp, wo die Daten gespeichert werden.Danach wird temp in den Argumentdatenstrom kopiert.Wenn die Funktion zurückkehrt, werden beide Zeichenketten gelöscht.Verwenden Sie temp.append (...) Anstatt Daten in die globale Zeichenkette temp zu schreiben oder die korrekte Signatur mit einem Zeiger auf die globale Zeichenkette zu verwenden und durch diesen Zeiger anzufügen – hansmaad

+0

Sie sollten append verwenden, da die Write-Funktion für eine Ressource, die Sie laden, mehrfach aufgerufen werden kann – hansmaad

+0

das stürzt auf mich – Tim

16

handle muss eine statische Elementfunktion sein. Sie können CURLOPT_WRITEDATA

class Filter 
{ 
private: 
    std::string content_; 
    static size_t handle(char * data, size_t size, size_t nmemb, void * p); 
    size_t handle_impl(char * data, size_t size, size_t nmemb); 
}; 

size_t Filter::handle(char * data, size_t size, size_t nmemb, void * p) 
{ 
    return static_cast<Filter*>(p)->handle_impl(data, size, nmemb); 
} 

size_t Filter::handle_impl(char* data, size_t size, size_t nmemb) 
{ 
    content_.append(data, size * nmemb); 
    return size * nmemb; 
} 

int main() 
{ 
    // curl initialization... should be done in a constructor 
    Filter f; 
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, &f); 
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, &Filter::handle); 
    // curl cleanup... should be done in a destructor 
    return 0; 
} 
+0

Gibt es eine andere Möglichkeit als eine Instanz zu erstellen? –

+1

Wenn Sie in std :: string Filter :: contents schreiben möchten, benötigen Sie eine Instanz. Wenn Sie in einen globalen Inhaltspuffer schreiben möchten, können Sie einfach die statische Handle-Methode oder eine freie Handle-Funktion verwenden. – hansmaad

+1

+1, das ist der Weg zu gehen. @ Prasanth Madhavan, zu dem 'Filter'' handle' wrde, wenn du keine Instanz erstellt hast? –

1

Ich bin mit curlpp:

std::stringstream result; 

request.setOpt(cURLpp::Options::WriteStream(&result)); 
request.perform(); 

dies die Antwort Webserver auf den String namens Ergebnis.