謝俊松,倪飛舟,陳浩強(qiáng)
安徽醫(yī)科大學(xué)計(jì)算機(jī)系,安徽合肥230032
近年來(lái),和其他疾病相比,因心血管疾病而死亡的人數(shù)占到很大一部分,成為危害我國(guó)民眾生命健康的主要原因之一[1]。24 h 動(dòng)態(tài)心電圖能較長(zhǎng)時(shí)間記錄佩戴者的心電信息,但是無(wú)法記錄對(duì)應(yīng)運(yùn)動(dòng)狀態(tài)。醫(yī)學(xué)上判斷一個(gè)人心動(dòng)過(guò)速的標(biāo)準(zhǔn)為心率大于100次/min,如果此人是在運(yùn)動(dòng)過(guò)程中,正常情況下的心率也會(huì)大于100 次/min,所以僅靠心電數(shù)據(jù)不能完全反映用戶的健康情況。用戶在劇烈運(yùn)動(dòng)后心跳恢復(fù)正常水平的時(shí)間在臨床醫(yī)學(xué)上也是心臟健康的一個(gè)重要指標(biāo)。文獻(xiàn)[2-5]研究基于Android 手機(jī)的心電監(jiān)護(hù)。文獻(xiàn)[6-8]研究了遠(yuǎn)程心電監(jiān)護(hù)。
本文提出一種利用Android 手機(jī)內(nèi)置的G-sensor(重力傳感器,又名加速度傳感器)采集x、y 和z 三軸加速度數(shù)據(jù)來(lái)分析運(yùn)動(dòng)狀態(tài)和運(yùn)動(dòng)強(qiáng)度,然后與心電數(shù)據(jù)結(jié)合,得到有運(yùn)動(dòng)情景的動(dòng)態(tài)心電圖,進(jìn)而提高心電圖診斷的準(zhǔn)確性。相比直接在心電采集器中集成新的傳感器的設(shè)計(jì)方案,本文充分利用智能手機(jī)的功能,減少心電采集器和手機(jī)之間的數(shù)據(jù)通信量,提高心電采集器電池續(xù)航能力,降低醫(yī)療成本,這些優(yōu)點(diǎn)都將促進(jìn)該方案的推廣和實(shí)施,具有廣泛的社區(qū)和家庭應(yīng)用前景。
本系統(tǒng)由心電采集器、Android手機(jī)APP、中心服務(wù)器和客戶端(移動(dòng)端和PC 端)4 大部分組成,其中Android 手機(jī)APP 是核心,也是本文重點(diǎn)研究設(shè)計(jì)的部分,它承擔(dān)著心電數(shù)據(jù)的接收和處理,三軸加速度數(shù)據(jù)的采集和處理,以及存儲(chǔ)和發(fā)送心電和運(yùn)動(dòng)數(shù)據(jù)到中心服務(wù)器。
心電采集器負(fù)責(zé)采集心電數(shù)據(jù),Android 手機(jī)通過(guò)藍(lán)牙接收心電數(shù)據(jù)并處理,分析運(yùn)動(dòng)狀態(tài)、運(yùn)動(dòng)強(qiáng)度,并將心電圖和運(yùn)動(dòng)狀態(tài)在手機(jī)上顯示,給出常見的心電異常、跌倒警告,同時(shí)將數(shù)據(jù)通過(guò)移動(dòng)網(wǎng)絡(luò)(3G/4G/5G/WIFI)傳送到中心服務(wù)器,用戶家屬和醫(yī)務(wù)人員可以通過(guò)客戶端與中心服務(wù)器通信,從而實(shí)時(shí)查看用戶心電圖和運(yùn)動(dòng)狀態(tài)圖。
采集器需要采集具有周期性的心電生理信號(hào),同時(shí)接觸人體皮膚工作,要求具有抗干擾和放大心電信號(hào)等功能。本文選擇AD8232[9]調(diào)理模塊,它是一款集成前端,適用于對(duì)心臟生物電信號(hào)進(jìn)行信號(hào)調(diào)理來(lái)進(jìn)行心率監(jiān)護(hù),內(nèi)部主要由一個(gè)專用儀表放大器(IA)、一個(gè)運(yùn)算放大器(A1)、一個(gè)右腿驅(qū)動(dòng)放大器(A2)和一個(gè)中間電源電壓基準(zhǔn)電壓緩沖器(A3)四大部分組成。此外,AD8232 內(nèi)置導(dǎo)聯(lián)脫落檢測(cè)電路和一個(gè)自動(dòng)快速恢復(fù)電路,該電路可在導(dǎo)聯(lián)重新連接后迅速恢復(fù)信號(hào)。
心電信號(hào)采集后需要將數(shù)據(jù)傳輸?shù)紸ndroid APP端,本文的研究前提是使用者隨身攜帶著手機(jī),所以兩者距離較近,可以采用藍(lán)牙通信方式,藍(lán)牙傳輸具有安全、速度快和延遲低等特點(diǎn)[10-11]。本文采用ATK HC-05藍(lán)牙模塊,同時(shí)目前Android主流手機(jī)都自帶藍(lán)牙4.0模塊,相比集成移動(dòng)通信模塊,節(jié)約了開發(fā)成本。
中心服務(wù)器需要不間斷接收手機(jī)端傳輸?shù)臄?shù)據(jù),以及為客戶端提供服務(wù),需要支持多用戶、多設(shè)備并發(fā)連接,長(zhǎng)連接和高并發(fā)是必不可少的,結(jié)合文獻(xiàn)[12-13],本系統(tǒng)選用Netty 作為異步通信框架。
通過(guò)Netty的服務(wù)端功能,啟動(dòng)服務(wù)供手機(jī)端進(jìn)行長(zhǎng)連接。收到手機(jī)發(fā)起的連接請(qǐng)求后,分配一個(gè)Channel用于處理本次連接,接收手機(jī)傳輸?shù)谋O(jiān)護(hù)數(shù)據(jù),定期發(fā)送心跳維持長(zhǎng)連接。整體設(shè)計(jì)如圖1所示。
圖1 中心服務(wù)器整體設(shè)計(jì)圖Fig.1 Overall design of central server
APP需要通過(guò)藍(lán)牙接收心電采集器傳輸?shù)臄?shù)據(jù),繪制心電圖,進(jìn)行QRS 波檢查和常見心電異常檢測(cè),采集三軸加速度數(shù)據(jù)并分析運(yùn)動(dòng)狀態(tài)、繪制運(yùn)動(dòng)狀態(tài)圖,檢測(cè)摔倒,存儲(chǔ)并傳輸必要數(shù)據(jù)到中心服務(wù)器,其中心電圖的繪制、異常檢測(cè)、運(yùn)動(dòng)狀態(tài)分析、繪制運(yùn)動(dòng)狀態(tài)圖是重點(diǎn)和難點(diǎn)。
APP 使用openGL ES(OpenGL for Embedded Systems)來(lái)繪制心電圖,它是三維圖形APIOpenGL的子集,主要為手機(jī)、PDA和游戲主機(jī)等嵌入式設(shè)備而設(shè)計(jì)[14]。自定義控件類ECGView繼承自GLSurfaceView,GLSurfaceView有兩種渲染模式RENDERMODE_CONTINUOUSLY和RENDERMODE_WHEN_DIRTY。RENRENDERMODE_CONTINUOUSLY模式表示系統(tǒng)自動(dòng)觸發(fā)渲染,不需要主動(dòng)調(diào)用代碼,但觸發(fā)時(shí)間間隔較短,經(jīng)過(guò)小米8 手機(jī)測(cè)試大約每隔10~20 ms 即觸發(fā)渲染動(dòng)作,CPU 始終處于高負(fù)荷運(yùn)轉(zhuǎn),手機(jī)耗電速度較快;RENDERMODE_WHEN_DIRTY 模式只有在創(chuàng)建和調(diào)用requestRender()時(shí)才會(huì)觸發(fā)渲染,需要主動(dòng)調(diào)用代碼。 結(jié)合本系統(tǒng)實(shí)際情況,選用RENDERMODE_WHEN_DIRTY 作為心電圖的渲染模式。
藍(lán)牙連接成功后,使用BluetoothSocket 類的getInputStream()方法來(lái)獲取輸入流inputStream,隨后每隔300 ms 讀取一次輸入流inputStream,并存入緩存隊(duì)列ecgDataList 中。為了能及時(shí)處理緩存數(shù)據(jù),同時(shí)降低CPU 開銷,本文提出一種“依據(jù)緩存大小動(dòng)態(tài)調(diào)整時(shí)間間隔”的方法,即如果緩存大于597 字節(jié)(3 個(gè)ecg 數(shù)據(jù)包)則等待100 ms 再次調(diào)用requestRender()方法刷新心電圖,否則等待300 ms。采用此方法,使累積的數(shù)據(jù)得到及時(shí)處理,又降低了CPU使用率,心電圖顯示流暢,系統(tǒng)運(yùn)行效果良好。
本文使用開源的QRS波檢查算法[15-16],下面著重介紹心電異常檢測(cè)算法。
2.2.1 心動(dòng)過(guò)速和心動(dòng)過(guò)緩心動(dòng)過(guò)速和心動(dòng)過(guò)緩都是由于心臟跳動(dòng)過(guò)快或者過(guò)慢引起的,表現(xiàn)為每分鐘的心率值超過(guò)一定值或者低于一定值,具體的值該取多少也有不同的標(biāo)準(zhǔn),如圖2所示是本系統(tǒng)的算法流程,其中低運(yùn)動(dòng)強(qiáng)度指的是靜止?fàn)顟B(tài)(站/躺/坐等):(1)心動(dòng)過(guò)速:低運(yùn)動(dòng)強(qiáng)度下,連續(xù)檢測(cè)到5 個(gè)心率值在100 次/min 以上,則判斷為心動(dòng)過(guò)速。使用參數(shù)iHrFastSum來(lái)標(biāo)識(shí)滿足條件(心率100次/min以上)的連續(xù)QRS波個(gè)數(shù),每當(dāng)檢測(cè)到一個(gè)心率值在100以上,則iHrFastSum加1,同時(shí)判斷iHrFastSum是否為5,等于5則檢測(cè)到心動(dòng)過(guò)速并把iHrFastSum置為0;每當(dāng)檢測(cè)到一個(gè)心率值在100以下,則把iHrFastSum置為0。另外,在高運(yùn)動(dòng)強(qiáng)度下不進(jìn)行檢測(cè)。(2)心動(dòng)過(guò)緩:連續(xù)檢測(cè)5個(gè)心率值在60次/min以下,則判斷為心動(dòng)過(guò)緩,其算法實(shí)現(xiàn)與心動(dòng)過(guò)速類似。
圖2 心動(dòng)過(guò)速和過(guò)緩算法流程圖Fig.2 Algorithm flowchart of tachycardia and bradycardia
2.2.2 二聯(lián)律和三聯(lián)律二聯(lián)律和三聯(lián)律在心電圖上都表現(xiàn)為連續(xù)波形的周期性變化,下面是關(guān)于其檢測(cè)算法的描述:(1)二聯(lián)律:低運(yùn)動(dòng)強(qiáng)度下,相鄰2n、2n+1 的RR 間隔超過(guò)100 ms,2n、2n+2、2n+4…RR 間隔小于50 ms;2n+1、2n+3、2n+5…RR 間隔小于50 ms。檢測(cè)到5 個(gè)這樣的周期變化波形則判斷為二聯(lián)律。檢測(cè)算法思想為:使用一個(gè)隊(duì)列iHrQueue存放RR 間隔值,變量iBigeminySum 記錄已有滿足二聯(lián)律條件的QRS 波個(gè)數(shù)。首先從iHrQueue 隊(duì)列尾部取最后4個(gè)數(shù),看是否滿足上述條件,不滿足就將iBigeminySum 置0,并且退出函數(shù)。當(dāng)最后4 個(gè)數(shù)滿足條件時(shí),再看iBigeminySum 的值,如果為0(表示n-1 到n-5 不滿足條件),將iBigeminySum 置為4 并退出函數(shù)。如果不為0 則從后向前比較2n分別與2n+2、2n+4、2n+6…的RR間隔(iBigeminySum>0表示,前面幾個(gè)數(shù)間的間隔已經(jīng)比較過(guò),2n與2n+1 間的間隔也已經(jīng)比較過(guò)并都滿足條件),如果哪一步間隔不滿足條件,用比較時(shí)的臨時(shí)變量給iBigeminySum 賦值(分奇偶不同),并退出函數(shù)。如果全部滿足條件,則檢查iBigeminySum是否為10,是則說(shuō)明檢測(cè)到二聯(lián)律。(2)三聯(lián)律:低運(yùn)動(dòng)強(qiáng)度下,相鄰3n、3n+1、3n+2的RR間隔不同,最大和最小RR 間隔差距超過(guò)100 ms,RR間隔呈周期性變化。3n、3n+3、3n+6…RR 間隔小于50 ms;3n+1、3n+4、3n+7…RR 間隔小于50 ms;3n+2、3n+5、3n+8…RR間隔小于50 ms。檢測(cè)到5個(gè)這樣的周期變化波形則判斷為三聯(lián)律,其算法實(shí)現(xiàn)思想與二聯(lián)律類似。
2.2.3 心律失常心律失常:低運(yùn)動(dòng)強(qiáng)度下,相鄰RR間隔變化超過(guò)較短RR間隔的1/2,出現(xiàn)10次以上后則判斷為心率失常。由于是通過(guò)相鄰RR間隔比較得到是否異常,為了避免同一RR間隔和前后兩個(gè)RR間隔比較得到兩次異常,使用布爾變量isHrAbnormalRecord作標(biāo)記。變量iHrAbnormalSum表示心率失常個(gè)數(shù)的累積量。當(dāng)檢測(cè)到一次心律失常時(shí),iHrAbnormalSum加1,同時(shí)將isHrAbnormalRecord置為true。檢測(cè)函數(shù)開始將判斷isHrAbnormalRecord是否為true,是則退出函數(shù),并把isHrAbnormalRecord置為false;不是則進(jìn)行下面的檢測(cè)。在iHrAbnormalSum加1后為10時(shí),則判斷檢測(cè)到心律失常。
為了和心電圖作對(duì)比,軟件設(shè)計(jì)將運(yùn)動(dòng)狀態(tài)圖放在心電圖的下方,看到心電圖的同時(shí)也能看到對(duì)應(yīng)的運(yùn)動(dòng)狀態(tài),運(yùn)動(dòng)狀態(tài)圖和心電圖運(yùn)動(dòng)方向一致,即自右向左移動(dòng)。目前軟件通過(guò)三軸加速度可以分析出靜止(站/坐/躺)、走和跑3種常見的人體運(yùn)動(dòng)狀態(tài)。
自定義SportView 控件繼承自View 類,實(shí)現(xiàn)其onDraw()方法,在onDraw()方法里需要繪制不同運(yùn)動(dòng)狀態(tài)對(duì)應(yīng)的狀態(tài)圖。設(shè)計(jì)手機(jī)滿屏下可以完整顯示3 個(gè)運(yùn)動(dòng)狀態(tài)圖,每個(gè)運(yùn)動(dòng)狀態(tài)圖對(duì)應(yīng)寬度為rWidth=screenWidth/3,并將繪制的運(yùn)動(dòng)狀態(tài)數(shù)據(jù)放入stepValues列表中,每隔300 ms刷新一次。
Android內(nèi)置G-sensor可以檢測(cè)x、y和z軸3個(gè)方向的加速度(單位m/s2),運(yùn)動(dòng)姿態(tài)會(huì)產(chǎn)生相應(yīng)方向加速度。根據(jù)文獻(xiàn)[17-18]知道,不管如何佩戴手機(jī),總有至少一個(gè)軸具有相對(duì)較大的周期性加速度變化。步行的時(shí)候主要運(yùn)動(dòng)方向是前進(jìn)方向和垂直方向,呈現(xiàn)周期性變化;垂直方向:抬腳時(shí),重心向上,加速度正向增加;兩腳觸地時(shí),重心下移,加速度反向減少;水平方向:抬腳時(shí),加速度增加;收腳時(shí),加速度減小。
本文需要分析出正常步行和跑步,對(duì)于普通人來(lái)說(shuō),二者的區(qū)別僅僅是在步頻上,正常步行的步頻為90~120 步/min,如果大于120 步/min,則認(rèn)為人處于跑的狀態(tài),通過(guò)步頻來(lái)檢測(cè)步行和跑狀態(tài)[19]。將三軸的加速度值合成一個(gè)加速度矢量|V|,計(jì)算式子為,該值在步行時(shí)基本是正弦曲線變化規(guī)律?;舅枷胧牵ㄟ^(guò)對(duì)該加速度矢量的長(zhǎng)度和方向的判斷,來(lái)判斷是否經(jīng)過(guò)波峰或者波谷,通過(guò)峰值的計(jì)算以及加速度的閾值決策來(lái)實(shí)時(shí)計(jì)算步數(shù),得到步頻,進(jìn)而判斷出運(yùn)動(dòng)狀態(tài),具體實(shí)現(xiàn)步驟如下:(1)使用均值濾波器對(duì)x、y、z的值進(jìn)行濾波:每4個(gè)數(shù)求平均值,使用求得的平均值作為輸出,來(lái)計(jì)算和加速度|V|,使數(shù)據(jù)更加平滑。(2)檢測(cè)波峰波谷:使用變量isUp 來(lái)標(biāo)識(shí)當(dāng)前|V|值是上升還是下降,如果是上升則使用conUpCount 來(lái)記錄持續(xù)上升次數(shù),如果是下降將isUp=false,conUpCount=0。檢測(cè)到波峰的條件是當(dāng)前|V|值是下降,之前是上升并且上升次數(shù)至少大于2 或之前的值大于20。檢測(cè)到波谷的條件是之前為下降現(xiàn)在為上升。(3)去干擾:文獻(xiàn)[19]可知正常行走兩步時(shí)間間隔為200~2 000 ms,由此檢測(cè)最近兩次波峰的時(shí)間差,去除高頻噪音。(4)動(dòng)態(tài)閾值(thresholdValue)判斷波峰有效性:因?yàn)椴煌謾C(jī)型號(hào)內(nèi)置的加速度傳感器可能不同,導(dǎo)致靈敏度也可能不同。算法通過(guò)調(diào)整動(dòng)態(tài)閾值來(lái)判斷波峰的有效性,只有當(dāng)波峰的值peakValue 和波谷的值valleyValue 之間的差值大于thresholdValue 才是有效波峰。thresholdValue 的值是根據(jù)最近4 次波峰波谷的差值來(lái)計(jì)算。(5)去除錯(cuò)誤步數(shù):設(shè)計(jì)連續(xù)運(yùn)動(dòng)大于5步才正式計(jì)步,計(jì)算步頻。
對(duì)于靜止?fàn)顟B(tài)(站/坐/躺)檢測(cè)比較簡(jiǎn)單,根據(jù)上面的步驟(1)計(jì)算得到的|V|,計(jì)算最近10 個(gè)值的方差,如果方差值小于0.1則說(shuō)明處于靜止?fàn)顟B(tài)。
摔倒如果發(fā)生在老年人身上是非常危險(xiǎn)的,特別是患有心臟疾病的老年人,所以本系統(tǒng)也把摔倒作為一個(gè)運(yùn)動(dòng)異常發(fā)出報(bào)警信息。結(jié)合文獻(xiàn)[20]設(shè)計(jì)本系統(tǒng)的摔倒檢測(cè)算法,具體步驟如下:(1)中值濾波:中值濾波器濾波函數(shù)為y=medfilt1(x,n),其中x是待濾波的三軸加速度信號(hào)|V|,n為窗口大小,此處n設(shè)計(jì)為3,150 個(gè)數(shù)據(jù)為一組進(jìn)行濾波,即y(k)是x(k-1:k+1)的中值。當(dāng)k處于邊緣時(shí),即k=0 或149 時(shí),y(k)分別取Median[0 1 2]和Median[148 149 0]。(2)檢測(cè)摔倒:使用閾值法,低閾值lowThresholdValue=5,高閾值highThresholdValue=25,根據(jù)步驟(1)得到的數(shù)據(jù),如果前面有值小于lowThresholdValue,而后面的值至少有一個(gè)大于highThresholdValue,則判斷為出現(xiàn)預(yù)摔倒。(3)降低誤檢率:如果發(fā)生摔倒,后面一段時(shí)間的運(yùn)動(dòng)狀態(tài)不可能是走或跑,特別是老年人,系統(tǒng)為了降低誤檢率,當(dāng)檢測(cè)到預(yù)摔倒后,繼續(xù)判斷后面5 s內(nèi)的運(yùn)動(dòng)狀態(tài),如果不是走或跑,則發(fā)出摔倒警告。
本次測(cè)試使用的是小米8 手機(jī),運(yùn)動(dòng)情景心電圖界面如圖3所示,可以正常查看到心電波形、運(yùn)動(dòng)狀態(tài)、實(shí)時(shí)心率和步頻。圖4為連續(xù)檢測(cè)到5個(gè)大于100次/min 的心率值,并且運(yùn)動(dòng)情景不是跑、走等高強(qiáng)度狀態(tài),彈出了警告信息,同時(shí)將警告短信發(fā)送至預(yù)留手機(jī)號(hào),達(dá)到了預(yù)期設(shè)計(jì)。圖5所示為PC 客戶端對(duì)用戶的監(jiān)護(hù)界面,界面展示的信息更加全面,可以統(tǒng)計(jì)時(shí)段內(nèi)的所有異常情況,實(shí)現(xiàn)了有運(yùn)動(dòng)情景的動(dòng)態(tài)心電遠(yuǎn)程監(jiān)護(hù)。
圖3 運(yùn)動(dòng)情景心電圖Fig.3 Electrocardiogram with the recognition of motion states
圖4 心電異常Fig.4 Abnormal electrocardiogram
圖5 PC客戶端監(jiān)護(hù)Fig.5 PC client monitoring
本文研究設(shè)計(jì)了基于G-sensor的有運(yùn)動(dòng)情景動(dòng)態(tài)心電監(jiān)護(hù)系統(tǒng),重點(diǎn)介紹了Android APP的設(shè)計(jì),研究和實(shí)現(xiàn)了運(yùn)動(dòng)狀態(tài)分析算法,最終完成了有運(yùn)動(dòng)情景心電圖的顯示,為醫(yī)生的診斷提供了情景數(shù)據(jù),同時(shí)在PC和手機(jī)端也能遠(yuǎn)程實(shí)時(shí)監(jiān)護(hù)。該系統(tǒng)設(shè)計(jì)時(shí)充分使用了Android手機(jī)已有的功能,降低了設(shè)備和醫(yī)療成本,為將來(lái)的遠(yuǎn)程醫(yī)療提供了新的設(shè)計(jì)思路。