最近做了关于医疗的项目,用了HL7协议,以下是解析的代码:

HL7解析器:

 using System;
using System.Text;
using System.Xml;
using System.IO; namespace CA2
{
/// <summary>
/// HL7解析器
/// </summary>
public static class HL7ToXmlConverter
{
private static XmlDocument _xmlDoc; /// <summary>
/// 把HL7信息转成XML形式
/// 分隔顺序 \n,|,~,^,&
/// </summary>
/// <param name="sHL7">HL7字符串</param>
/// <returns></returns>
public static string ConvertToXml(string sHL7)
{
_xmlDoc = ConvertToXmlObject(sHL7);
return _xmlDoc.OuterXml;
} public static XmlDocument ConvertToXmlObject(string sHL7)
{
_xmlDoc = CreateXmlDoc();
sHL7 = sHL7.Replace("\\v","").Replace("\\u001c","");
sHL7 = sHL7.Replace("\\r","\n");
//把HL7分成段
string[] sHL7Lines = sHL7.Split('\n'); ////去掉XML的关键字
//for (int i = 0; i < sHL7Lines.Length; i++)
//{
// sHL7Lines[i] = Regex.Replace(sHL7Lines[i], @"[^ -~]", "");
//} for (int i = ; i < sHL7Lines.Length; i++)
{
// 判断是否空行
if (sHL7Lines[i] != string.Empty)
{
string sHL7Line = sHL7Lines[i];
//通过/r 或/n 回车符分隔
string[] sFields = HL7ToXmlConverter.GetMessgeFields(sHL7Line);
if (string.IsNullOrWhiteSpace(sFields[]) == false)
{
// 为段(一行)创建第一级节点
if (string.IsNullOrWhiteSpace(sFields[]) == false)
{
XmlElement el = _xmlDoc.CreateElement(sFields[]);
_xmlDoc.DocumentElement.AppendChild(el);
// 循环每一行
for (int a = ; a < sFields.Length; a++)
{
// 为字段创建第二级节点
XmlElement fieldEl = _xmlDoc.CreateElement(sFields[] + "." + a.ToString());
//是否包括HL7的连接符
if (sFields[a] != @"^~\&")
{//0:如果这一行有任何分隔符
//通过~分隔
string[] sComponents = HL7ToXmlConverter.GetRepetitions(sFields[a]);
if (sComponents.Length > )
{//1:如果可以分隔
for (int b = ; b < sComponents.Length; b++)
{
XmlElement componentEl = _xmlDoc.CreateElement(sFields[] + "." + a.ToString() + "." + b.ToString());
//通过&分隔
string[] subComponents = GetSubComponents(sComponents[b]);
if (subComponents.Length > )
{//2.如果有字组,一般是没有的。。。
for (int c = ; c < subComponents.Length; c++)
{
//修改了一个错误
string[] subComponentRepetitions = GetComponents(subComponents[c]);
if (subComponentRepetitions.Length > )
{
for (int d = ; d < subComponentRepetitions.Length; d++)
{
XmlElement subComponentRepEl = _xmlDoc.CreateElement(sFields[] + "." + a.ToString() + "." + b.ToString() + "." + c.ToString() + "." + d.ToString());
subComponentRepEl.InnerText = subComponentRepetitions[d];
componentEl.AppendChild(subComponentRepEl);
}
}
else
{
XmlElement subComponentEl = _xmlDoc.CreateElement(sFields[] + "." + a.ToString() + "." + b.ToString() + "." + c.ToString());
subComponentEl.InnerText = subComponents[c];
componentEl.AppendChild(subComponentEl); }
}
fieldEl.AppendChild(componentEl);
}
else
{//2.如果没有字组了,一般是没有的。。。
string[] sRepetitions = HL7ToXmlConverter.GetComponents(sComponents[b]);
if (sRepetitions.Length > )
{
XmlElement repetitionEl = null;
for (int c = ; c < sRepetitions.Length; c++)
{
repetitionEl = _xmlDoc.CreateElement(sFields[] + "." + a.ToString() + "." + b.ToString() + "." + c.ToString());
repetitionEl.InnerText = sRepetitions[c];
componentEl.AppendChild(repetitionEl);
}
fieldEl.AppendChild(componentEl);
el.AppendChild(fieldEl);
}
else
{
componentEl.InnerText = sComponents[b];
fieldEl.AppendChild(componentEl);
el.AppendChild(fieldEl);
}
}
}
el.AppendChild(fieldEl);
}
else
{//1:如果不可以分隔,可以直接写节点值了。
fieldEl.InnerText = sFields[a];
el.AppendChild(fieldEl);
}
}
else
{//0:如果不可以分隔,可以直接写节点值了。
fieldEl.InnerText = sFields[a];
el.AppendChild(fieldEl);
}
}
}
}
}
}
return _xmlDoc;
} /// <summary>
/// 通过|分隔 字段
/// </summary>
/// <param name="s"></param>
/// <returns></returns>
private static string[] GetMessgeFields(string s)
{
return s.Split('|');
} /// <summary>
/// 通过^分隔 组字段
/// </summary>
/// <param name="s"></param>
/// <returns></returns>
private static string[] GetComponents(string s)
{
return s.Split('^');
} /// <summary>
/// 通过&分隔 子分组组字段
/// </summary>
/// <param name="s"></param>
/// <returns></returns>
private static string[] GetSubComponents(string s)
{
return s.Split('&');
} /// <summary>
/// 通过~分隔 重复
/// </summary>
/// <param name="s"></param>
/// <returns></returns>
private static string[] GetRepetitions(string s)
{
return s.Split('~');
} /// <summary>
/// 创建XML对象
/// </summary>
/// <returns></returns>
private static XmlDocument CreateXmlDoc()
{
XmlDocument output = new XmlDocument();
XmlElement rootNode = output.CreateElement("HL7Message");
output.AppendChild(rootNode);
return output;
} public static string GetText(XmlDocument xmlObject, string path)
{
XmlNode node = xmlObject.DocumentElement.SelectSingleNode(path);
if (node != null)
{
return node.InnerText;
}
else
{
return null;
}
} public static string GetText(XmlDocument xmlObject, string path, int index)
{
XmlNodeList nodes = xmlObject.DocumentElement.SelectNodes(path);
if (index <= nodes.Count)
{
return nodes[index].InnerText;
}
else
{
return null;
}
} public static String[] GetTexts(XmlDocument xmlObject, string path)
{
XmlNodeList nodes = xmlObject.DocumentElement.SelectNodes(path);
String[] arr = new String[nodes.Count];
int index = ;
foreach (XmlNode node in nodes)
{
arr[index++] = node.InnerText;
}
return arr; } public static string FormatXml(string sUnformattedXml)
{ XmlDocument xd = new XmlDocument();
xd.LoadXml(sUnformattedXml);
StringBuilder sb = new StringBuilder();
StringWriter sw = new StringWriter(sb);
XmlTextWriter xtw = null;
try
{
xtw = new XmlTextWriter(sw);
xtw.Formatting = Formatting.Indented;
xtw.Indentation = ;
xtw.IndentChar = '\t';
xd.WriteTo(xtw);
}
finally
{
if (xtw != null)
xtw.Close();
}
return sb.ToString();
}
}
}

程序入口:

using System;
using System.Collections.Generic;
using System.Xml; namespace CA2
{
class Program
{
static void Main(string[] args)
{
String myHL7string = @"\vMSH|^~\\&||Mindray|||20191113163421||ORU^R01|2|P|2.3.1||||||UNICODE\rPID|1||^^^^MR||^患者名称|||男\rPV1|1||儿科\rOBR|1||7|00001^Automated Count^99MRC|||20191113102722|||单位||||||||||||||HM||||||||人员\rOBX|1|IS|08001^Take Mode^99MRC||C||||||F\rOBX|2|IS|08002^Blood Mode^99MRC||P||||||F\rOBX|3|IS|08003^Test Mode^99MRC||CBC+DIFF+CRP||||||F\rOBX|4|IS|01002^Ref Group^99MRC||儿童||||||F\rOBX|5|NM|30525-0^Age^LN||3|yr|||||F\rOBX|6|NM|6690-2^WBC^LN||10.62|10*9/L|4.00-12.00|N|||F\rOBX|7|NM|704-7^BAS#^LN||0.01|10*9/L|0.00-0.10|N|||F\rOBX|8|NM|706-2^BAS%^LN||0.1|%|0.0-1.0|N|||F\rOBX|9|NM|751-8^NEU#^LN||8.06|10*9/L|2.00-8.00|H~N|||F\rOBX|10|NM|770-8^NEU%^LN||75.8|%|50.0-70.0|H~N|||F\rOBX|11|NM|711-2^EOS#^LN||0.02|10*9/L|0.02-0.80|N|||F\rOBX|12|NM|713-8^EOS%^LN||0.2|%|0.5-5.0|L~N|||F\rOBX|13|NM|731-0^LYM#^LN||2.11|10*9/L|0.80-7.00|N|||F\rOBX|14|NM|736-9^LYM%^LN||19.9|%|20.0-60.0|L~N|||F\rOBX|15|NM|742-7^MON#^LN||0.42|10*9/L|0.12-1.20|N|||F\rOBX|16|NM|5905-5^MON%^LN||4.0|%|3.0-12.0|N|||F\rOBX|17|NM|789-8^RBC^LN||4.29|10*12/L|3.50-5.20|N|||F\rOBX|18|NM|718-7^HGB^LN||117|g/L|120-160|L~N|||F\rOBX|19|NM|787-2^MCV^LN||80.1|fL|80.0-100.0|N|||F\rOBX|20|NM|785-6^MCH^LN||27.2|pg|27.0-34.0|N|||F\rOBX|21|NM|786-4^MCHC^LN||339|g/L|310-370|N|||F\rOBX|22|NM|788-0^RDW-CV^LN||12.7|%|11.0-16.0|N|||F\rOBX|23|NM|21000-5^RDW-SD^LN||37.1|fL|35.0-56.0|N|||F\rOBX|24|NM|4544-3^HCT^LN||34.4|%|35.0-49.0|L~N|||F\rOBX|25|NM|777-3^PLT^LN||224|10*9/L|100-300|N|||F\rOBX|26|NM|32623-1^MPV^LN||8.7|fL|6.5-12.0|N|||F\rOBX|27|NM|32207-3^PDW^LN||16.3||15.0-17.0|N|||F\rOBX|28|NM|10002^PCT^99MRC||0.194|%|0.108-0.282|N|||F\rOBX|29|NM|30392-5^NRBC#^LN||0.002|10*9/L|0.000-9999.999|N|||F\rOBX|30|NM|26461-4^NRBC%^LN||0.02|%|0.00-9999.99|N|||F\rOBX|31|NM|10014^PLCR^99MRC||19.6|%|11.0-45.0|N|||F\rOBX|32|NM|10013^PLCC^99MRC||44|10*9/L|30-90|N|||F\rOBX|33|NM|26477-0^*ALY#^LN||0.00|10*9/L|0.00-0.20|N|||F\rOBX|34|NM|13046-8^*ALY%^LN||0.0|%|0.0-2.0|N|||F\rOBX|35|NM|10000^*LIC#^99MRC||0.00|10*9/L|0.00-0.20|N|||F\rOBX|36|NM|10001^*LIC%^99MRC||0.0|%|0.0-2.5|N|||F\rOBX|37|NM|71426-1^FR-CRP^LN||12.56|mg/L|0.00-4.00|H~N|||F\rOBX|38|NM|15001^WBC Histogram. Left Line^99MRC||13||||||F\rOBX|39|NM|15003^WBC Histogram. Middle Line^99MRC||36||||||F\rOBX|40|NM|15002^WBC Histogram. Right Line^99MRC||71||||||F\rOBX|41|NM|15004^WBC Histogram. Meta Length^99MRC||1||||||F\rOBX|42|NM|15009^WBC Histogram. Total^99MRC||7675||||||F\rOBX|43|ED|15008^WBC Histogram. BMP^99MRC|||F|\rOBX|59|NM|15208^WBC DIFF Scattergram. FSC-LOG dimension^99MRC||0||||||F\r\u001c\r";
Test(myHL7string);
Console.ReadLine();
}
static void Test(string myHL7string)
{
string sHL7asXml = HL7ToXmlConverter.ConvertToXml(myHL7string);
XmlDocument xmlObject = HL7ToXmlConverter.ConvertToXmlObject(myHL7string);
XmlNodeList allOBX = xmlObject.SelectNodes("//OBX");
int i = ;
List<OutAnalyzerResultItemDTO> listOutAnalyzerResultItemDTO = new List<OutAnalyzerResultItemDTO>();
var strSpecimenTime = HL7ToXmlConverter.GetText(xmlObject, "OBR/OBR.7");
OutAnalyzerResultDTO outAnalyzerResultDTO = new OutAnalyzerResultDTO()
{
FlowNum = int.Parse(HL7ToXmlConverter.GetText(xmlObject, "OBR/OBR.3")),
SpecimenTime = DateTime.Parse(string.Format("{0}-{1}-{2} {3}:{4}:{5}",
strSpecimenTime.Substring(, ),
strSpecimenTime.Substring(, ),
strSpecimenTime.Substring(, ),
strSpecimenTime.Substring(, ),
strSpecimenTime.Substring(, ),
strSpecimenTime.Substring(, ))),
};
foreach (XmlElement element in allOBX)
{
if (i >= && i <= )
{
listOutAnalyzerResultItemDTO.Add(new OutAnalyzerResultItemDTO()
{
ItemCode = FormatItemCode(element.GetElementsByTagName("OBX.3")[].InnerText),//项目对照编码
HLFlag = FormatFlag(element.SelectSingleNode("OBX.8/OBX.8.0"), element.SelectSingleNode("OBX.8")),//高低标记
ReferenceRange = element.GetElementsByTagName("OBX.7")[].InnerText,//参考值
Result = element.GetElementsByTagName("OBX.5")[].InnerText,//检测结果
Uint = element.GetElementsByTagName("OBX.6")[].InnerText,//检测单位
});
}
i += ;
}
outAnalyzerResultDTO.resultItemDTOs = listOutAnalyzerResultItemDTO;
listOutAnalyzerResultItemDTO.ForEach(x =>
{
Console.Write("代码:" + x.ItemCode);
Console.Write(" 结果:" + x.Result);
Console.Write(" 参考值:" + x.ReferenceRange);
Console.Write(" 单位:" + x.Uint);
Console.WriteLine(" 高低值:" + x.HLFlag);
});
}
static string FormatItemCode(string allStr)
{
var a1 = allStr.IndexOf("^");
var a2 = allStr.LastIndexOf("^");
var aa = allStr.Substring(a1 + , a2 - a1 - );
return aa;
}
static string FormatFlag(XmlNode str1, XmlNode str2)
{
return str1 == null ? str2.InnerText : str1.InnerText;
}
}
}

HL7解析器的更多相关文章

  1. XML技术之DOM4J解析器

    由于DOM技术的解析,存在很多缺陷,比如内存溢出,解析速度慢等问题,所以就出现了DOM4J解析技术,DOM4J技术的出现大大改进了DOM解析技术的缺陷. 使用DOM4J技术解析XML文件的步骤? pu ...

  2. AFN解析器里的坑

    AFN框架是用来用来发送网络请求的,它的好处是可以自动给你解析JSON数据,还可以发送带参数的请求AFN框架还可以监测当前的网络状态,还支持HTTPS请求,分别对用的类为AFNetworkReacha ...

  3. SpringMVC视图解析器

    SpringMVC视图解析器 前言 在前一篇博客中讲了SpringMVC的Controller控制器,在这篇博客中将接着介绍一下SpringMVC视 图解析器.当我们对SpringMVC控制的资源发起 ...

  4. XML技术之SAX解析器

    1.解析XML文件有三种解析方法:DOM SAX DOM4J. 2.首先SAX解析技术只能读取XML文档中的数据信息,不能对其文档中的数据进行添加,删除,修改操作:这就是SAX解析技术的一个缺陷. 3 ...

  5. 学习SpringMVC——说说视图解析器

    各位前排的,后排的,都不要走,咱趁热打铁,就这一股劲我们今天来说说spring mvc的视图解析器(不要抢,都有位子~~~) 相信大家在昨天那篇如何获取请求参数篇中都已经领略到了spring mvc注 ...

  6. SpringMVC入门案例及请求流程图(关于处理器或视图解析器或处理器映射器等的初步配置)

    SpringMVC简介:SpringMVC也叫Spring Web mvc,属于表现层的框架.Spring MVC是Spring框架的一部分,是在Spring3.0后发布的 Spring结构图 Spr ...

  7. [LeetCode] Mini Parser 迷你解析器

    Given a nested list of integers represented as a string, implement a parser to deserialize it. Each ...

  8. Duilib源码分析(三)XML解析器—CMarkup

    上一节介绍了控件构造器CDialogBuilder,接下来将分析其XML解析器CMarkup: CMarkup:xml解析器,目前内置支持三种编码格式:UTF8.UNICODE.ASNI,默认为UTF ...

  9. CozyRSS开发记录9-快速实现一个RSS解析器

    CozyRSS开发记录9-快速实现一个RSS解析器 1.再读RSS标准 既然需要自己实现一个RSS解析器,那自然需要仔细的读一读RSS的标准文档.在网上随便找了两份,一份英文一份中文: http:// ...

随机推荐

  1. linux - mysql - 新建用户

    新建用户 使用如下命令创建一个用户名和密码分别为"myuser"和"mypassword"的用户,localhost在User表里是Host字段(主机). my ...

  2. 三、linux环境的搭建1(oracle、ssh、jdk、mysql、samba、tomcat)

    linux环境的搭建1(oracle.ssh.jdk.mysql.samba.tomcat)   网络配置 方案一 tip 1 使用ifconfig : ifconfig eth0 新ip 然后编辑/ ...

  3. spring security和java web token整合

    思路: spring security 1.用户输入用户名密码. 2.验证:从库中(可以是内存.数据库等)查询该用户的密码.角色,验证用户名和密码是否正确.如果正确,则将填充Authenticatio ...

  4. ASP.NET Identity系列教程-1目录

    https://www.cnblogs.com/hao-1234-1234/p/8857437.html ASP.NET Identity系列教程 13 Getting Started with Id ...

  5. 题解【洛谷P1948】[USACO08JAN]电话线Telephone Lines

    题面 题解 很显然,答案满足单调性. 因此,可以使用二分答案求解. 考虑\(check\)的实现. 贪心地想,免费的\(k\)对电话线一定都要用上. 每次\(check\)时将小于\(mid\)的边权 ...

  6. OpenShift 4.3环境中创建基于Go的Operator

    详细步骤可以参考官方文档 https://docs.openshift.com/container-platform/4.3/operators/operator_sdk/osdk-getting-s ...

  7. 基于Android的在线播放器系统的设计与实现

    文章结构: 1 引言 1.1系统的研究背景 现在的时代是互联网的时代,互联网高速发展的同时,无线网络也接入了互联网.社会的各个领域都已经被无线网络渗透.小的比如手机,电脑,电视.大的比如灯光系统,智能 ...

  8. linux 创建svn版本库,并在svn上配置checkstyle做代码风格检查

    一.创建SVN版本库 1.安装svn服务器 yum install subversion 2.查看版本 svnserve --version 3.建立SVN版本库目录(即你的SVN服务器里面的文件存放 ...

  9. python3练习100题——020

    原题链接:http://www.runoob.com/python/python-exercise-example20.html 题目:一球从100米高度自由落下,每次落地后反跳回原高度的一半:再落下 ...

  10. TOYS(计算几何-入门)

    题目 ‘^’代表叉乘 ‘•’代表点乘 点积:a•b=ax*bx+ay*by 叉积:a^b=ax*by-bx*ay