簡體   English   中英

mySQL 查詢有點麻煩

[英]A bit of trouble with mySQL querying

假設我有一個名為“ users ”的表,其中包含系統的所有用戶。 每個用戶都有一個“ role由”定義“ roles ,除了”一欄為“ name ”和“ id ”列。 每個角色為“ worker ”的用戶都由“ supervisor ”提供建議,如“ advised_by ”列所定義。

我想查詢我的數據庫,以便它返回工作人員和他們的主管的姓名和一行,這可能沒有連接嗎?

感謝您的任何建議,我一直在反對這個問題一段時間了

編輯:感謝所有試圖提供幫助的人。 抱歉,我想回想起來,這是一個非常模糊/糟糕的描述。 我會在這里嘗試更好地建模表格。

列:名稱、ID、角色、Advised_by

第 1 行:Bob,123,工人,321

第 2 行:Tom,321,主管,不適用

我想返回所有標記為“工人”的人的結果,以及他們的姓名和主管的姓名,例如:Bob、Worker、Tom 在一行中。 我試圖避免添加連接,因為我的教授要求我們不要因為性能下降而使用它們,但似乎沒有可行的方法來解決它,在這種情況下,我會接受連接。

編輯 2:猜猜我只是一個白痴,我意識到在我全部輸入之后我可以很容易地使用別名來完成它。 抱歉給麻煩的人

需要更多詳細信息,但您需要加入該表以在一個 MySQL 語句中同時獲取主管和工作人員的姓名。

假設advised_by 列包含為該worker 提供建議的用戶的ID:

SELECT u.id, u.name, u2.id AS supervisorID, u2.name AS supervisorNAME 
FROM users u, users u2 
WHERE u.advised_by = u2.id AND u.role = 'worker'

冒着重復 EpochGalaxy 提供的答案的風險......

問:沒有連接可以嗎?

答:是的。 有可能的。 一種方法是使用相關子查詢。

考慮您需要運行以獲取主管姓名的查詢...

 SELECT s.name
   FROM users s
  WHERE s.id = 321

如果您對從用戶那里檢索到的每一行都運行這樣的查詢會怎樣。

假設您運行這樣的查詢:

SELECT u.id
     , u.name
     , u.role
     , u.advised_by
  FROM users u
 ORDER BY u.id

對於該查詢中的每一行,就在您返回它之前,您運行一個查詢以獲取主管的姓名。

我們可以通過在 SELECT 列表中使用子查詢來實現這一點。

作為在 SELECT 列表中運行子查詢的一個簡單示例,請考慮此查詢。 (我們運行這樣的查詢沒有合乎邏輯的理由,但作為一個簡單的演示,我們可以運行一個子查詢......

SELECT u.id
     , u.name
     , u.role
     , u.advised_by
     , ( SELECT 'bar' ) AS foo
  FROM users u
 ORDER BY u.id

此查詢返回的行將包含一個名為 foo 的附加列。 分配給列的值將從子查詢的結果中提供...“SELECT 'bar'”。

現在我們知道我們可以在 SELECT 列表中運行一個子查詢,並返回一列,我們可以嘗試其他的東西。 像這樣:

SELECT u.id
     , u.name
     , u.role
     , u.advised_by
     , ( SELECT s.name
           FROM users s
          WHERE s.id = 321
       ) AS s_name
  FROM users u
 ORDER BY u.id

這樣,對於外部查詢返回的每一行,MySQL 都會運行 SELECT 列表中的子查詢,並取子查詢返回的值,並將返回的值放入外部查詢返回的行的列中。

該子查詢將僅從 id = 321 的用戶行中獲取名稱。

所以這並沒有真正讓我們得到我們需要的東西。

這就是訣竅……我們可以在那里放置一個表達式,而不是文字值 321,該表達式包含對外部查詢中的表的引用。

SELECT u.id
     , u.name
     , u.role
     , u.advised_by
     , ( SELECT s.name
           FROM users s
          WHERE s.id = u.advised_by
       ) AS s_name
  FROM users u
 ORDER BY u.id

啊哈!

現在,對於外部查詢返回的每一行,MySQL 將在 SELECT this 中運行子查詢。

這一次,子查詢包含對來自外部查詢行的 advisor_by 列的引用。 MySQL 將從被返回的行(由外部查詢)中獲取 dvised_by 列中的值,然后在子查詢執行之前將其滑入子查詢。 子查詢的返回進入結果集的列。

這樣,我們從 sbuquery 獲得的結果由外部查詢中的值決定。 子查詢外部查詢相關。

注意事項的一些重要限制: 另一個查詢的 SELECT 列表中的子查詢必須正好返回列。 (它可以是一個表達式,一個字面量。但是子查詢的返回不允許返回兩列或更多列。

子查詢必須返回不超過一行。 如果它返回零行,則將 NULL 值分配給外部查詢中的列。

上例中的子查詢滿足條件。 SELECT 列表中只有一個表達式,並且 id 列在 users 表中是唯一的,因此它不能返回多於一行。

使用這樣的子查詢的 SQL 術語是相關子查詢

所以,回答你的問題,是的......沒有連接操作就可以達到指定的結果。


其他一些注意事項:

在性能方面,子查詢的效率很重要。 它將為外部查詢返回的每一行執行。 如果我們返回 10,000 行,那就是執行 10,000 次子查詢。

因此,這種方法最適合外部查詢返回少量行且相關子查詢非常有效的情況。

使用以下查詢:

SELECT (u.name)workername, (select name from users where id=u.advised_by)supervisor FROM `users` u where u.roles="worker" 

您描述的示例表結構:

--
-- Database: `test`
--

-- --------------------------------------------------------

--
-- Table structure for table `users`
--

CREATE TABLE `users` (
  `id` int(11) NOT NULL,
  `name` varchar(255) NOT NULL,
  `roles` varchar(255) NOT NULL,
  `advised_by` int(11) NOT NULL
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

--
-- Dumping data for table `users`
--

INSERT INTO `users` (`id`, `name`, `roles`, `advised_by`) VALUES
(1, 'test1', 'supervisor', 0),
(2, 'test2', 'worker', 1),
(3, 'test3', 'worker', 1);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM