Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / MySQL [игнор отключен] [закрыт для гостей] / Как сравнить две последних записи / 14 сообщений из 14, страница 1 из 1
08.11.2017, 17:01
    #39549752
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
есть таблица куда скидывается цены по нескольким товарам, нужно узнать какое количество товаров подешевело а сколько подорожало, сравнивать надо две последних записи по каждому товару.

namepricedtшарф122017-11-06 16:07:05шапка102017-11-06 16:07:05перчатки72017-11-06 16:07:05шарф112017-11-06 16:06:05шапка112017-11-06 16:06:05перчатки112017-11-06 16:06:05шарф102017-11-06 16:05:05шапка102017-11-06 16:05:05перчатки102017-11-06 16:05:05
...
Рейтинг: 0 / 0
08.11.2017, 19:23
    #39549845
Akina
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
...
Рейтинг: 0 / 0
08.11.2017, 22:57
    #39549938
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
все равно не понятно. научился проставлять номера, а как дальше?
Код: sql
1.
2.
SELECT @i:=@i+1 num, t1.*  FROM `table` t1, (SELECT @i:=0) x
ORDER BY `dt` DESC 
...
Рейтинг: 0 / 0
09.11.2017, 00:04
    #39549955
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
Кое что получилось, но что то мне подсказывает что можно сократить

Код: sql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
SELECT * FROM

( SELECT @i:=@i+1 num, t1.*  FROM `table` t1, (SELECT @i:=0) x
 ORDER BY `dt` DESC  ) tt1

LEFT JOIN 

( SELECT @i:=@i+1 num, t2.*  FROM `table` t2, (SELECT @i:=0) x
 ORDER BY `dt` DESC  ) tt2

ON tt1.name = tt2.name
AND tt1.num < tt2.num
AND tt1.dt > tt2.dt

GROUP BY tt1.name
...
Рейтинг: 0 / 0
09.11.2017, 01:52
    #39549973
vkle
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
yarnikКое что получилосьОно точно решает исходную задачу
yarnikнужно узнать какое количество товаров подешевело а сколько подорожало, сравнивать надо две последних записи по каждому товару?
Не думаю.
Максимум, что дает Ваш вариант - это две цены, но не улавливаю гарантии, что они будут именно из двух последних записей по товару.

По задаче, насколько понимаю, надо сравнивать записи за 16:07:05 (последняя) и 16:06:05 (предпоследняя) и в итоге получить что-то вроде "один товар подорожал и два подешевело" (шарф подорожал, шапка и перчатки подешевели).

У меня получилось так (решение "в лоб", без попыток оптимизации)
Код: sql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
SELECT
    COUNT(1) AS `count`,
    `up_down`
    FROM
    (
        SELECT 
            IF(`price_1` > `price_2`, 'up', IF(`price_1` < `price_2`, 'down', 'const')) AS `up_down`
        FROM
        (
            SELECT
                IF(
                    @name = `name`, 
                    @num := @num + 1,  
                    @num := 1 + LEAST(0, @name := `name`)
                ) AS `num`,
                `price` AS `price_1`,
                `name`
            FROM 
                `table`, 
                (SELECT @num := 1, @name := '_') AS `a` 
            ORDER BY 
                `name` ASC,
                `dt` DESC
        ) AS `s1`
        JOIN
        (
            SELECT
                IF(
                    @name = `name`, 
                    @num := @num + 1,  
                    @num := 1 + LEAST(0, @name := `name`)
                ) AS `num`,
                `price` AS `price_2`,
                `name`
            FROM 
                `table`, 
                (SELECT @num := 1, @name := '_') AS `a` 
            ORDER BY 
                `name` ASC,
                `dt` DESC
        ) AS `s2`
        ON `s1`.`name` = `s2`.`name` AND `s1`.`num` = 1 AND `s2`.`num` = 2
    ) AS `a`
GROUP BY
    `up_down`
...
Рейтинг: 0 / 0
09.11.2017, 09:24
    #39550022
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
Спасибо за ответ.
vkleОно точно решает исходную задачу? Не думаю.

Максимум, что дает Ваш вариант - это две цены, но не улавливаю гарантии, что они будут именно из двух последних записей по товару.

По задаче, насколько понимаю, надо сравнивать записи за 16:07:05 (последняя) и 16:06:05 (предпоследняя) и в итоге получить что-то вроде "один товар подорожал и два подешевело" (шарф подорожал, шапка и перчатки подешевели).

Не полностью, но промежуточно.

Мне по задаче и надо получить последних 2 цены и далее их сравнить.
Последних - по дате (извините, что это не написал, думал это само собой понятно). А это 16:07:05 и 16:06:05

К сравнению я еще не дошел, поэтому и написал про кое-что как промежуточный вариант который выполняет первую часть задачи - выдает 2 цены
...
Рейтинг: 0 / 0
09.11.2017, 10:33
    #39550050
vkle
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
Насчет промежуточного варианта понятно. :)
Насчет выборки для сравнения двух последних дат таки ошибка есть. Вот это условие
Код: sql
1.
2.
AND tt1.num < tt2.num
AND tt1.dt > tt2.dt

не гарантирует, что будут выбраны для сравнения именно две последние даты, под него попадает так же пара первой и последней дат, первой и второй и множества промежуточных, если они будут. А группировка без агрегатной функции "отбросит лишнее" чуть ли не случайным образом. Как-то вот так.
...
Рейтинг: 0 / 0
09.11.2017, 10:38
    #39550053
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
И вот решение которое решает задачу.
Код: sql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
SELECT SUM(dif) FROM (
    SELECT SIGN(tt1.price-tt2.price) AS dif FROM

    ( SELECT @i:=@i+1 num, t1.*  FROM `table` t1, (SELECT @i:=0) x
      ORDER BY `dt` DESC  ) tt1

    JOIN 

    ( SELECT @i:=@i+1 num, t2.*  FROM `table` t2, (SELECT @i:=0) x
      ORDER BY `dt` DESC  ) tt2

    ON tt1.name = tt2.name
    AND tt1.num < tt2.num
    AND tt1.dt > tt2.dt

    GROUP BY tt1.name
) d


Конечно я считаю чудом, что группировка прошла именно так, где tt1 максимально свежая запись и tt2 следующая за ней.
Но ведь работает.
Буду признателен за более правильное и логичное решение.
...
Рейтинг: 0 / 0
09.11.2017, 10:52
    #39550063
vkle
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
Откуда взялись столбцы tt1.rate и tt2.rate? В исходных данных их нет, в вычисляемых - тоже нет.
...
Рейтинг: 0 / 0
09.11.2017, 11:27
    #39550086
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
rate = price
(извиняюсь, нет возможности редактировать)
...
Рейтинг: 0 / 0
09.11.2017, 11:44
    #39550102
paver
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
yarnikБуду признателен за более правильное и логичное решение.
Добавить в таблицу пару полей: Признак актуальной цены и Разность с предыдущей (актуальной) ценой ))
...
Рейтинг: 0 / 0
09.11.2017, 12:12
    #39550127
mahoune
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
yarnik,

исправлено
...
Рейтинг: 0 / 0
09.11.2017, 19:38
    #39550521
vkle
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
Что-то не так в датском королевстве. Простой тест дает один нуль:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
MariaDB [t]> SELECT * FROM `table`;
+------------------+-------+---------------------+
| name             | price | dt                  |
+------------------+-------+---------------------+
| шарф             |    12 | 2017-11-06 16:07:05 |
| шапка            |    10 | 2017-11-06 16:07:05 |
| перчатки         |     7 | 2017-11-06 16:07:05 |
| перчатки         |    11 | 2017-11-06 16:06:05 |
| перчатки         |    10 | 2017-11-06 16:05:05 |
| шарф             |    11 | 2017-11-06 16:06:05 |
| шапка            |    11 | 2017-11-06 16:06:05 |
| шарф             |    10 | 2017-11-06 16:05:05 |
| шапка            |    10 | 2017-11-06 16:05:05 |
+------------------+-------+---------------------+
9 rows in set (0.00 sec)

MariaDB [t]> SELECT SUM(dif) FROM (
    ->     SELECT SIGN(tt1.price-tt2.price) AS dif FROM
    -> 
    ->     ( SELECT @i:=@i+1 num, t1.*  FROM `table` t1, (SELECT @i:=0) x
    ->       ORDER BY `dt` DESC  ) tt1
    -> 
    ->     JOIN 
    -> 
    ->     ( SELECT @i:=@i+1 num, t2.*  FROM `table` t2, (SELECT @i:=0) x
    ->       ORDER BY `dt` DESC  ) tt2
    -> 
    ->     ON tt1.name = tt2.name
    ->     AND tt1.num < tt2.num
    ->     AND tt1.dt > tt2.dt
    -> 
    ->     GROUP BY tt1.name
    -> ) d;
+----------+
| SUM(dif) |
+----------+
|        0 |
+----------+
1 row in set (0.00 sec)

MariaDB [t]> 
Видимо, сказывается волшебное
yarnikя считаю чудом, что группировка прошла именно так
...
Рейтинг: 0 / 0
10.11.2017, 15:25
    #39551071
yarnik
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как сравнить две последних записи
не стоит смеяться, работает как на тесте http://sqlfiddle.com/#!9/e7ab7/1
так и у меня на сервере, правда на сервере время работы от 0,5 до 1,5 сек...
...
Рейтинг: 0 / 0
Форумы / MySQL [игнор отключен] [закрыт для гостей] / Как сравнить две последних записи / 14 сообщений из 14, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]