Mysql
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Mysql

Tính toán phương tiện cho nhiều cột trong cùng một bảng trong một lệnh gọi truy vấn

Điều này là một nỗi đau lớn ở cổ trong MySQL. Bạn có thể khôn ngoan khi sử dụng Oracle Express Edition hoặc postgreSQL miễn phí nếu bạn định thực hiện rất nhiều công việc xếp hạng thống kê này. Tất cả chúng đều có MEDIAN(value) tổng hợp các chức năng được tích hợp sẵn hoặc có sẵn dưới dạng phần mở rộng. Đây là một sqlfiddle nhỏ chứng minh điều đó. http://sqlfiddle.com/#!4/53de8/6/0

Nhưng bạn đã không hỏi về điều đó.

Trong MySQL, vấn đề cơ bản của bạn là phạm vi của các biến như @rownum. Bạn cũng có một vấn đề xoay vòng:đó là bạn cần chuyển các hàng trong truy vấn của mình thành cột.

Trước tiên, hãy giải quyết vấn đề xoay vòng. Những gì bạn sẽ làm là tạo một liên hợp của một số truy vấn lớn. Ví dụ:

SELECT 'median_wages' AS tag, wages AS value
  FROM (big fat query making median wages) A
 UNION
SELECT 'median_volunteer_hours' AS tag, hours AS value
  FROM (big fat query making median volunteer hours) B
 UNION
SELECT 'median_solvent_days' AS tag, days AS value
  FROM (big fat query making median solvency days) C

Vì vậy, đây là kết quả của bạn trong một bảng các cặp thẻ / giá trị. Bạn có thể xoay bảng đó như vậy, để lấy một hàng với một giá trị trong mỗi cột.

SELECT SUM( CASE tag WHEN 'median_wages' THEN value ELSE 0 END 
          ) AS median_wages, 
SELECT SUM( CASE tag WHEN 'median_volunteer_hours' THEN value ELSE 0 END
          ) AS median_volunteer_hours, 
SELECT SUM( CASE tag WHEN 'median_solvent_days' THEN value ELSE 0 END 
          ) AS median_solvent_days
FROM (
    /* the above gigantic UNION query */
 ) Q

Đó là cách bạn xoay vòng các hàng (từ truy vấn UNION trong trường hợp này) thành các cột. Đây là một hướng dẫn về chủ đề này. http://www.artfulsoftware.com/infotree/qrytip.php?id =523

Bây giờ chúng ta cần giải quyết các truy vấn con tính toán trung bình. Mã trong câu hỏi của bạn trông khá tốt. Tôi không có dữ liệu của bạn nên rất khó để tôi đánh giá nó.

Nhưng bạn cần tránh sử dụng lại biến @rownum. Gọi nó là @ rownum1 trong một trong các truy vấn của bạn, @ rownum2 trong truy vấn tiếp theo, v.v. Đây là một trò chơi sql dinky chỉ làm một trong những điều này. http://sqlfiddle.com/#!2/2f770/1/0

Bây giờ chúng ta hãy xây dựng nó một chút, làm hai phương tiện khác nhau. Đây là fiddle http://sqlfiddle.com/#!2/2f770/2/ 0 và đây là truy vấn UNION. Thông báo nửa sau của truy vấn liên hợp sử dụng @rownum2 thay vì @rownum .

Cuối cùng, đây là truy vấn đầy đủ với xoay vòng. http://sqlfiddle.com/#!2/2f770/13/0

 SELECT SUM( CASE tag WHEN 'Boston' THEN value ELSE 0 END ) AS Boston,
           SUM( CASE tag WHEN 'Bronx' THEN value ELSE 0 END ) AS Bronx   
   FROM (
 SELECT 'Boston' AS tag, pop AS VALUE
  FROM (
        SELECT @rownum := @rownum +1 AS  `row_number` , pop
          FROM pops, 
        (SELECT @rownum :=0)r
          WHERE pop >0 AND city = 'Boston'
          ORDER BY pop
        ) AS ordered_rows, 
        ( 
         SELECT COUNT( * ) AS total_rows
           FROM pops
          WHERE pop >0 AND city = 'Boston'
        ) AS rowcount
  WHERE ordered_rows.row_number = FLOOR( total_rows /2 ) +1
  UNION ALL
 SELECT 'Bronx' AS tag, pop AS VALUE
  FROM (
        SELECT @rownum2 := @rownum2 +1 AS  `row_number` , pop
          FROM pops, 
        (SELECT @rownum2 :=0)r
          WHERE pop >0 AND city = 'Bronx'
          ORDER BY pop
        ) AS ordered_rows, 
        ( 
         SELECT COUNT( * ) AS total_rows
           FROM pops
          WHERE pop >0 AND city = 'Bronx'
        ) AS rowcount
  WHERE ordered_rows.row_number = FLOOR( total_rows /2 ) +1
) D

Đây chỉ là hai trung gian. Bạn cần năm. Tôi nghĩ rằng thật dễ dàng để xảy ra trường hợp tính toán trung bình này là khó thực hiện trong MySQL trong một truy vấn duy nhất.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Các hàm được lưu trữ trong MySQL - Tên cột &bảng động / biến

  2. Kiểu dữ liệu MySQL tương ứng với Java Date ()

  3. Sử dụng kết quả SQL trong vòng lặp foreach

  4. Kiểm soát phiên bản MySQL - Subversion

  5. MySQL lưu trữ lỗi cú pháp thủ tục sau khi BEGIN