Sql Server сложный подзапрос - PullRequest
0 голосов
/ 07 ноября 2011

Рассмотрим эти две таблицы:

CREATE TABLE GAME_ROUNDS(
    RoundId int primary key NOT NULL,
    GameId int NOT NULL,
    RoundNumber int NOT NULL,
    Value varchar(20) ,
    Guess varchar(20) ,
    Answer varchar(20) ,
    Correct bit NOT NULL,       
    Seconds int NOT NULL,
    Milliseconds int NOT NULL)

CREATE TABLE GAMES(
    GameId int  primary key NOT NULL,
    GameTypeId int NOT NULL,
    GameDate datetime NOT NULL,     
    GameValues varchar(500) null)

Вот некоторые примеры данных:

insert into games(gameid, gametypeid, gamedate, gamevalues) values(1, 1,'2011-11-01 08:00:16.790',NULL)
insert into games(gameid, gametypeid, gamedate, gamevalues) values(2, 1,'2011-11-02 10:48:37.257',NULL)
insert into games(gameid, gametypeid, gamedate, gamevalues) values(3, 1,'2011-11-03 15:35:52.160',NULL)
insert into games(gameid, gametypeid, gamedate, gamevalues) values(4, 1,'2011-11-03 14:35:52.160',NULL)
insert into games(gameid, gametypeid, gamedate, gamevalues) values(5, 2,'2011-10-30 21:28:27.803','00,01,02,03,04,05,06,07,08,09')
insert into games(gameid, gametypeid, gamedate, gamevalues) values(6, 2,'2011-11-02 21:28:14.770','00,01,02,03,04,05,06,07,08,09')
insert into games(gameid, gametypeid, gamedate, gamevalues) values(7, 2,'2011-11-03 21:28:14.770','00,01,02,03,04,05,06,07,08,09')
insert into games(gameid, gametypeid, gamedate, gamevalues) values(8, 2,'2011-11-04 21:32:15.470','10,11,12,13,14,15,16,17,18,19')
insert into games(gameid, gametypeid, gamedate, gamevalues) values(9, 2,'2011-11-05 22:32:15.470','10,11,12,13,14,15,16,17,18,19')
insert into games(gameid, gametypeid, gamedate, gamevalues) values(10, 2,'2011-11-06 21:32:15.470','10,11,12,13,14,15,16,17,18,19')

insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(1, 1, 1,'Feb', '4', '4', 1, 0, 500)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(2, 1, 2,'Jul', '0', '0', 1, 0, 500)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(3, 1, 3,'Mar', '4', '4', 1, 0, 531)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(4, 2, 1,'Dec', '6', '6', 1, 0, 437)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(5, 2, 2,'May', '2', '2', 1, 0, 484)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(6, 2, 3,'Sep', '6', '6', 1, 0, 500)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(7, 3, 1,'Mar', '4', '3', 0, 0, 515)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(8, 3, 2,'Apr', '0', '0', 1, 0, 484)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(9, 3, 3,'May', '2', '2', 1, 0, 500)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(10, 4, 1,'Oct', '1', '1', 1, 0, 468)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(11, 4, 2,'Jan', '1', '1', 1, 0, 500)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(12, 4, 3,'Nov', '4', '4', 1, 0, 484)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(13, 5, 1,'0', '0', '0', 1, 0, 637)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(14, 5, 2,'5', '6', '6', 1, 0, 875)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(15, 5, 3,'8', '3', '3', 1, 0, 531)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(16, 6, 1,'9', '4', '4', 1, 0, 472)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(17, 6, 2,'6', '0', '0', 1, 0, 563)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(18, 6, 3,'8', '3', '3', 1, 0, 443)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(19, 7, 1,'0', '0', '0', 1, 0, 468)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(20, 7, 2,'9', '4', '4', 1, 0, 456)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(21, 7, 3,'4', '5', '5', 1, 0, 547)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(22, 8, 1,'12', '1', '1', 1, 0, 615)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(23, 8, 2,'18', '1', '1', 1, 0, 701)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(24, 8, 3,'16', '6', '6', 1, 0, 515)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(25, 9, 1,'10', '5', '5', 1, 0, 500)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(26, 9, 2,'19', '2', '2', 1, 0, 546)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(27, 9, 3,'15', '4', '4', 1, 0, 515)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(28, 10, 1,'13', '2', '2', 1, 0, 484)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(29, 10, 2,'12', '1', '1', 1, 0, 484)
insert into game_rounds(roundid, gameid, roundnumber, value, guess, answer, correct, seconds, milliseconds) values(30, 10, 3,'11', '6', '6', 1, 0, 453)

Эти таблицы являются частью игры с памятью, над которой я работаю.Детали не важны, но по мере того, как вы играете в игру, ваше время угадывания улучшается.

Одним из примеров является игра, в которой вам нужно указать код месяца, когда он представлен с месяцем.Итак, октябрь = 1, ноябрь = 4, декабрь = 6 и т. Д.

Я хочу написать запрос, в котором сообщается мне по каждому игровому типу и сочетанию игрового значения игрового идентификатора, где было получено среднее предположение в 500 миллисекунд.

Вот что у меня есть:

select vt.gametypeid, vt.gamevalues, min(vt.gamedate)
from (
         select dg.gametypeid, dg.gameid, dg.gamedate, dg.gamevalues, count(gr.gameid) as numberofrounds, cast(sum(gr.seconds*1000 + gr.milliseconds) as decimal)/cast(count(gr.gameid) as decimal) as avgguessmilliseconds
         from game_rounds gr (nolock)
         inner join games dg (nolock) on dg.gameid = gr.gameid
         where gr.gameid not in(select gameid from game_rounds (nolock) where correct = 0)
         group by gr.gameid, dg.gametypeid, dg.gamevalues, dg.gamedate, dg.gameid, dg.gamedate
         having cast(sum(gr.seconds*1000 + gr.milliseconds) as decimal)/cast(count(gr.gameid) as decimal) <= 500
) vt
group by vt.gametypeid, vt.gamevalues

Вот результат

gametypeid  gamevalues                                         gamedate
----------- -------------------------------------------------- -----------------------
1           NULL                                               2011-11-02 10:48:37.257
2           00,01,02,03,04,05,06,07,08,09                      2011-10-30 21:28:27.803
2           10,11,12,13,14,15,16,17,18,19                      2011-11-04 21:32:15.470

Проблема в том, что у меня нет GameId для ссылки на,То, что я не хочу, это вернуть Gameid в моем наборе результатов.

Есть ли способ сделать это, используя чистый SQL (без курсора или табличной переменной)?

Ответы [ 2 ]

1 голос
/ 08 ноября 2011

Я думаю, что это сделает вас. Я предположил, что вам нужна ПЕРВАЯ игра, которая соответствует заданным критериям (поскольку вы использовали мин игровой даты в своем примере) Ясно, что для каждого комбо gametypeid / values ​​может быть несколько игр, отвечающих всем требованиям.

SELECT GameId, 
       GameTypeId, 
       GameValues, 
       GameDate 
FROM
(
   SELECT   G.GameId,
        G.GameTypeId,
        G.GameValues,
        G.GameDate,
        RANK() OVER(Partition By G.GameTypeId, G.GameValues Order By
               G.GameDate DESC) As Ranking 
    FROM    GAMES G
    JOIN    GAME_ROUNDS GR
        ON  G.GameId = GR.GameId
    GROUP
    BY      G.GameId,
        G.GameTypeId,
        G.GameValues,
        G.GameDate
    HAVING  SUM(CASE GR.Correct WHEN 0 THEN 1 ELSE 0 END) = 0
    AND     AVG(CAST(GR.Seconds * 1000 + GR.Milliseconds as DECIMAL)) <= 500
) CandidateResults
WHERE   Ranking = 1
1 голос
/ 07 ноября 2011

Мой нерешительный ответ: "Да" .Я думаю, что оператор APPLY для вас, так как вы хотите результаты в строке без использования курсора или табличной переменной.Проверьте это Ссылка out.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...