MySQL "WITH"절


98

MySQL을 사용하여 "WITH"절이있는 뷰를 만들려고합니다.

WITH authorRating(aname, rating) AS
   SELECT aname, AVG(quantity)
   FROM book
   GROUP BY aname

그러나 MySQL이 이것을 지원하는 것 같지 않습니다.

나는 이것이 꽤 표준이라고 생각했고 오라클이 이것을 지원한다고 확신합니다. 어쨌든 MySQL이 "WITH"절을 사용하도록 강제하는 것이 있습니까? MyISAM 및 innoDB 엔진으로 시도했습니다. 둘 다 작동하지 않습니다.

답변:


109

업데이트 : MySQL 8.0은 마침내 재귀 CTE를 포함한 공통 테이블 표현식의 기능을 얻습니다.

다음은이를 알리는 블로그입니다. http://mysqlserverteam.com/mysql-8-0-labs-recursive-common-table-expressions-in-mysql-ctes/

아래는 제가 2008 년에 썼던 초기 답변입니다.


MySQL 5.x는 Common Table ExpressionsWITH 라고도하는 SQL-99에 정의 된 구문을 사용하는 쿼리를 지원하지 않습니다 .

이것은 2006 년 1 월부터 MySQL에 대한 기능 요청입니다. http://bugs.mysql.com/bug.php?id=16244

공통 테이블 표현식을 지원하는 기타 RDBMS 제품 :


1
SQLite는 2014-02-03에 릴리스 된 버전 3.8.3 부터 WITH 절 을 지원합니다 .
Martijn 2014

H2와 Firebird를 목록에 추가했습니다.
a_horse_with_no_name 2014

2
@BillKarwin : 나는 생각하지 않는다 MySQL은 지금까지 구현합니다 모든 현대적인 DBMS가 (점검 제한 조건, 윈도우 함수, 표현식에 대한 인덱스 부분 인덱스, 이연 제약 ...) 기능이 있습니다.
a_horse_with_no_name 2014

2
@a_horse_with_no_name, 그들은 확장성에 훨씬 더 높은 우선 순위를 두는 것 같습니다. 그들은 현대 하드웨어를 활용하기 위해 내부를 더 확장 가능하게 만드는 데 오랫동안 집중 해 왔습니다. 그러나 나는 그들이 SQL 기능을 무시했다고 생각합니다.
Bill Karwin 2014

1
@BlakeMcBride, 틀 렸습니다. 귀하의 의견은 FUD이며 사실 근거가 없습니다. Oracle은 또한 Oracle DB가 잘하지 못하는 일을하는 다른 데이터베이스 제품을 소유하고 있습니다. 예 : TimesTen, BerkeleyDB. 그들은 시장을 확장하기 위해 이러한 데이터베이스를 확보했습니다. MySQL은 웹 애플리케이션 시장에서 지배적이지만 Oracle DB는 그렇지 않아 MySQL을 인수했습니다. 오라클이 MySQL을 햄스트링하는 것은 의미가 없습니다. 저는 4 월 컨퍼런스에서 Oracle MySQL 개발자들과 이야기를 나눴으며 실제로 그들은 MySQL 용 WITH 구현을 위해 작업하고 있습니다.
Bill Karwin 16.06.06

17

다음과 같은 무언가에 관심이있을 수 있습니다.

select * from (
    select * from table
) as Subquery

Subquery를 설명해 주시겠습니까? 내가 select * from ((select * from table1) UNION ALL (select * from table2)) Group By something?

1
@Kathy Hi Subquery는 파생 테이블 자체에 사용한 이름입니다. 사용할 때 from ( ... )임시 테이블 (파생 테이블)과 같은 것을 만들고 이름이 필요합니다. 그래서 as Subquery. 질문에 대답 할 수 있습니다. 가능하지만 외부 파생 테이블에 이름을 입력해야합니다 ( Group By). 도움이 되었기를 바랍니다.
MOSTY Mostacho

@MostyMostacho 안녕하세요, 저를 여기 숟가락으로 조금 먹일 수 있습니까? MySQL로 변환하는 데 어려움을 겪고 있습니다. 당신은 그것을 볼 수 있습니까? 여기에 링크 하거나 내 질문에 답할 수 있습니까? 링크
Pranav

13

올바른 구문이 있습니다.

WITH AuthorRating(AuthorName, AuthorRating) AS
   SELECT aname         AS AuthorName,
          AVG(quantity) AS AuthorRating
   FROM Book
   GROUP By Book.aname

그러나 다른 사람들이 언급했듯이 MySQL은이 명령을 지원하지 않습니다. WITH는 SQL : 1999에 추가되었습니다. SQL 표준의 최신 버전은 SQL : 2008입니다. Wikipedia 에서 SQL : 1999의 다양한 기능을 지원하는 데이터베이스에 대한 추가 정보를 찾을 수 있습니다 .

MySQL은 전통적으로 SQL 표준에 대한 지원이 다소 뒤처졌지만 Oracle, SQL Server (최근) 및 DB2와 같은 상용 데이터베이스는이를 좀 더 밀접하게 따랐습니다. PostgreSQL은 일반적으로 꽤 표준을 준수합니다.

MySQL의 로드맵을 살펴볼 수 있습니다. 이 기능이 언제 지원되는지는 확실하지 않지만 읽을 수있는 롤업 쿼리를 만드는 데는 좋습니다.


10

오라클은 WITH를 지원합니다.

이렇게 보일 것입니다.

WITH emps as (SELECT * FROM Employees)
SELECT * FROM emps WHERE ID < 20
UNION ALL
SELECT * FROM emps where Sex = 'F'

@ysth WITH는 일반적으로 검색에서 제외되는 일반적인 단어이기 때문에 구글하기가 어렵습니다.

하위 쿼리 팩터링이 작동하는 방식을 보려면 SELECT 문서 를보고 싶을 것 입니다.

나는 이것이 OP에 대답하지 않는다는 것을 알고 있지만 ysth가 시작되었을 수있는 혼란을 정리하고 있습니다.


어쨌든 내 혼란을 해결하지 못했습니다. WITH 절이 없지만 WITH 문이 있다는 말입니까?
ysth

1
아, 알겠습니다. 선택에 선행하는 선택의 절입니다. CREATE VIEW에서도 사용할 수 있습니까? 하위 선택 결합과 어떻게 다릅니 까? WITH 뒤의 이름에 매개 변수가있는 온라인 예제가 보이지 않습니다. 어떻게 작동합니까?
ysth

1
아주 다릅니다. 동일한 subqry를 두 번 정의 할 필요없이 두 번 사용합니다. 물론 거기에 동일한 쿼리를 복사 / 붙여 넣기 할 수 있지만 이것은 간단한 예입니다. WITH 절이 페이지에 대해 계속되고 기본 쿼리에서 4 번 사용되었다고 상상해보십시오. 그러면 감사 할 것입니다.

구문을 설명해야하는 문서에 연결했습니다. 보기에서. 물론 거기에서 작동합니다.

3

@Mosty Mostacho의 답변을 바탕으로 테이블에 존재하지 않고 다른 데이터베이스에없는 항목을 결정하는 특정 경우에 대해 MySQL에서 동등한 작업을 수행하는 방법은 다음과 같습니다.

select col1 from (
   select 'value1' as col1 union
   select 'value2' as col1 union
   select 'value3' as col1
) as subquery
left join mytable as mytable.mycol = col1
where mytable.mycol is null
order by col1

매크로 기능이있는 텍스트 편집기를 사용하여 값 목록을 인용 된 select union 절로 변환 할 수 있습니다.




0

임시 테이블을 사용해 본 적이 있습니까? 이것은 내 convern을 해결했습니다.

create temporary table abc (
column1 varchar(255)
column2 decimal
);
insert into abc
select ...
or otherwise
insert into abc
values ('text', 5.5), ('text2', 0815.8);

그런 다음이 세션의 모든 선택에서이 테이블을 사용할 수 있습니다.

select * from abc inner join users on ...;

1
나는 주목해야한다 : stackoverflow.com/questions/343402/… 당신은 테이블을 두 번 열 수 없다 :-(
Claus

테이블의 작은 데이터 세트에 대한 My Sollution : abc와 같은 테이블 abc2 생성; abc2에 삽입 select * from abc;
Claus
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.