Автоматическое создание записей временного интервала - PullRequest
0 голосов
/ 21 июня 2020

У меня есть следующее определение таблицы и инструкция INSERT, которые работают нормально.

create table.    tour_detail (
  location_id NUMBER(4),
  time interval day to second
  )

insert into tour_detail.    
(location_id,time)
 values (3, interval '11:30' hour to minute)

Можно ли изменить CTE в приведенном ниже примере в таблице tour_detail для выполнения следующих действий.

  • Измените его, чтобы оставить только HH24: MI, а остальные поля = 0.

  • Как время может зависеть друг от друга, например val = val + rand (6,12) минут.

  • Если val> = 23:45, его можно сбросить на какой-то случайный HH24: MI.

  • can для каждого tour_hdr (tour_id) создается случайное количество (15-25) строк tour_detail. При создании этих строк используйте только строки идентификаторов местоположений, где location_type = 'G'

  • необходимо убедиться, что один и тот же location_id не является последовательным

Я в настоящее время, сохраняя tour_detail (tour_time) в MMDDYYYY HH24: MI: SS, и мне нужно только HH: SS.

 ALTER SESSION SET.  NLS_DATE_FORMAT = 'MMDDYYYY HH24:MI:SS';



CREATE TABLE locations AS
SELECT level AS location_id,
   'Door ' || level AS location_name,

CASE.    round(dbms_random.value(1,3)) 
        WHEN 1 THEN 'A' 
        WHEN 2 THEN 'T' 
        WHEN 3 THEN 'G' 
     END AS location_type

FROM   dual
CONNECT BY level <= 25;


ALTER TABLE locations 
     ADD ( CONSTRAINT location_id_pk
   PRIMARY KEY (location_id));


CREATE TABLE tour_hdr AS
SELECT level AS tour_id,
   'Tour ' || level AS tour_name
FROM   dual
CONNECT BY level <= 15;


 ALTER TABLE tour_hdr
     ADD ( CONSTRAINT tour_hdr_id_pk
   PRIMARY KEY (tour_id));


create table tour_detail 
(
      tour_id NUMBER(4),
      tour_time DATE,
      location_id NUMBER(4)
 )

declare
  v_loc number;      
  v_prev_loc number := 0;
  v_dt date := trunc(sysdate);
  v_dt_save date := trunc(sysdate);
begin

 for trs in ( select tour_id  from tour_hdr)
  loop

   -- for each  tour generate 15 to 25 rows
    for i in 1..dbms_random.value(15, 25) loop
   
    
   -- If date >23:45:00 reset. Should I
  -- interval be used instead of date

   IF v_dt > (v_dt_save + (1/1440*1425))
   THEN 
   
      -- reset time 
        v_dt :=  v_dt_save;

    ELSE

    -- increase last used date by random 6 to 12 minutes
      
   v_dt := v_dt + dbms_random.value(6,12)/(24*60);

   END IF;

 -- get random location
  select location_id 
    into v_loc 
    from (select location_id from locations where location_type = 'G' order by dbms_random.value) 
    where rownum = 1;

   IF v_prev_loc != v_loc
   THEN
        insert into tour_detail (tour_id, tour_time, location_id)
       values (trs.tour_id, v_dt, v_loc);
       v_prev_loc := v_loc;
    END IF;

  end loop;
 end loop;
end;

Моя цель - извлечь запись из tour_detail и найти запись для таблицы access_history и посмотреть, успел ли охранник, рано или поздно, не добраться до этого места. Короче говоря, мне нужно будет сравнить MMDDYYYY HH24: MI: SS с строкой временного интервала. Было бы сложно это сделать sh

1 Ответ

1 голос
/ 21 июня 2020

Это не , что ясно, какой результат вы действительно хотите, и должен ли location_id быть фиксированным или случайным (если да, то как?).

Если вы хотите сгенерировать заданное количество строк со случайными значениями интервала, тогда можно использовать рекурсивный cte и dbms_random.value. Вам необходимо определить максимальную длину интервала и количество итераций. Например, это дает вам 10 записей с интервалами до 12 часов:

with cte(rnd, n) as (
    select dbms_random.value, 1 from dual
    union all
    select dbms_random.value, n+ 1 from cte where n < 10
)
select 3 as location_id, rnd * 12 * interval '1' hour as time
from cte order by n

Вы можете превратить это в оператор insert, просто добавив следующую строку в самом начале запроса:

insert into tour_detail (location_id, time)
with ...
select ...

Демонстрация на DB Fiddle :

LOCATION_ID | TIME               
----------: | :------------------
          3 | +00 07:13:32.262069
          3 | +00 03:45:18.965145
          3 | +00 07:13:41.394986
          3 | +00 02:24:19.516714
          3 | +00 11:38:16.000109
          3 | +00 11:11:47.947329
          3 | +00 08:14:54.641965
          3 | +00 02:52:43.090595
          3 | +00 03:44:26.418538
          3 | +00 09:29:35.390110
...