iT邦幫忙

0

資料庫如何用簡短的SQL指令更新欄位資料

  • 分享至 

  • xImage

小弟我有一張表紀錄著以下資訊

id | customerID | customer_cardnumber | default
------------- | -------------
1 | A00001 | 123456 | NO
2 | A00002 | 015986 | YES
3 | A00001 | 111589 | YES
4 | B00001 | 044867 | YES

假如今天我要將A00001的123456卡號改為預設,並將A00001的111589卡號設為非預設
像這樣的內容
id | customerID | customer_cardnumber | default
------------- | -------------
1 | A00001 | 123456 | YES
2 | A00002 | 015986 | YES
3 | A00001 | 111589 | NO
4 | B00001 | 044867 | YES

我目前的作法是像這樣

UPDATE customers SET default='NO' WHERE customerID='A00001' and customer_cardnumber = '111589';
UPDATE customers SET default='YES' WHERE customerID='A00001' and customer_cardnumber = '123456';

想問說有沒有更好的SQL寫法,感覺我的寫法不是很好

卡不一定一張啊,所以保險的就是先
UPDATE customers SET default='NO' WHERE customerID='A00001';

然後新的預設卡號有可能不存在啊,
跑 INSERT INTO 一下
INSERT INTO customers
(customerID, customer_cardnumber, default)
VALUES ('A00001','123456','YES');

基本上因為卡號不重複且索引,
所以有紀錄上面會失敗,再跑一次 UPDATE
UPDATE customers
SET default='YES'
WHERE customer_cardnumber='123456';

好吧,我承認我是來亂的,但真的要考慮這些條件喔,因為真的會發生
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中
1
froce
iT邦大師 1 級 ‧ 2022-11-08 14:12:16
最佳解答
UPDATE customers 
SET `default` = case 
                  when `default` = 'NO' then 'YES' else 'NO'
                end
where (`customer_cardnumber` = '123456' OR `default` = 'YES') and `customerID` ='A00001' ;

這樣直接做switch會不會比較方便?

看更多先前的回應...收起先前的回應...
froce iT邦大師 1 級 ‧ 2022-11-09 08:49:39 檢舉

改了一下,這樣你做stored procedure只需要2個參數,也比較合理。
昨天被你寫的誤導,其實依你的需求應該是要輸入顧客ID,解除原本預設卡號,將新卡號設成預設。

另外預設那個欄位建議規劃為布林值

phes11434 iT邦新手 2 級 ‧ 2022-11-09 10:06:04 檢舉

感謝你提出的建議

froce iT邦大師 1 級 ‧ 2022-11-09 10:12:06 檢舉

我在sql online裡操作是正常的。
https://sqliteonline.com/
你自己用建議先對where的條件自己先select一下。

CREATE TABLE IF NOT EXISTS `customers` (
  `id` int(6) unsigned NOT NULL,
  `customerID` char(6) NOT NULL,
  `customer_cardnumber` char(6) NOT NULL,
  `default` varchar(3) NOT NULL,
  PRIMARY KEY (`id`)
) DEFAULT CHARSET=utf8;
INSERT INTO `customers` (`id`, `customerID`, `customer_cardnumber`, `default`) VALUES
(1, 'A00001', '123456', 'NO'),
(2, 'A00002', '015986', 'YES'),
(3, 'A00001', '111589', 'YES'),
(4, 'B00001', '044867', 'YES');

UPDATE customers 
SET `default` = case 
                  when `default` = 'NO' then 'YES' else 'NO'
                end
where (`customer_cardnumber` = '123456' OR `default` = 'YES') and `customerID` ='A00001' ;
phes11434 iT邦新手 2 級 ‧ 2022-11-09 10:23:26 檢舉

我手誤打錯字,才跑不出來,已解決,感謝

小山丘 iT邦新手 2 級 ‧ 2022-11-09 17:09:53 檢舉

確定只會有兩張卡?
A00001多了一張卡這個就行不通了

froce iT邦大師 1 級 ‧ 2022-11-09 17:19:14 檢舉

沒有喔,我的篩選條件是A0001裡,default是YES的和特定卡號切換狀態。
應該不會有你說的多了一張卡就不行。

倒是要先確定要設定的卡不是預設的卡就是了,要不然default的值會出錯

0
小山丘
iT邦新手 2 級 ‧ 2022-11-08 12:03:38
  UPDATE customers 
  SET default =CASE WHEN customer_cardnumber='111589' THEN 'NO' 
                    WHEN customer_cardnumber='123456' THEN 'YES' 
               ELSE default END
  WHERE customerID='A00001'

我是覺得你原本那樣就好
然後欄位命名盡量不要使用到關鍵字比較好

phes11434 iT邦新手 2 級 ‧ 2022-11-08 12:25:48 檢舉

欄位名稱我是用中文,只是發問改成英文,臨時想到default這單字就用了,感謝提醒
主要感覺我的寫法有點多(兩段式)

用中文也不好啦!!!!

0
ckp6250
iT邦好手 1 級 ‧ 2022-11-08 14:54:26

如果customerID,customer_cardnumber都有設索引的話,這樣應該也很效率。

replace into customers ('A00001','111589','NO'),('A00001','123446','YES');
0

這邊,其實我看起來你有錯誤的行為認知。

尋求簡短的用法並不是不好的事。
只是...這得要看你的操作行為及指向過程而決定。

就你的問題來看
「將A00001的123456卡號改為預設,
並將A00001的111589卡號設為非預設」

先思考你的操作動作行為。要達到你上面說的操作行為,只有一種模式。
就是按一行執行兩個動作。
這樣來去思考同時動的簡化SQL語法。這樣是對的。

可是,有可能每一次都是123456跟111589嘛??連動的原理在哪??
這沒有其對應的規則。

所以我會將其視為兩次操作動作。
這樣子的話。
其實你的

UPDATE customers SET default='NO' WHERE customerID='A00001' and customer_cardnumber = '111589';
UPDATE customers SET default='YES' WHERE customerID='A00001' and customer_cardnumber = '123456';

並不會不好。而且認真來說。如果就程式來看待的話。你也只會有一段參數化的程式碼。只是運行了兩次動作。

當然了,這邊是指行為操作。
但如果是下SQL語法直接操作的話。
一般多重條件的設定不同值的情況下。少量值可以搭配IF。多量值可以搭配CASE。
但一般我並不建議將SQL語法當程式設計使用。

froce iT邦大師 1 級 ‧ 2022-11-09 08:55:31 檢舉

嘛...其實他想做的應該是我上面後來改過的,解除預設卡號並加入新卡號,這個的確一步就能做到了,而且有時候拆成兩步會有其他衍生問題像是第一步做完第二步還沒做就出問題了。
資料庫的操作尤其是寫入我個人是覺得能一步做最好就是一步做,這樣可以享受資料庫的原子性,除非真的太複雜。

切換對應式嘛?
這的確有可能。

phes11434 iT邦新手 2 級 ‧ 2022-11-09 09:38:39 檢舉

froce你的建議很讚

我要發表回答

立即登入回答