powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Oracle [игнор отключен] [закрыт для гостей] / предыдущее значение с условием
9 сообщений из 9, страница 1 из 1
предыдущее значение с условием
    #39637848
usmazat
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Добрый день! Есть таблица(id,username, send_date,message) в ней хранится список сообщений диалог пользователей по какой то теме
как можно запросом вытащить предыдущее сообщение(не от самого себя) от пользователя в этом диалоге?

запрос вида


Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
with t as

( select 1 id ,   'userA' username ,  to_date('12.02.2018 10:08:05','DD.MM.YYYY HH24:MI:SS') send_date ,'problem 1' message  from dual union all
select 2,   'userB'  ,  to_date('12.02.2018 11:34:12','DD.MM.YYYY HH24:MI:SS') ,'what ?' from dual union all
select 3,   'userB'  ,  to_date('12.02.2018 14:12:02','DD.MM.YYYY HH24:MI:SS'),'try this' from dual union all
select 4,   'userA'  ,  to_date('13.02.2018 09:29:23','DD.MM.YYYY HH24:MI:SS') ,'see here' from dual union all
select 5,   'userB'  ,  to_date('13.02.2018 13:34:12','DD.MM.YYYY HH24:MI:SS') ,'do this' from dual

) select t.*,  lag(t.message) over ( order by M.SEND_DATE)  reply_to from t 

выдает

id username send_date message reply_to 1 user A 12.02.2018 10:08:05 'problem 1' null 2 user B 12.02.2018 11:34:12 'what ?' 'problem1' 3 user B 12.02.2018 14:12:02 'try this' 'what?' 4 user A 13.02.2018 09:29:23 'see here' 'try this' 5 user B 13.02.2018 13:34:12 'do this' 'see here'

a надо

id username send_date message reply_to 1 user A 12.02.2018 10:08:05 'problem 1' null 2 user B 12.02.2018 11:34:12 'what ?' 'problem1' 3 user B 12.02.2018 14:12:02 'try this' 'problem1' 4 user A 13.02.2018 09:29:23 'see here' 'try this' 5 user B 13.02.2018 13:34:12 'do this' 'see here'
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39637855
Фотография AmKad
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
select id, username, send_date, message,
last_value(decode(is_last, 1, message) ignore nulls) over (order by send_date rows between unbounded preceding and 1 preceding) prev_message
from
   (select t.*, decode(lead(username) over (order by send_date), username, 0, 1) is_last
    from t
   ) t;

        ID USERN SEND_DATE           MESSAGE   PREV_MESS
---------- ----- ------------------- --------- ---------
         1 userA 2018-02-12 10:08:05 problem 1
         2 userB 2018-02-12 11:34:12 what ?    problem 1
         3 userB 2018-02-12 14:12:02 try this  problem 1
         4 userA 2018-02-13 09:29:23 see here  try this
         5 userB 2018-02-13 13:34:12 do this   see here
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39638944
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Код: plsql
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.
select *
  from t
    match_recognize
    ( order by send_date desc
      measures
        this.id as id
      , this.username as username
      , this.send_date as send_date
      , this.message as message
      , first(prev.message) as prev_message
      one row per match
      after match skip to next row
      pattern (this same* (prev+ | $))
      define
        prev as prev.username <> this.username
      , same as same.username = this.username
    )
  order by id
;

         ID USERN SEND_DATE         MESSAGE   PREV_MESS
----------- ----- ----------------- --------- ---------
          1 userA 12.02.18 10:08:05 problem 1
          2 userB 12.02.18 11:34:12 what ?    problem 1
          3 userB 12.02.18 14:12:02 try this  problem 1
          4 userA 13.02.18 09:29:23 see here  try this
          5 userB 13.02.18 13:34:12 do this   see here
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39638948
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
AmKad
Код: plsql
1.
2.
3.
last_value(decode(is_last, 1, message) ignore nulls) over (order by send_date rows between unbounded preceding and 1 preceding) prev_message
from
   (select t.*, decode(lead(username) over (order by send_date), username, 0, 1) is_last

Код: plsql
1.
2.
3.
lag(prev_message) ignore nulls over (order by send_date) prev_message
from
   (select t.*, decode(lead(username) over (order by send_date), username, null, message) prev_message
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39639121
usmazat
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Elic,oracle 10.2.0.5
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39639145
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
usmazatElic,oracle 10.2.0.5Твоё горе форум интересует меньше всего.
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39639198
Фотография Stax
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
usmazatElic,oracle 10.2.0.5

нет last_value(decode(is_last, 1, message) ignore nulls ) ?

.....
stax
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39641665
Фотография dbms_photoshop
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Elic
Код: plsql
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.
select *
  from t
    match_recognize
    ( order by send_date desc
      measures
        this.id as id
      , this.username as username
      , this.send_date as send_date
      , this.message as message
      , first(prev.message) as prev_message
      one row per match
      after match skip to next row
      pattern (this same* (prev+ | $))
      define
        prev as prev.username <> this.username
      , same as same.username = this.username
    )
  order by id
;

         ID USERN SEND_DATE         MESSAGE   PREV_MESS
----------- ----- ----------------- --------- ---------
          1 userA 12.02.18 10:08:05 problem 1
          2 userB 12.02.18 11:34:12 what ?    problem 1
          3 userB 12.02.18 14:12:02 try this  problem 1
          4 userA 13.02.18 09:29:23 see here  try this
          5 userB 13.02.18 13:34:12 do this   see here

Если диалог ведут двое можно обойтись без старта из каждой строки и оглядывания назад.
Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
select *
  from t
    match_recognize
    ( order by send_date
      measures
        decode(classifier(), 'X', last(y.message), last(x.message)) prev
      all rows per match
      pattern ((x+ y+)+)
      define
        x as x.username = nvl(last(x.username, 1), username)
      , y as y.username = nvl(last(y.username, 1), username)
    )
  order by id


Возможно, define допиливается до общего случая. Надо пошевелить извилиной на досуге.
...
Рейтинг: 0 / 0
предыдущее значение с условием
    #39642260
Фотография dbms_photoshop
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
dbms_photoshopВозможно, define допиливается до общего случая. Надо пошевелить извилиной на досуге.Собственно
Код: plsql
1.
2.
3.
      define
        x as x.username = prev(username) or prev(username) is null or prev(username) = last(y.username)
      , y as y.username = prev(username) or prev(username) is null or prev(username) = last(x.username)
...
Рейтинг: 0 / 0
9 сообщений из 9, страница 1 из 1
Форумы / Oracle [игнор отключен] [закрыт для гостей] / предыдущее значение с условием
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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