Есть ли способ генерировать произвольное количество строк, которое может использоваться в JOIN, аналогичном синтаксису Oracle:
SELECT LEVEL FROM DUAL CONNECT BY LEVEL<=10
Есть ли способ генерировать произвольное количество строк, которое может использоваться в JOIN, аналогичном синтаксису Oracle:
SELECT LEVEL FROM DUAL CONNECT BY LEVEL<=10
Ненавижу сказать это, но MySQL
является единственным RDBMS
для большого четырех, у которого нет этой функции.
В Oracle
:
SELECT *
FROM dual
CONNECT BY
level < n
В MS SQL
(до 100
rows):
WITH hier(row) AS
(
SELECT 1
UNION ALL
SELECT row + 1
FROM hier
WHERE row < n
)
SELECT *
FROM hier
или используя подсказку до 32768
WITH hier(row) AS
(
SELECT 1
UNION ALL
SELECT row + 1
FROM hier
WHERE row < 32768
)
SELECT *
FROM hier
OPTION (MAXRECURSION 32767) -- 32767 is the maximum value of the hint
В PostgreSQL
:
SELECT *
FROM generate_series (1, n)
В MySQL
ничего.
В MySql я понимаю, что вы можете получить более одной строки с SELECT без таблицы (или DUAL).
Следовательно, чтобы получить несколько строк, вам нужна реальная или временная таблица с по крайней мере требуемым количеством строк.
Однако вам не нужно создавать временную таблицу, так как вы можете использовать ЛЮБАЯ существующую таблицу, которая имеет как минимум количество требуемых строк. Итак, если у вас есть таблица с по крайней мере требуемым количеством строк, используйте:
SELECT @curRow := @curRow + 1 AS row_number
FROM sometable
JOIN (SELECT @curRow := 0) r
WHERE @curRow<100;
Просто замените "sometable" на имя любой вашей таблицы, по крайней мере, на необходимое количество строк.
PS: "r" - это таблица "alias": я мог бы использовать "AS r". Любой подзапрос в предложении FROM или JOIN создает "производную таблицу", которая, как и все таблицы, должна иметь имя или псевдоним. (См. Руководство по MySql: 13.2.9.8. Подзапросы в разделе FROM)
Считаете ли вы ЛЕВЫЙ ВНЕШНИЙ ПРИСОЕДИНЯЙТЕСЬ?
Я не знаю, помогает ли это, но вы можете подсчитывать строки из каждого оператора select с помощью sth. как:
SET @NUM = 0;
SELECT @NUM: = @NUM + 1 rowNumber, * FROM...
И позже присоединитесь к ним на этом. В больших базах данных это может быть очень медленно.
Если я понимаю вас, вам нужен список consequtive numbers?
Просто создайте список:
create table artificial_range (id int not null primary key auto_increment, idn int);
insert into artificial_range (idn) values (0); --first row
insert into artificial_range(idn) select idn from artificial_range; --2nd
insert into artificial_range(idn) select idn from artificial_range; -- now 4 rows
insert into artificial_range(idn) select idn from artificial_range; --8
insert into artificial_range(idn) select idn from artificial_range; --16
insert into artificial_range(idn) select idn from artificial_range; --32
insert into artificial_range(idn) select idn from artificial_range; --64
insert into artificial_range(idn) select idn from artificial_range; --128
... и т.д., пока у вас не будет, скажем, 1024.
update artificial_range set idn = id - 1 ;
- теперь у вас есть серия, смотрящая на 1 (id) и серию, начинающуюся с 0
Теперь присоединитесь к нему или присоедините к его преобразованиям:
create view days_this_century as
select date_add('2000-01-01', interval a.idn day) as cdate
from artificial_range;
У меня была таблица со столбцом (c5
), которая содержала число x, мне понадобилось выражение SQL, которое повторяло ту же строку x чисел раз.
В моей таблице A содержится
c1 c2 c3 c4 c5
16 1 2 16 3
16 1 2 17 2
16 1 2 18 1
И мне нужно:
c1 c2 c3 c4 c5 n
16 1 2 16 3 1
16 1 2 16 3 2
16 1 2 16 3 3
16 1 2 17 2 1
16 1 2 17 2 2
16 1 2 18 1 1
Я решил, что с выражением:
SELECT
c1, c2, c3, c4, c5, row_number AS n
FROM
(
SELECT
@curRow := @curRow + 1 AS row_number
FROM
tablea
JOIN (SELECT @curRow := 0) r
WHERE
@curRow < (
SELECT
max(field1)
FROM
tablea
)
) AS vwtable2
LEFT JOIN tablea d ON vwtable2.row_number <= tablea.field1;