Rumah > pangkalan data > tutorial mysql > Bagaimanakah Saya Boleh Menggunakan Pernyataan CASE Dengan Betul dalam Klausa WHERE dalam SQL Server 2008?

Bagaimanakah Saya Boleh Menggunakan Pernyataan CASE Dengan Betul dalam Klausa WHERE dalam SQL Server 2008?

Mary-Kate Olsen
Lepaskan: 2025-01-11 09:54:42
asal
747 orang telah melayarinya

How Can I Correctly Use CASE Statements Within WHERE Clauses in SQL Server 2008?

Mengatasi Isu Pernyataan KES dalam SQL Server 2008 WHERE Klausa

Menggunakan pernyataan CASE dalam klausa WHERE dalam SQL Server 2008 boleh menimbulkan kesukaran. Pertanyaan berikut menunjukkan masalah biasa:

<code class="language-sql">SELECT
    tl.storenum 'Store #', 
    co.ccnum 'FuelFirst Card #', 
    co.dtentered 'Date Entered',
    CASE st.reasonid 
        WHEN 1 THEN 'Active' 
        WHEN 2 THEN 'Not Active' 
        WHEN 0 THEN st.ccstatustypename 
        ELSE 'Unknown' 
    END 'Status',
    CASE st.ccstatustypename 
        WHEN 'Active' THEN ' ' 
        WHEN 'Not Active' THEN ' ' 
        ELSE st.ccstatustypename 
    END 'Reason',
    UPPER(REPLACE(REPLACE(co.personentered,'RT\\',''),'RACETRAC\\','')) 'Person Entered',
    co.comments 'Comments or Notes'
FROM 
    comments co
    INNER JOIN cards cc ON co.ccnum=cc.ccnum
    INNER JOIN customerinfo ci ON cc.customerinfoid=ci.customerinfoid
    INNER JOIN ccstatustype st ON st.ccstatustypeid=cc.ccstatustypeid
    INNER JOIN customerstatus cs ON cs.customerstatuscd=ci.customerstatuscd
    INNER JOIN transactionlog tl ON tl.transactionlogid=co.transactionlogid
    LEFT JOIN stores s ON s.StoreNum = tl.StoreNum
WHERE 
    CASE LEN('TestPerson')
        WHEN 0 THEN co.personentered  = co.personentered
        ELSE co.personentered LIKE '%TestPerson'
    END 
    AND cc.ccnum = CASE LEN('TestFFNum')
        WHEN 0 THEN cc.ccnum 
        ELSE 'TestFFNum' 
    END 
    AND CASE LEN('2011-01-09 11:56:29.327') 
        WHEN 0 THEN co.DTEntered = co.DTEntered 
        ELSE 
            CASE LEN('2012-01-09 11:56:29.327') 
                WHEN 0 THEN co.DTEntered >= '2011-01-09 11:56:29.327' 
                ELSE co.DTEntered BETWEEN '2011-01-09 11:56:29.327' AND '2012-01-09 11:56:29.327' 
            END 
    END
    AND tl.storenum < 699 
ORDER BY tl.StoreNum</code>
Salin selepas log masuk

Penyelesaian: Pemfaktoran Semula dengan Logik Boolean

Isu teras terletak pada penggunaan pernyataan CASE yang tidak sesuai secara langsung dalam logik bersyarat klausa WHERE. Ungkapan CASE harus menghasilkan nilai; ia tidak sepatutnya menjadi keseluruhan syarat.

Penyelesaian melibatkan menggantikan pernyataan CASE dengan logik boolean yang setara menggunakan operator AND dan OR:

<code class="language-sql">SELECT
    tl.storenum 'Store #', 
    co.ccnum 'FuelFirst Card #', 
    co.dtentered 'Date Entered',
    CASE st.reasonid 
        WHEN 1 THEN 'Active' 
        WHEN 2 THEN 'Not Active' 
        WHEN 0 THEN st.ccstatustypename 
        ELSE 'Unknown' 
    END 'Status',
    CASE st.ccstatustypename 
        WHEN 'Active' THEN ' ' 
        WHEN 'Not Active' THEN ' ' 
        ELSE st.ccstatustypename 
    END 'Reason',
    UPPER(REPLACE(REPLACE(co.personentered,'RT\\',''),'RACETRAC\\','')) 'Person Entered',
    co.comments 'Comments or Notes'
FROM 
    comments co
    INNER JOIN cards cc ON co.ccnum=cc.ccnum
    INNER JOIN customerinfo ci ON cc.customerinfoid=ci.customerinfoid
    INNER JOIN ccstatustype st ON st.ccstatustypeid=cc.ccstatustypeid
    INNER JOIN customerstatus cs ON cs.customerstatuscd=ci.customerstatuscd
    INNER JOIN transactionlog tl ON tl.transactionlogid=co.transactionlogid
    LEFT JOIN stores s ON s.StoreNum = tl.StoreNum
WHERE 
    (LEN('TestPerson') = 0 AND co.personentered = co.personentered) OR (LEN('TestPerson') > 0 AND co.personentered LIKE '%TestPerson')
    AND ((LEN('TestFFNum') = 0 AND cc.ccnum = cc.ccnum) OR (LEN('TestFFNum') > 0 AND cc.ccnum = 'TestFFNum'))
    AND ((LEN('2011-01-09 11:56:29.327') = 0 AND co.DTEntered = co.DTEntered) OR (LEN('2012-01-09 11:56:29.327') = 0 AND co.DTEntered >= '2011-01-09 11:56:29.327') OR (co.DTEntered BETWEEN '2011-01-09 11:56:29.327' AND '2012-01-09 11:56:29.327'))
    AND tl.storenum < 699
ORDER BY tl.StoreNum;</code>
Salin selepas log masuk

Peningkatan Prestasi

Sementara pertanyaan yang diperbetulkan ini berfungsi dengan betul, prestasi boleh dipertingkatkan lagi:

  • Kurangkan Bersarang: Keadaan OR bersarang dalam boleh menjadi kurang cekap. Pertimbangkan struktur pertanyaan alternatif (cth., menggunakan UNION ALL untuk kriteria carian yang berbeza).
  • Pengindeksan: Pastikan indeks wujud pada lajur yang kerap digunakan dalam fasal WHERE (cth., co.personentered, cc.ccnum, co.DTEntered, tl.storenum).
  • Parameterisasi: Jika nilai 'Ujian' ini ialah pembolehubah, gunakan pertanyaan berparameter untuk mengelakkan penghuraian pertanyaan berulang.

Dengan menangani perkara ini, anda boleh mencipta pertanyaan SQL yang lebih cekap dan boleh dibaca.

Atas ialah kandungan terperinci Bagaimanakah Saya Boleh Menggunakan Pernyataan CASE Dengan Betul dalam Klausa WHERE dalam SQL Server 2008?. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

sumber:php.cn
Kenyataan Laman Web ini
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn
Artikel terbaru oleh pengarang
Tutorial Popular
Lagi>
Muat turun terkini
Lagi>
kesan web
Kod sumber laman web
Bahan laman web
Templat hujung hadapan