2009-08-19 5 views
2

그래서 세 가지 경우 모두 내 구문이 정확하지만 (PostgreSQL은 어떤 것도 신경 쓰지 않습니다) 결과는이 세 가지 쿼리 모두에서 같은 순서로 나타납니다. 낯선 사람이라도 다음 중 하나에서 DESC를 추가/삭제해도 영향이 없습니다. 하위 쿼리의 요소를 기반으로 결과를 정렬 할 수 있습니까?하위 쿼리 및 정렬? (ORDER BY)

Sort by affiliation 
SELECT * FROM articles_view WHERE (1=1) 
AND spubid IN 
    (SELECT people.spubid FROM people WHERE (people.slast ilike 'doe') 
    GROUP BY people.spubid, people.slast, people.saffil) 
AND spubid IN 
    (SELECT status.spubid FROM status WHERE ((status.imonth >= 01 OR status.imonth IS NULL) AND status.iyear >= 2000) AND ((status.imonth <= 01 OR status.imonth IS NULL) AND status.iyear <= 2008) ORDER BY status.iyear, status.imonth) 

Sort by last name, descending order 
SELECT * FROM articles_view WHERE (1=1) 
AND spubid IN 
    (SELECT people.spubid FROM people WHERE (people.slast ilike 'doe') 
    GROUP BY people.spubid, people.slast, people.saffil ORDER BY people.slast DESC) 
AND spubid IN 
    (SELECT status.spubid FROM status WHERE ((status.imonth >= 01 OR status.imonth IS NULL) AND status.iyear >= 2000) AND ((status.imonth <= 01 OR status.imonth IS NULL) AND status.iyear <= 2008)) 

Sort by year/month descending order 
SELECT * FROM articles_view WHERE (1=1) 
AND spubid IN 
    (SELECT people.spubid FROM people WHERE (people.slast ilike 'doe') 
    GROUP BY people.spubid, people.slast, people.saffil) 
AND spubid IN 
    (SELECT status.spubid FROM status WHERE ((status.imonth >= 01 OR status.imonth IS NULL) AND status.iyear >= 2000) AND ((status.imonth <= 01 OR status.imonth IS NULL) AND status.iyear <= 2008) ORDER BY status.iyear, status.imonth DESC) 

왜 ORDER BY 조건이 결과의 순서에 영향을 미치지 않는지 잘 모르겠습니다.

********* 업데이트 : 내 모든 정렬을 수행하기 위해 (이 경우 articles_view에) 내보기에 배열 열을 사용하여 한 일을 결국 무엇

. 그런 식으로 기본 쿼리에서 모든 종류의 "열"을 수행하고 JOINS를 사용하지 않아도됩니다. 뷰가 정의되는 방식으로, 사람/상태 테이블의 주어진 pubid (기본 키)와 일치하는 모든 열 (둘 다 1-> 많음)이 뷰의 배열 열에 저장됩니다.

SELECT * FROM articles_view WHERE 
    ((articles_view.skeywords_auto ilike '%ice%') OR (articles_view.skeywords_manual ilike '%ice%')) 
    ORDER BY (articles_view.authors[1]).slast 

난 항상 배열의 첫 번째 멤버 (포스트 그레스의 첫 번째 인덱스가 1이 아닌 보통 0) 것을 알고 있기 때문에이 작동하는 이유는, 기본입니다 : 정렬 나의 질의는 다음과 같다 저자 (또는 1 차 신분)가 필요합니다.

답변

0

(사례 articles_view) 모든 정렬 작업을 수행합니다. 그런 식으로 기본 쿼리에서 모든 종류의 "열"을 수행하고 JOINS를 사용하지 않아도됩니다. 뷰가 정의되는 방식으로, 사람/상태 테이블의 주어진 pubid (기본 키)와 일치하는 모든 열 (둘 다 1-> 많음)이 뷰의 배열 열에 저장됩니다.

SELECT * FROM articles_view WHERE 
    ((articles_view.skeywords_auto ilike '%ice%') OR (articles_view.skeywords_manual ilike '%ice%')) 
    ORDER BY (articles_view.authors[1]).slast 

난 항상 배열의 첫 번째 멤버 (포스트 그레스의 첫 번째 인덱스가 1이 아닌 보통 0) 것을 알고 있기 때문에이 작동하는 이유는, 기본입니다 : 정렬 나의 질의는 다음과 같다 저자 (또는 1 차 신분)가 필요합니다.

3

모든 하위 쿼리는 조건에 대한 결과 집합을 제공하여 spubid가 있는지 확인합니다. 실제로 상태 테이블에 조인 한 다음 외부 쿼리의 order by 절에있는 열을 사용해야합니다. 같은

뭔가 :

SELECT * 
FROM articles_view 
     INNER JOIN status ON articles_view.spubid = status.spubid 
     INNER JOIN people ON articles_view.spubid = people.spubid 
WHERE ((status.imonth >= 01 OR status.imonth IS NULL) AND status.iyear >= 2000) 
     AND ((status.imonth <= 01 OR status.imonth IS NULL) 
     AND status.iyear <= 2008 AND people.slast ilike 'doe') 
ORDER BY status.iyear, status.imonth 
+0

나는 그것이 두려웠다. 나는 정말로 조인을 사용하지 않기를 바란다. (제품이 너무 길어서 서브 쿼리를 대신 사용하게된다.) –

+0

내부 조인을 사용하면 적절한 결과 만 얻을 수 있으며 쿼리 최적화 프로그램은 조인이 적용되기 전에 where 절을 만족하지 않는 항목을 제거하는 계획을 결정해야합니다. –

1

당신은 단지에있는 문에서 사용되는 데이터를 정렬한다. 최상위 Select 문을 정렬해야합니다.

편집 :

그리고 IN 절 내부 선택 문이 결과의 전반적인 분류에 기여하지 않기 때문에, 당신은 따라서 불필요한을 할 필요에서 서버를 방지, 그들로부터 조항에 의해 순서를 제거해야

처리.

2

바깥 쪽 쿼리를 주문하는 것이 아닙니다. 내부 검색어 만 주문하고 있습니다. 완벽하게 합법적이지만 그 내적 결과로 수행하는 작업은 모두 spubid을 해당 작업과 비교하는 것으로 그 순서는 중요하지 않습니다.

찾고있는 것은 JOIN입니다.

SELECT * 
FROM articles_view 
INNER JOIN status ON (status.spubid = articles_view.spubid AND ((status.imonth >= 01 OR status.imonth IS NULL) AND status.iyear >= 2000) AND ((status.imonth <= 01 OR status.imonth IS NULL) AND status.iyear <= 2008)) 
WHERE spubid IN 
    (SELECT people.spubid FROM people WHERE (people.slast ilike 'doe') 
    GROUP BY people.spubid, people.slast, people.saffil) 
ORDER BY status.iyear, status.imonth DESC 

(A 또한 가입으로 당신은 다른 조회를 다시 쓸 수 있지만, 간단하게하기 위해 나 혼자 한 것이있었습니다.)이있는

내가보기에 배열 열을 사용하여 한 일을 결국 무엇
+0

사용자가 사람 또는 상태 테이블의 필드를 정렬할지 여부를 미리 알지 못하기 때문에 둘 다 참여해야합니다. 문제는 제가 남긴 제품입니다. 많은 양의 데이터를 쿼리에 통합 할 필요는 없지만 다양한 정렬 옵션을 허용하려면 이것이 유일한 옵션 인 것 같습니다. –

+1

"JOIN"여부에 관계없이 많은 데이터를 쿼리 * 처리 *에 통합합니다. 당신의 관심사가 간단히 많은 * 컬럼 *을 반환한다면, 그것은 * 쉽게 * 수정됩니다 : 단순히'SELECT *'대신'SELECT articles_view. *'를하십시오. – VoteyDisciple