Sqlserver
 sql >> Teknologi Basis Data >  >> RDS >> Sqlserver

Membandingkan tanggal yang disimpan sebagai varchar

Menyimpan nilai tanggal sebagai varchar sangatlah salah.

Jika memungkinkan, Anda harus mengubah tabel untuk menyimpannya sebagai tipe data tanggal.
Anda dapat melakukannya dalam beberapa langkah sederhana:

  1. Ganti nama kolom saat ini (saya menduga ScheduleStartDate juga varchar) menjadi columnName_old. Ini dapat dengan mudah dilakukan dengan menggunakan sp_rename .

  2. Gunakan alter table untuk menambahkan kolom dengan tipe data yang sesuai.

  3. Salin nilai dari kolom lama ke kolom baru menggunakan pernyataan pembaruan. Karena semua tanggal disimpan dalam format yang sama, Anda dapat menggunakan convert seperti ini:set ScheduleStartDate = convert(date, NULLIF(ltrim(rtrim(ScheduleStartDate_old)), ''), 103) Jika versi server sql Anda 2012 atau lebih tinggi, gunakan try_convert . Catatan saya telah menggunakan nullif , ltrim dan rtrim untuk mengonversi nilai yang hanya berisi spasi putih menjadi nol.
  4. Lepaskan dan buat ulang indeks yang mereferensikan kolom ini. Cara termudah untuk melakukannya adalah dengan mengklik kanan indeks pada SSMS dan memilih script index as -> drop and create .
  5. Gunakan alter table untuk menghapus kolom lama.

Catatan: jika kolom ini direferensikan ke objek lain di database, Anda juga harus mengubah objek ini. Ini termasuk prosedur tersimpan, kunci asing, dll`.

Jika Anda tidak dapat mengubah jenis data kolom, dan versi server sql Anda lebih rendah dari 2012, Anda perlu menggunakan konversi seperti ini:

SELECT * FROM tblServiceUsersSchedule 
WHERE CONVERT(DATE, NULLIF(ScheduleEndDate, RTRIM(LTRIM('')), 103) 
      < CAST(GETDATE() As Date);
AND ScheduleEndDate IS NOT NULL

Perhatikan bahwa jika Anda memiliki bahkan satu baris di mana data kolom tidak dalam format hh/bb/tttt, ini akan menimbulkan kesalahan.

Untuk sql server versi 2012 atau lebih tinggi, gunakan Try_convert . Fungsi ini hanya akan mengembalikan null jika konversi gagal:

SELECT * FROM tblServiceUsersSchedule 
WHERE TRY_CONVERT(DATE, NULLIF(ScheduleEndDate, RTRIM(LTRIM('')), 103)
      < CAST(GETDATE() As Date);
AND ScheduleEndDate IS NOT NULL

Catatan: Saya telah menggunakan CAST(GETDATE() as Date) untuk menghapus bagian waktu dari tanggal saat ini. Ini berarti Anda hanya akan mendapatkan catatan di mana ScheduleEndDate setidaknya berumur satu hari. Jika Anda ingin juga mendapatkan catatan di mana ScheduleEndDate hari ini, gunakan <= bukannya < .

Satu hal terakhir: Menggunakan fungsi pada kolom dalam klausa where akan mencegah Sql Server menggunakan pengindeksan apa pun pada kolom ini.
Ini adalah alasan lain mengapa Anda harus mengubah kolom ke tipe data yang sesuai.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Pemecahan Masalah Replikasi Transaksional SQL Server

  2. Klausa WHERE bersyarat di SQL Server

  3. Gunakan TYPEPROPERTY() untuk Mengembalikan Informasi tentang Tipe Data di SQL Server

  4. PHP, ORM, MSSQL dan Unicode, apakah mungkin untuk membuat ini bekerja bersama?

  5. Bagaimana cara menggunakan alias di klausa where?