2013-06-06 7 views
0

이 내 쿼리의 문제가 일부입니다 실행에SQL - 파생 테이블에서 알 수없는 열

SELECT 
    (SELECT id FROM users WHERE name = 'John') as competitor_id, 
    (SELECT MIN(duration) 
     FROM 
      (SELECT duration FROM attempts 
       WHERE userid=competitor_id ORDER BY created DESC LIMIT 1,1 
      ) x 
    ) as best_time 

,이 오류가 발생합니다 :

#1054 - Unknown column 'competitor_id' in 'where clause'

그것은 파생 테이블 'X'처럼 보인다 상위 쿼리 별칭 competitor_id을 볼 수 없습니다. 파생 된 모든 테이블에서 사용할 수있는 일종의 글로벌 별칭을 만드는 방법이 있습니까?

WHERE 절에서 직접 하위 쿼리로 competitor_id 쿼리를 사용할 수는 있지만 별칭을 사용하지 않는 것이 좋습니다. 그러나 실제 쿼리가 훨씬 커지고 더 많은 하위 쿼리와 파생 테이블에 competitor_id을 사용해야합니다. 동일한 하위 쿼리를 더 많이 사용하면 비효율적입니다.

답변

0

select 문에서 파생 테이블을 사용할 필요가없는 경우에도 다음과 같은 작업을 수행하지 않습니까?

SELECT 
    users.id as competitor_id, 
    MIN(duration) as best_time 
FROM users 
inner join attempts on users.id = attempts.user_id 
WHERE name = 'John' 
group by users.id 
0

그 절에 다른 곳에서 참조 할 수없는 선택 출력 절에 도입 된 식별자 때문에이 오류가 발생합니다 - SQL 식별자/열이 기본적으로 아래 밖으로 밀려되지 않습니다 (또는 가로 질러).

하지만 가능한 경우에도이 방법으로 쿼리를 작성하는 것은 좋지 않습니다. 사용자와 시도 (사용자 아이디) 사이에 JOIN을 사용하고 이름을 기준으로 필터링하십시오. 그런 다음 SQL 쿼리 계획자는 상위 관계형 대수를 가져 와서 효율적인 계획을 작성합니다. 그룹에 대한 집계 (MIN)가 처리되므로 수동 주문 또는 제한이 필요하지 않습니다.

SELECT u.id, u.name, MIN(a.duration) as duration 
FROM users u 
-- match up each attempt per user 
JOIN attempts a 
ON a.userid = u.id 
-- only show users with this name 
WHERE u.name = 'John' 
-- group so we get the min duration *per user* 
-- (name is included so it can be in the output clause) 
GROUP BY u.id, u.name 
0

검색어에 대해 다소 이상하게 보입니다. 가장 안쪽의 하위 쿼리가 하나의 행을 선택한 다음 min(duration)을 가져갑니다. min은 하나의 행만 있기 때문에 불필요합니다. 검색어로 문구를 쓸 수 있습니다.

SELECT u.id as competitor_id, a.duration as best_time 
from users u left outer join 
    attempts a 
    on u.id = a.userid 
where u.name = 'John' 
order by a.created desc 
limit 1, 1; 

쿼리가 시도하는 것으로 보입니다. 그러나 이것은 귀하의 의도가 아닙니다. 아마도 가장 최근의 시간을 제공하고있을 것입니다. (MySQL을 사용하고 있다면, limit 1, 1은 실제로 두 번째 가장 최근의 기록을 가지고 있습니다). 이 정확히 하나 개의 행이 반환되도록 것 group by u.id 추가

SELECT u.id as competitor_id, min(a.duration) as best_time 
from users u left outer join 
    attempts a 
    on u.id = a.userid 
where u.name = 'John' 

: 최소 기간 (아마도 "최고")는, 당신이 할 것입니다 얻으려면.