[英]What is the best way to implement a sql for retrieving multiple user names from same query?
我有一個產品表,其中包含3列created_user_id,updated_user_id和in_charge_user_id,所有這些都與我的用戶表相關,其中存儲了用戶的ID和名稱。
我想建立一個有效的查詢來獲取相應的user_id的名稱。
我到目前為止構建的查詢如下:
SELECT products.*,
(SELECT name FROM user WHERE user_id = products.created_user_id) as created_user,
(SELECT name FROM user WHERE user_id = products.updated_user_id) as updated_user,
(SELECT name FROM user WHERE user_id = products.in_charge_user_id) as in_charge_user
FROM products
此查詢的問題是,如果我有30,000條記錄,則每行要執行3個查詢。
有什么更有效的方法來實現這一目標? 我正在使用mysql。
對於每種類型的用戶ID(已創建,已更新,in_charge),您只需聯接一次users表:
SELECT
products.*,
u1.username AS created_username,
u2.username AS updated_username,,
u3.username AS in_charge_username,
FROM products
JOIN user u1 ON products.created_user_id = u1.user_id
JOIN user u2 ON products.updated_user_id = u2.user_id
LEFT JOIN user u3 ON products.in_charge_user_id = u3.user_id
這是獲取數據的最佳實踐方法。 它與您的子選擇查詢類似,但是我認為數據庫可以優化和利用更好的現代方法。
重要:
您需要在兩個表中的所有user_id字段上使用外鍵索引! 這樣,無論表中有多少行,查詢都將非常快。 這需要一個支持外鍵的引擎,例如InnoDB
。
LEFT JOIN
還是內INNER JOIN
?
由於其他答案表明是LEFT JOIN
,所以我不會做LEFT JOIN
。 如果您在產品表中有一個用戶ID,則在用戶表中必須有一個鏈接的user_id,除了in_charge_user只出現一次。 否則,數據將在語義上被破壞。 外鍵確保您始終具有鏈接的user_id,並且只有在沒有鏈接的產品時才能刪除user_id。 JOIN
等效於INNER JOIN
。
您可以使用LEFT JOIN代替子選擇。
您的查詢應類似於:
SELECT
P.*,
[CU].[name],
[UU].[name],
[CU].[name]
FROM products AS [P]
LEFT JOIN user AS [CU] ON [CU].[user_id] = [P].[created_user_id]
LEFT JOIN user AS [UU] ON [UU].[user_id] = [P].[updated_user_id]
LEFT JOIN user AS [CU] ON [CU].[user_id] = [P].[in_charge_user_id]
首先,您的查詢應該沒問題。 您只需要在user(user_id)
或更好的user(user_id, name)
上建立索引以提高性能。 我想第一個存在。
其次,您可以使用LEFT JOIN
編寫此代碼:
SELECT p.*, uc.name as created_user,
uu.name as updated_user, uin.name as in_charge_user
FROM products p LEFT JOIN
user uc
ON uc.user_id = p.created_user_id LEFT JOIN
user uu
ON uu.user_id = p.updated_user_id LEFT JOIN
user uin
ON uin.user_id = p.in_charge_user_id;
使用上述指標之一,這兩種方法應具有非常相似的性能。
還要注意使用LEFT JOIN
。 這可以處理一個或多個用戶ID丟失的情況。
嘗試以下查詢
SELECT products.*, c.name as created_user,u.name as updated_user,i.name as in_charge_user
FROM products left join user c on(products.created_user_id=c.user_id ) left join user u on(products.updated_user_id=u.user_id ) left join user u on(products.in_charge_user_id=i.user_id )
同樣,正如Gordon Linoff提到的,在用戶表上創建索引將更快地獲取數據。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.