टेम्पर्ड प्रकारों के साथ पैरामीटर के रूप में फ़ंक्शन को स्वीकार करना

Dec 18 2020

प्रोग्रामिंग और सी ++ के लिए काफी नया है। मेरे पास एक फ़ंक्शन है जो मैं फ़ंक्शन-पॉइंटर्स को अस्थायी मानों के साथ तर्क के रूप में स्वीकार करना चाहता हूं। यही है जो मेरा मतलब है...

मेरा यह कार्य है:

template<typename... ColumnTypes, typename... ParameterTypes>
   void query(std::function<void(bool success, ozo::rows_of<ColumnTypes...>& results)> callback, const 
   std::string& query, ParameterTypes&& ... parameters);

"ozo :: row_of" के लिए उपनाम है:

template <typename ... Ts>
   std::vector<std::tuple<Ts...>> 

मैं चाहता हूं कि प्रत्येक क्वेरी को कॉलबैक प्रदान किया जाए, यह कॉलबैक विभिन्न प्रकारों को स्वीकार करने में सक्षम होगा। उदा। "ColumnTypes"

मैंने क्या प्रयास किया है:

void myfunc(bool succeeded, ozo::rows_of<int>& results)
{
     //code
}

postgres_caller->query(myfunc, "SELECT length FROM this_table WHERE id > $1 AND id < $2;", 11, 14);

परिणाम:

.cpp:241:26: error: no matching member function for call to 'query'
    postgres_caller->query(myfunc, "SELECT length FROM this_table WHERE id > $1 AND id < $2;", 11, 14);
    ~~~~~~~~~~~~~~~~~^~~~~

.h: 165: 22: ध्यान दें: उम्मीदवार टेम्पलेट को नजरअंदाज किया गया: 'फ़ंक्शन <void (बूल, वेक्टर <tuple <टाइप-पैरामीटर-0-0 ...), एलोकेटर <tuple <टाइप-पैरामीटर-0-0 से मेल नहीं खा सका ... >> :: फ़ंक्शन <शून्य (bool सफलता, ozo :: row_of <ColumnTypes ...> और परिणाम)> कॉलबैक, const std :: string & query, ParameterTypes && ... पैरामीटर)

मैंने मेमने के साथ भी कोशिश की:

postgres_caller->query([](bool succeeded, ozo::rows_of<int>& results)
                            {
                                //code
                            }, "SELECT length FROM this_table WHERE id > $1 AND id < $2;", 11, 14);

परिणाम:

error: no matching member function for call to 'query'
    postgres_caller->query([](bool succeeded, ozo::rows_of<int>& results)
    ~~~~~~~~~~~~~~~~~^~~~~

.h: 165: 22: ध्यान दें: उम्मीदवार टेम्पलेट को नजरअंदाज किया गया: 'फ़ंक्शन <void (बूल, वेक्टर <tuple <टाइप-पैरामीटर-0-0 ...), एलोकेटर <tuple <टाइप-पैरामीटर-0-0 से मेल नहीं खा सका ... >> परिणाम)> कॉलबैक, const std :: string & query, ParameterTypes && ... पैरामीटर) ^

क्या यह उल्लेखनीय है और यह कैसे किया जा सकता है? बहुत सराहना की। / जॉन

जवाब

1 super Dec 18 2020 at 23:02

टेम्पलेट कटौती केवल आपके द्वारा पास किए जाने वाले सटीक प्रकार पर काम करती है, इसलिए यदि आप किसी फ़ंक्शन पॉइंटर में पास होते हैं, तो टेम्पलेट std::functionउस फ़ंक्शन पॉइंटर को किस प्रकार कन्वर्ट करने के लिए घटा नहीं सकता है।

उपयोग करने के बजाय कॉल करने योग्य टेम्पलेट पैरामीटर बनाएं std::function

template<typename Callable, typename... ParameterTypes>
void query(Callable callback, const std::string& query, ParameterTypes&& ... parameters) {
    callback( ... ); // use it like this
}

अधिकांश समय आपको कॉलबैक के हस्ताक्षर को हटाने की आवश्यकता नहीं होती है। बस इसे उन तर्कों के साथ कहें, जिनकी आप अपेक्षा करते हैं।

यदि यह पर्याप्त नहीं है, तो कॉलबैक के हस्ताक्षर के रूप में अच्छी तरह से कटौती करने के तरीके हैं, लेकिन यह थोड़ा और अधिक वर्बोस हो जाता है और अधिकांश समय कोई वास्तविक उद्देश्य नहीं होता है।