2014-12-09 2 views
3

Я пытаюсь написать запрос SQL (Proc SQL), чтобы получить данные из таблицы, например:SAS SQL иерархический запрос

 
order_id   base_order_id   customer_id 
========================================================== 
1      null       1 //only one transaction 
------------------------------------------------------------------------------- 
2      null       1    //order_start 
3      2        1 
4      3        1    
5      4        1 
6      5        1 
7      6        1    //order_end 
------------------------------------------------------------------------------- 

следующим образом:

 
order_id   last_order_id   customer_id 
1      null       1     
2      7        1      

Позвольте мне это так , Order_id 2 имеет 6 подпроцессов. Мы можем предположить, что полный заказ для этого одного клиента состоит из order_id от 2 до 7. Order start = order_id 2, когда весь заказ заканчивается на order_id 7.

Я начинаю в sas sql. Я попытался присоединиться к той же таблице через левое соединение, «имея», но ничего не получилось. Есть ли способ получить результат запроса, как в таблице 2?

Заранее спасибо.

EDIT2. SQL я написал, что приносит самый близкий результат.

SELECT t1.order_id, t1.base_order_id as last_order_id, t1.customer_id 

FROM table1 t1 

GROUP BY t1.order_id 
    HAVING (t1.order_id = max(t1.base_order_id) 
    or t1.base_order_id IS NULL) 
+1

Я не знаю, как это сделать, используя SQL proc SQL. Но вы можете сделать это в базовой базе данных, используя там рекурсивную/иерархическую функциональность. Или, используя другие функции в системе SAS. –

+0

Можете ли вы объяснить, как вычисляется last_order_id? Это не совсем понятно мне из примера. – JJFord3

+0

@ JJFord3 Я редактировал свой пост. Надеюсь, теперь это намного яснее для Тебя. – vengen

ответ

2

Так как Гордон говорит в комментариях, я не могу придумать способ сделать это в PROC SQL.

Однако способ «SAS» для этого был бы связанным анализом компонентов. PROC OPTNET в SAS/OR делает именно это.

data have; 
input order_id base_order_id customer_id; 
datalines; 
1 . 1 
2 . 1 
3 2 1 
4 3 1 
5 4 1 
6 5 1 
7 6 1 
; 
run; 

/*Connect the first order to itself*/ 
data have; 
set have; 
if base_order_id = . then base_order_id = order_id; 
run; 

/*Use SAS/OR and connected components*/ 
proc optnet 
    data_links = have(rename=(order_id = to base_order_id = from)) 
    out_nodes = out; 
    concomp; 
run; 

/*Summarize and add customer id*/ 
proc sql noprint; 
create table want as 
select a.order_id, 
     a.last_order_id, 
     b.customer_id 
    from (
     select min(node) as order_id, 
       max(node) as last_order_id 
      from out 
      group by concomp 
    ) as a 
     left join 
    test as b 
     on a.order_id = b.order_id; 
quit; 

Это возвращает то, что вы ищете в наборе данных WANT.

+0

большое спасибо.К сожалению, моя компания не предоставила мне SAS/OR. У меня только SAS EG6.1. Поэтому мне придется оставить эту задачу в покое. Спасибо. – vengen

+0

EG - это только ваша IDE. SAS/OR - это компонент, лицензированный, как SAS/STAT или SAS/GRAPH. Возможно, вы не лицензировали его. Попробуйте, и если вы не обнаружите «PROC OPTNET», то у вас его нет. Затем вам необходимо перевернуть свой собственный компонентный анализ на шаге данных. – DomPazz

+0

Спасибо. Как вы сказали ... Я запустил PROC OPTNET, но он дает ошибку - не лицензирован. – vengen

0

Единственный способ, о котором я знаю, требует, чтобы вы добавляли 2 новых столбца к данным, которые вы запрашиваете. Приятное объяснение этого можно найти здесь:

http://www.sitepoint.com/hierarchical-data-database-2/

У меня нет времени прямо сейчас, чтобы расшифровывать, что и положить все это в SO ответа. Я позже изменю этот ответ с помощью некоторого кода, который добавит 2 новых столбца в ваш примерный набор данных. ИМО, это самая сложная часть.

Некоторые хорошие вещи об этом подходе:

  1. Это не рекурсивный - это позволяет для любого SQL запроса, чтобы пройти всю иерархию в один проход.
  2. Он поддерживает индексирование, поэтому, если у вас много данных, ваши запросы будут работать быстрее.
  3. Это довольно легко понять/запросить. Простые запросы могут возвращать мощные результаты. Я использовал этот подход в сложной цепочке поставок, чтобы определить будущие узкие места с помощью простого простого SQL-запроса.
+0

Спасибо. Ждем Вашего ответа. – vengen

Смежные вопросы