2014-04-14 17 views
22

Tôi có bảng sau đây, cung cấp nhiều địa chỉ email cho mỗi người dùng.Postgres - Chuyển Hàng đến Cột

enter image description here

tôi cần phải làm phẳng này ra để cột trên một truy vấn người dùng. Để cung cấp cho tôi địa chỉ email "mới nhất" dựa trên ngày tạo.

user.name | user.id | email1   | email2   | email3** 

Mary  | 123  | [email protected] | [email protected] | [email protected] 

Joe  | 345  | [email protected] | [NULL]   | [NULL] 

Trả lời

33

Sử dụng crosstab() từ mô-đun tablefunc.

SELECT * FROM crosstab(
    $$SELECT user_id, user_name, rn, email_address 
    FROM (
     SELECT u.user_id, u.user_name, e.email_address 
      , row_number() OVER (PARTITION BY u.user_id 
          ORDER BY e.creation_date DESC NULLS LAST) AS rn 
     FROM usr u 
     LEFT JOIN email_tbl e USING (user_id) 
     ) sub 
    WHERE rn < 4 
    ORDER BY user_id 
    $$ 
    , 'VALUES (1),(2),(3)' 
    ) AS t (user_id int, user_name text, email1 text, email2 text, email3 text); 

Tôi đã sử dụng ký hiệu đô la cho tham số đầu tiên, không có ý nghĩa đặc biệt. Nó chỉ là tiện lợi nếu bạn có để thoát khỏi dấu nháy đơn trong chuỗi truy vấn mà là một trường hợp phổ biến:

lời giải thích chi tiết và hướng dẫn tại đây:

Và đặc biệt, đối với "cột bổ sung":

Các đặc biệt khó khăn đây là:

  • Việc thiếu tên chủ chốt.
    -> Chúng tôi thay thế bằng row_number() trong truy vấn con.

  • Số lượng email khác nhau.
    -> Chúng tôi giới hạn tối đa. của ba ở bên ngoài SELECT
    và sử dụng crosstab() với hai thông số, cung cấp danh sách các khóa có thể có.

Chú ý đến NULLS LAST in the ORDER BY.

+2

hoàn hảo, thankyou. Có chính xác những gì tôi cần. Truy vấn này sẽ vượt xa tôi một chút, nhưng đã giúp tôi học hỏi và hiểu được nhiều. – dacology

+0

Đối với những người tự hỏi. Không, điều này không hoạt động trên AWS Redshift. –

+0

@MarcelloGrechiLins: Giải pháp này dành cho Postgres chứ không phải Redshift. –

8

Nếu bất cứ ai khác mà tìm thấy câu hỏi này và cần một giải pháp năng động cho điều này, nơi bạn có một số lượng không xác định các cột để transpose đến và đi không chính xác 3, bạn có thể tìm thấy một giải pháp tốt đẹp ở đây: https://github.com/jumpstarter-io/colpivot

Các vấn đề liên quan