Saya punya metode generik dengan kode (dummy) ini (ya saya sadar IList memiliki predikat, tetapi kode saya tidak menggunakan IList tetapi beberapa koleksi lain, toh ini tidak relevan untuk pertanyaan ...)
static T FindThing<T>(IList collection, int id) where T : IThing, new()
{
foreach T thing in collecion
{
if (thing.Id == id)
return thing;
}
return null; // ERROR: Cannot convert null to type parameter 'T' because it could be a value type. Consider using 'default(T)' instead.
}
Ini memberi saya kesalahan build
"Tidak dapat mengonversi nol untuk mengetik parameter 'T' karena itu bisa menjadi tipe nilai. Sebagai gantinya gunakan 'default (T)'."
Bisakah saya menghindari kesalahan ini?
null
terlepas dari apakahT
iniObject
atauint
atauchar
.Jawaban:
Dua pilihan:
default(T)
yang berarti Anda akan kembalinull
jika T adalah tipe referensi (atau tipe nilai yang dapat dibatalkan),0
untukint
,'\0'
untukchar
, dll. ( Tabel nilai default (C # Referensi) )where T : class
kendala dan kemudian kembalinull
seperti biasasumber
Nullable<int>
atauNullable<DateTime>
sebaliknya. Jika Anda menggunakan jenis yang tidak dapat dibatalkan dan harus mewakili nilai nol, Anda hanya meminta masalah.sumber
Anda bisa menyesuaikan batasan Anda:
Kemudian mengembalikan nol diizinkan.
sumber
IDisposable
. Ya, sebagian besar waktu tidak harus begitu.System.String
tidak menerapkanIDisposable
, misalnya. Penjawab seharusnya menjelaskan itu, tetapi itu tidak membuat jawaban salah. :)Tambahkan batasan kelas sebagai kendala pertama untuk tipe generik Anda.
sumber
Jika Anda memiliki objek maka perlu mengetikkan
jika Anda perlu mengembalikan nol.
sumber
Di bawah ini adalah dua opsi yang dapat Anda gunakan
atau
sumber
Pilihan Anda yang lain adalah menambahkan ini di akhir deklarasi Anda:
Dengan begitu itu akan memungkinkan Anda untuk mengembalikan nol.
sumber
where T : class, IList
. Jika Anda memiliki kendala untuk berbagai jenis, Anda mengulangi tokenwhere
, seperti padawhere TFoo : class where TBar : IList
.solusi dari karya TheSoftwareJedi,
Anda juga dapat mengarsipkannya dengan menggunakan beberapa tipe nilai dan nullable:
sumber
Ambil rekomendasi kesalahan ... dan baik pengguna
default(T)
ataunew T
.Anda harus menambahkan perbandingan dalam kode Anda untuk memastikan bahwa itu adalah kecocokan yang valid jika Anda menggunakan rute itu.
Kalau tidak, berpotensi mempertimbangkan parameter output untuk "kecocokan ditemukan".
sumber
Berikut adalah contoh yang berfungsi untuk nilai pengembalian Nullable Enum:
sumber
where TEnum : struct, Enum
. Ini memastikan bahwa penelepon tidak sengaja memberikan tipe nilai yang bukan enum (seperti aint
atau aDateTime
).Alternatif lain untuk 2 jawaban yang disajikan di atas. Jika Anda mengubah jenis pengembalian menjadi
object
, Anda dapat kembalinull
, sementara pada saat yang sama memberikan pengembalian non-nol.sumber
Demi kelengkapan, ada baiknya mengetahui Anda juga bisa melakukan ini:
Ini mengembalikan sama dengan
return default(T);
sumber
Bagi saya ini berfungsi sebagaimana adanya. Di mana tepatnya masalahnya?
sumber