MIMICIII 数据库中患者住院次数分布
数据库中三个病人ID
最近在用MIMICIII数据库提取一些数据,突然意识到一个问题,提取出的数据很多患者都是多次入院的。因此,特地去查看下数据库中到底有多少患者住了多少次的医院。
在MIMICIII数据库中,存在这三个病人ID,分别为:subject_id, hadm_id, icustay_id。这三个不同的ID分别代表了不同的意义:
subject_id:
在数据库的官方文档是这样描述的:
SUBJECT_ID is a unique identifier which specifies an individual patient.
因此subject_id代表了每一个患者,在数据库中,一个subject_id就收入了一个患者。
hadm_id
数据库的官方文档,对于hamd_id的定义为:
HADM_ID, which represents a single patient’s admission to the hospital.
hadm_id相当于国内医院的住院号,每一次的住院就会自动给你生成一个住院号,一个患者可能会拥有多个住院号。
icustay_id
这个标识符用于患者在ICU中停留,在官方文档的解释是:
ICUSTAY_ID is unique to a patient ICU stay.
当然,一个患者一次住院可以有多次进入ICU。但是同时也存在这一个ICU转入另一个ICU单元时,icustay_id不变的情况:
As an ICUSTAY_ID groups all ICU admissions within 24 hours of each other, it is possible for a patient to be transferred from one type of ICU to another and have the same ICUSTAY_ID.
理解这三个不同的标识符很重要,详情可以仔细阅读MIMICIII数据库的官方文档。
数据库患者住院次数的分布
在这里,我们主要使用SQL查询语句进行查询。想要知道“每个患者在这个数据库中住了多少次医院?”,我们只需要知道,“每个患者到底有多少个hamd_id”,也就是说,“在以hadm_id,作为唯一标识符的ADMISSIONS表中,查看出现了多少次的subject_id”就行了。
使用聚合函数进行查询
要完成上述这个目标,我们需要对ADMISSIONS表进行聚合查询。聚合函数有很多,以下五种比较常用:
- COUNT:计算表中的记录数目
- SUM:计算表中数值列中数据的合计值
- AVG:计算表中数值列中数据的平均值
- MAX:计算表中数值列中数据的最大值
- MIN:计算表中数值列中数据的最小值
我们所需要的是COUNT
函数来计算出现多少次的subject_id。当然,仅仅使用COUNT
函数,回报的就是这个表有多少行。比如:
SELECT COUNT(*)
FROM mimiciii.admissions
执行结果为:
count
------
58976
所以,我们还需要使用GROUP BY
语句进行分组,查询如下:
SELECT subject_id,count(*) as admissiontimes
FROM mimiciii.admissions
GROUP BY subject_id
这样,我们就可以得到每个subject_id出现了多少次了。
那么,如果我们想要得到仅仅只住了一次医院的病人怎么办?
我们可以使用HAVING
子句在分组中选择住院一次的患者:
SELECT subject_id,COUNT(*) as admissiontimes
FROM mimiciii.admissions
GROUP BY subject_id
HAVING COUNT(*) =1
至于,HAVING
和WHERE
子句的区别,这里主要简单的提一点。
WHERE
子句是指定行所对应的条件,而HAVING
子句指定组所对应的条件。
使用R链接数据库进行绘图
比起SQL,我更加喜欢把数据导入到R进行探索和分析。这个过程最容易联想到的是,从SQL的软件中将查询好的表格导出,然后用R将表格进行导入。其实不用那么麻烦,在R中提供了外接数据库的包,这里我使用的是PostgreSQL,因此我在R中配置的也是这个数据的包。由于我嫌麻烦,所以直接写了一个函数,方便直接调用进行查询,具体代码如下:
#载入数据库的包
library(RPostgreSQL)
library(DBI)
#连接数据库,并将其封装为一个函数
query <-function(query)
{
drv<-dbDriver("PostgreSQL")
con<-dbConnect(drv,host="localhost",port="5432",dbname="mimic",
user="",password="") ## 这里删除了用户名和密码
on.exit(
{
dbDisconnect(con)
}
)
dbGetQuery(con,query)
}
这样我就可以调用函数直接导入数据:
## MIMIC数据库中患者入院次数的统计
### 将SQL语句传入pt_sql的向量中
pt_sql <- "SELECT subject_id,count(*) as admissiontimes
FROM mimiciii.admissions
GROUP BY subject_id"
### 进行查询
pt_times <- query(pt_sql)
### 生成表格
x <- table(pt_times$admissiontimes)
###绘制条形图
barplot(x)
得到的结果挺让我惊讶的。
居然最多的患者住了42次医院?!
好了,这次就这样,如有错误,请大家多多指正。