解析HL7协议

前段时间一个项目中用到了HL7协议,这个协议一般只用在医院的项目中。不与医院合作的一般还都不知道,我自己刚接触这个的时候也是一脸的懵逼,其实仔细看看就能看出点门道,主要是协议,肯定都是有一定标准的。HL7也一样,好像是美国发明的,具体我也不说了,有兴趣的同学可以去看看背景什么的。我们只知道怎么用就行了。毕竟就是个协议。网络传输协议可以分为好多层,物理层、网络层、数据链接层、应用层等。如果有做过工控行业的同学,应该知道MODBUS协议,HL7根MODBUS差不多,是应用层协议,定义的只是数据格式。整个协议了解以后也很简单,自己看的时候也是翻了很多东西,资料不是很多,写出来供有需要的朋友参考吧。

在HL7通讯协议中,消息(Message)是数据在系统之间交换的基本单元,每条消息都有各自的消息类型, 用于

消息目的消息类型中有触发事件。一个消息由多个段(Segment)组成,每一段都有相应的名称,用于界定其内容或功能。

而一个段又由多个数据字段(Data Field)组成。一个消息中的第一个段总是消息头段(Message head segment),它指明

了发送和接收的程序名、消息类型、以及一个唯一的消息ID号码等,接下去段的构成由消息的类型决定。如,PID段

(Patient Identification Data)包括姓名、地址、社会保险号等。一个数据字段又有可能由多个组件组成。有些消息可进

一步由事件码(event code)细分。

每个消息头代表了不同的含义,一般一个消息都是以MSH开头的。每个版本的HL7协议都有详细的介绍,这个不同的项目定义也不同。每个段都是以换行结尾,每个数据之间用“|”分割。像这个例子


MSH|^~\&|H01||C13||20170417082206||ORM^O01|2017041708220617041000138810|P|2.4|||NE|AL|CHN|
PID|||000000672850||张三^||1993-11-20 00:00:00.0|F|||^||^^^^^^^^^|||O|||321282199311205225||||||||||||||||||||||
PV1||H|健康服务部^^^TEDAICH|||健康服务部^^^TEDAICH|||||||||||000498|99^自费|170410001388^^^^某某医院|||||||||||||||||||||||||20170417082206||
ORC|NW|170410504932||170410001388^10||N|||20170417082206|000498^张|||健康服务部|
OBR||17041000138810||Y0102032^*核素-14C尿素呼气试验^C14^碳14^Y0102^其他部位^Y1^ECT^99^~E0100014~120.0~1.0~碳--14呼气试验查幽门菌|||||||||||||0407^核医学科||N|120.0||
NTE|1|P||
DG1|||^^ICD-10|||A||||||||||^|


知道了协议的组成,解析就很简单了。先以换行符分割整个消息,再用| 分割数据,在根据自己的需求提取数据就ok了


int SplitString(char * source, CString split, CStringArray &strArray)
{
	strArray.RemoveAll();
	//const char * split = "\r\n";
	char * p;
	p = strtok(source, split);
	while (p != NULL) {
		CString str(p);
		strArray.Add(str);
		p = strtok(NULL, split);
	}
	return strArray.GetCount();
}

//以单个字符 "|"分割
int ExtString(CString str, CString split, CStringArray &strArray)
{
	CString strTemp;
	int nCount = 0;
	strArray.RemoveAll();
	while (str.Find(_T(split)) != -1)
		//查找字符串中是否有“|”出现 
	{
		strTemp = str.Left(str.Find(_T(split)));
		//提取字符串 
		str = str.Right(str.GetLength() - str.Find(_T(split)) - 1);
		//剩下的字符串 
		strArray.Add(strTemp);
		//提取出的字符加入动态数组 
		nCount++;
	}
	//最后一个字符串
	if (str.GetLength()>0)
	{
		strArray.Add(str);//提取出的字符加入动态数组 
		nCount++;
	}
	return nCount;
}

CString GetMessageByHead(CString strFilePath, CString strHead, int num)
{
	CFile file;
	char *pBuf;
	CString strResult = "";
	CStringArray strSegMentArrary;
	CStringArray strDataFieldArrary;

	if (file.Open(strFilePath, CFile::modeRead, NULL))
	{
		int iLen = file.GetLength();
		pBuf = new char[iLen + 1];
		file.Read(pBuf, iLen);
		pBuf[iLen] = 0;
		file.Close();
	}
	else
	{
		//Log::WriteLog("打开文件失败!");
		return "";
	}
	
	if (SplitString(pBuf, "\r\n", strSegMentArrary)>0)
	{
		if (strHead != "")
		{
			for (int i = 0; i < strSegMentArrary.GetCount(); i++)
			{
				CString strTemp = strSegMentArrary.GetAt(i);
				if (strTemp.Find(strHead) != -1)
				{
					ExtString(strTemp, "|", strDataFieldArrary);
					strResult = strDataFieldArrary.GetAt(num);
				}
			}
		}
	}

	delete[] pBuf;
	return  strResult;
}


 

你可能感兴趣的:(c++)