Ada paradoks dalam deskripsi pengecualian: Objek nullable harus memiliki nilai (?!)
Ini masalahnya:
Saya punya DateTimeExtended
kelas, ya sudah
{
DateTime? MyDataTime;
int? otherdata;
}
dan seorang konstruktor
DateTimeExtended(DateTimeExtended myNewDT)
{
this.MyDateTime = myNewDT.MyDateTime.Value;
this.otherdata = myNewDT.otherdata;
}
menjalankan kode ini
DateTimeExtended res = new DateTimeExtended(oldDTE);
melempar InvalidOperationException
dengan pesan:
Objek nullable harus memiliki nilai.
myNewDT.MyDateTime.Value
- valid dan mengandung DateTime
objek biasa .
Apa arti dari pesan ini dan apa yang saya lakukan salah?
Perhatikan oldDTE
tidak null
. Saya telah menghapus Value
dari myNewDT.MyDateTime
tetapi pengecualian yang sama dilempar karena setter yang dihasilkan.
Jawaban:
Anda harus mengubah jalur
this.MyDateTime = myNewDT.MyDateTime.Value;
menjadi adilthis.MyDateTime = myNewDT.MyDateTime;
Pengecualian yang Anda terima dilemparkan ke dalam
.Value
properti NullableDateTime
, karena diharuskan untuk mengembalikan aDateTime
(karena itulah kontrak untuk.Value
negara bagian), tetapi tidak dapat melakukannya karena tidak adaDateTime
untuk kembali, sehingga mengeluarkan pengecualian.Secara umum, itu adalah ide yang buruk untuk secara membabi buta memanggil
.Value
tipe nullable, kecuali Anda memiliki pengetahuan sebelumnya bahwa variabel itu HARUS mengandung nilai (yaitu melalui.HasValue
cek).EDIT
Berikut kode untuk
DateTimeExtended
itu tidak membuang pengecualian:Saya mengujinya seperti ini:
Menambahkan
.Value
padaother.MyDateTime
menyebabkan pengecualian. Menghapusnya menghilangkan pengecualian. Saya pikir Anda mencari di tempat yang salah.sumber
.Value
objek null masuk akal (saya kira), tetapi pesan pengecualian benar-benar menyesatkan jika Anda berhadapan dengan dua objek Nullable. Sesuatu seperti 'Properti .Value membutuhkan objek yang bukan nol' akan lebih masuk akal.Saat menggunakan metode ekstensi LINQ (misalnya
Select
,Where
), fungsi lambda mungkin dikonversi ke SQL yang mungkin tidak berperilaku identik dengan kode C # Anda. Sebagai contoh, hubung singkat C # dievaluasi&&
dan||
dikonversi ke SQLAND
danOR
. Ini dapat menyebabkan masalah saat Anda memeriksa null di lambda Anda.Contoh:
sumber
Coba jatuhkan
.value
sumber
Dalam hal ini oldDTE adalah null, jadi ketika Anda mencoba mengakses oldDTE.Value InvalidOperationException dilempar karena tidak ada nilai. Dalam contoh Anda, Anda dapat melakukannya:
sumber
Tetapkan anggota secara langsung tanpa
.Value
bagian:sumber
Sepertinya oldDTE.MyDateTime adalah nol, jadi konstruktor mencoba mengambil nilainya - yang dilemparkan.
sumber
Saya mendapat pesan ini ketika mencoba mengakses nilai-nilai objek bernilai nol.
ini akan menghasilkan kesalahan. Pertama, Anda harus memeriksa apakah objek tidak null
Ini bekerja.
sumber
this.MyDateTime = myNewDT.MyDateTime.Value;
, bukansName = myObj.Name;
Saya mendapat solusi ini dan itu berfungsi untuk saya
sumber