Mengakses anggota kelas dalam pernyataan if menggunakan std::is_same

Saya mencoba mengatasi masalah berikut: Saya ingin membuat pernyataan if yang melakukan sesuatu tergantung pada apakah argumen templat adalah objek tertentu atau bukan - dan jika ya, panggil fungsi anggota objek tersebut. Katakanlah saya ingin std::string

cuplikan:

#include <iostream>
#include <string>

template <typename T>
void is_string(const T& arg) {
    if (std::is_same<T, const std::string&>::value)
        std::cout << arg.length() << std::endl;
    else
        std::cout << "The argument is not a string" << std::endl;
}

int main() {
    is_string(0);
    return 0;
}

Itu tidak dapat dikompilasi, dengan kesalahan berikut:

types.cpp: In instantiation of ‘void is_string(const T&) [with T = int]’:
types.cpp:13:13:   required from here
types.cpp:7:13: error: request for member ‘length’ in ‘arg’, which is of non-class type ‘const int’
   std::cout << arg.length() << std::endl;

Saya rasa apa yang ingin saya capai mungkin tidak dapat dilakukan di C++11, tetapi saya akan menghargai beberapa saran tentang bagaimana melakukan hal seperti itu


person Jytug    schedule 12.11.2016    source sumber


Jawaban (2)


Dalam pernyataan if biasa, kedua cabang harus berupa kode yang valid. Dalam kasus Anda int.length() tidak masuk akal.

Di C++17 Anda cukup menggunakan constexpr if:

if constexpr(std::is_same<T, const std::string&>::value)
    std::cout << arg.length() << std::endl;
else
    std::cout << "The argument is not a string" << std::endl;

demo

Di C++11 (atau lebih lama) Anda dapat menggunakan kelebihan beban untuk mencapai hasil serupa:

void foo(std::string const& str){
    std::cout << str.length() << std::endl;
}

template<typename T>
void foo(T const&){
    std::cout << "The argument is not a string" << std::endl;
}

template <typename T>
void is_string(const T& arg) {
    foo(arg);
}

demo

person krzaq    schedule 12.11.2016

void is_string(const std::string& arg) {
  std::cout << arg.length() << std::endl;
}

template <typename T>
void is_string(const T& arg) {
  std::cout << "The argument is not a string" << std::endl;
}

Atau, lihat apakah kompiler Anda mendukung if constexpr C++17.

person Igor Tandetnik    schedule 12.11.2016