C ++ 20 diperkenalkan secara eksplisit (bool) yang dipilih secara kondisional pada waktu kompilasi apakah konstruktor dibuat eksplisit atau tidak.
Di bawah ini adalah contoh yang saya temukan di sini .
struct foo {
// Specify non-integral types (strings, floats, etc.) require explicit construction.
template <typename T>
explicit(!std::is_integral_v<T>) foo(T) {}
};
foo a = 123; // OK
foo b = "123"; // ERROR: explicit constructor is not a candidate (explicit specifier evaluates to true)
foo c {"123"}; // OK
Adakah yang bisa memberi tahu saya usecase explicit (bool)
lain selain menggunakan std::is_integral
?
tuple
fitur ini.Jawaban:
Motivasi itu sendiri dapat dilihat di koran .
Ada kebutuhan untuk membuat konstruktor eksplisit secara kondisional. Anda ingin:
Yang pertama baik-baik saja, konstruktor itu implisit. Tapi yang terakhir akan buruk, konstruktor itu
explicit
. Dengan C ++ 17 (atau C ++ 20 dengan konsep), satu-satunya cara untuk membuat karya ini adalah dengan menulis dua konstruktor - satuexplicit
dan satu tidak:Ini hampir seluruhnya digandakan - dan definisi konstruktor ini akan sama.
Dengan
explicit(bool)
, Anda bisa menulis konstruktor tunggal - dengan bagian eksplisit kondisional dari konstruksi dilokalkan keexplicit
-specifier:Maksud kecocokan ini lebih baik, lebih sedikit kode untuk ditulis, dan lebih sedikit pekerjaan yang harus dilakukan oleh kompiler selama resolusi kelebihan (karena ada lebih sedikit konstruktor yang harus dipilih).
sumber
enable_if_t
bagian menjadi kendala yang lebih cantik dan sederhana, mungkin menggunakan konsep. Tapi bukan itu inti dari pertanyaan ini.Kemungkinan penggunaan lain yang saya lihat adalah dengan template variadic:
Secara umum, baik untuk memiliki
explicit
konstruktor dengan hanya satu argumen (kecuali konversi diinginkan).begitu
sumber
Saya dapat melihat use case untuk mensyaratkan secara
explicit
kondisional ketika input mungkin berupa tipe tampilan (pointer mentah,std::string_view
) yang akan ditampung oleh objek baru setelah panggilan (hanya menyalin tampilan, bukan apa yang merujuk, tetap bergantung pada masa pakai objek yang dilihat), atau mungkin tipe seperti nilai (mengambil kepemilikan salinan, tanpa dependensi masa pakai eksternal).Dalam situasi seperti itu, penelepon bertanggung jawab untuk menjaga objek yang dilihat tetap hidup (callee memiliki pandangan, bukan objek asli), dan konversi tidak boleh dilakukan secara implisit, karena itu membuatnya terlalu mudah untuk objek yang secara implisit dibuat untuk hidup lebih lama dari objek yang dilihatnya. Sebaliknya, untuk tipe nilai, objek baru akan menerima salinannya sendiri, jadi meskipun salinan itu mahal, itu tidak akan membuat kode salah jika konversi implisit terjadi.
sumber