LINUX.ORG.RU

MySql, «свёртка» по битовому полю

 , ,


0

1

Есть табличка, надо «свернуть» по битовому полю.

Дано:

+---------------------+------+
| time_field          | bit  |
+---------------------+------+
| 2017-08-22 12:24:15 |    0 |
| 2017-08-22 12:24:16 |    0 |
| 2017-08-22 12:24:17 |    0 |
| 2017-08-22 12:24:18 |    1 |
| 2017-08-22 12:24:19 |    1 |
| 2017-08-22 12:24:20 |    1 |
| 2017-08-22 12:24:21 |    1 |
| 2017-08-22 12:24:38 |    0 |
| 2017-08-22 12:24:39 |    0 |
| 2017-08-22 12:24:40 |    0 |
+---------------------+------+

Результат:

| 2017-08-22 12:24:17 |    0 |
| 2017-08-22 12:24:21 |    1 |
| 2017-08-22 12:24:40 |    0 |

Т.е. как

SELECT MAX(time_field), bit FROM table GROUP BY bit;

но не группировка, а свёртка последовательных строк с одинаковым признаком.

Что-то не соображу, такое можно сделать попроще или нет?

★★★★★

Напиши какой результат хочешь получить, а то что-то не понятно чем тебя группировка не устраивает.

pi11 ★★★★★
()
Ответ на: комментарий от pi11

Вроде, написал. Группировка вернёт две записи, одна с 0, вторая с 1. А мне надо сгруппировать последовательные строки с одним признаком.

vvn_black ★★★★★
() автор топика
Ответ на: комментарий от anonymous
select * from Q q where 

    (select bit from Q q1 where
        q1.time_field > q.time_field 
        order by q1.time_field 
        asc limit 1)<>q.bit

  or not exists 

    (select bit from Q q1 where
        q1.time_field > q.time_field 
     order by q1.time_field asc
     limit 1)

  order by q.time_field

Проверяем что следующий элемент за строкой меняет значение бита, или это последний элемент в таблица

На постгре работает.

Но это решение не оптимально, т.к. делает много сканов( O(3*N) ), и проще пробежаться процедурой по отсортированным данным

anonymous
()

имно подобное в коде надо делать т.к. в база данных при таких извратах не помогает, а только мешает да и быстрее будет в коде.

vtVitus ★★★★★
()
CREATE TABLE events (
  id INT(11) UNSIGNED NOT NULL AUTO_INCREMENT,
  tstart INT(11) UNSIGNED NOT NULL DEFAULT 0,
  tend  INT(11) UNSIGNED NOT NULL DEFAULT 0,
  end   TINYINT(1) UNSIGNED NOT NULL DEFAULT 0,
  PRIMARY KEY (`id`),
  KEY event_start (`tstart`)
);

SELECT id FROM events WHERE bit = ? ORDER BY tstart DESC LIMIT 1;
UPDATE events SET tend = UNIX_TIMESTAMP() WHERE id = ?;

Думаю идея понятна. Если с таблицей работают несколько потоков - завернуть в транзакцию.

anonymous
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.