У меня есть функция, get_untracked_moves
, ниже. Моя цель состоит в том, чтобы для всех данных между двумя диапазонами дат находить последовательные события, которые находятся дальше, чем p_separation_distance
.PL/pgSQL: Сравнение последовательных строк
т.д .:
Если событие 1 и событие 2 40 м друг от друга, когда p_separation_distance 100й, запись будет возвращена с событием 1 ассоциированной cont_name как source_name
и События 2 в cont_name как target_name
.
CREATE FUNCTION get_untracked_moves(IN p_since_date TIMESTAMP WITHOUT TIME ZONE, IN p_before_date TIMESTAMP WITHOUT TIME ZONE, IN p_separation_distance INTEGER)
RETURNS TABLE (id INTEGER,
asset_name CHARACTER VARYING,
source_name CHARACTER VARYING,
target_name CHARACTER VARYING,
source_time TIMESTAMP WITHOUT TIME ZONE,
target_time TIMESTAMP WITHOUT TIME ZONE,
source_lat DOUBLE PRECISION,
source_lon DOUBLE PRECISION,
target_lat DOUBLE PRECISION,
target_lon DOUBLE PRECISION) AS $$
DECLARE
d_previous_location GEOMETRY;
d_previous_name CHARACTER VARYING;
d_previous_time TIMESTAMP WITHOUT TIME ZONE;
d_cur record;
BEGIN
-- Begin @ 0,0
d_previous_location := st_setsrid(st_makepoint(0,0), 4326);
d_previous_name := '';
d_previous_time := NULL;
FOR d_cur
IN
SELECT
rank() OVER (PARTITION BY events.asset_id ORDER BY events.event_time) AS idx,
tags.id asset_id,
tags.name asset_name,
d_previous_name,
conts.name cont_name,
events.position,
events.event_time evt_time
FROM
events
JOIN
assets tags ON tags.id = events.asset_id
JOIN
assets conts ON conts.id = events.container_asset_id
WHERE
events.event_time >= p_since_date
AND
events.event_time <= p_before_date
LOOP
IF (d_previous_time = NULL) THEN
d_previous_time := events.event_time;
END IF;
IF (st_distancesphere(events.position, d_previous_location)>=p_separation_distance) THEN
RETURN NEXT;
END IF;
d_previous_location := events.position;
d_previous_name := conts.name;
d_previous_time := events.event_time;
END LOOP;
END;
$$
LANGUAGE plpgsql VOLATILE;
Функция создает отлично, но когда я иду, чтобы запустить его с:
select * from get_untracked_moves('2015-11-1', '2015-12-1', 10000);
я получаю:
ERROR: missing FROM-clause entry for table "events"
LINE 1: SELECT (st_distancesphere(events.position, d_previous_locati...
^
QUERY: SELECT (st_distancesphere(events.position, d_previous_location)>=p_separation_distance)
CONTEXT: PL/pgSQL function "get_untracked_moves" line 41 at IF
********** Error **********
ERROR: missing FROM-clause entry for table "events"
SQL state: 42P01
Context: PL/pgSQL function "get_untracked_moves" line 41 at IF
Что я здесь отсутствует? Я думал, что включение FROM events
в мое заявление SELECT
было достаточно.
Вы должны читать на 'LAG()' функции окна и сделать все это в SQL ... –
Спасибо за предложение! Я бы очень хотел это сделать, но plpgsql; есть еще одна логика, которую я удалил, пытаясь сделать это как можно меньше, чтобы воспроизвести. – FuriousFolder
'событий' не существует внутри цикла. Обратитесь к этому столбцу как 'd_cur.position' –