tags:

views:

70

answers:

1

I have a table with data that looks like this:

create table demo_patient_info (
  attend timestamp,  
  patient_id int, 
  blood_pressure double
);

I would like to write (preferably ANSI) SQL queries that allow me to do the following:

query1:

return the difference between bp of all patients with each other (using a WHERE clause to restrict the number of rows returned in the cartesian product)

query2:

return the difference between bp of each patient and one specific (i.e. specified) patient in the table

+5  A: 

1)

SELECT 
    t1.patient_id
   ,t2.patient_id
   ,t1.blood_pressure - t2.blood_pressure as bp_diff
FROM
   demo_patient_info t1
CROSS JOIN
   demo_patient_info t2
WHERE
   t1.patient_id < t2.patient_id

2)

SELECT 
    t1.patient_id
   ,t2.patient_id
   ,t1.blood_pressure - t2.blood_pressure as bp_diff
FROM
   demo_patient_info t1
CROSS JOIN
   demo_patient_info t2
WHERE 
   t2.patient_id = 1

This will likely give two rows for each match though, which may or may not be OK

edit: WHERE t1.patient_id < t2.patient_id in query 1 is there to prevent the following, duplication and self matching

ID1 ID2  diff 
1    2    1.4 
2    1    1.4 
1    1     0

thanks to Jonathan Leffler for the hint :)

Paul Creasey
Pure SQL poetry. I havent tried it out yet. But it is aesthesticly pleasing (if that makes sense)
Stick it to THE MAN
Not sure I understand. Why will it give two rows for each match?. Assuming it does though, can I not use a SELECT DISTINCT to make sure the rows are unique?
Stick it to THE MAN
edited the post to explain the duplicates.
Paul Creasey
Ah thanks, I understand what you mean now. Its not a problem
Stick it to THE MAN
The CROSS JOIN should be filtered with a condition - usually t1.patient_id < t2.patient_id to remove self-comparisons and to list each pair just once.
Jonathan Leffler
Ah yes, good plan Jon, edited.
Paul Creasey