有时,只需要用XML作一些小的应用,比如只是简单地保存日志或者一些配置,这时我们只需要直接读写XML就好,效率第一。
Delphi盒子有一个直接读写XML文件 (例子和代码),其核心函数为下面两个函数(一读一写):

{-------------------------------------------------------------------------------

Fun/Pro: GetXMLNodeValue

@Date: 2004.12.11

@Param: xmlFile xml文件

@Param: xmlnodepath 节点

@Param: xmlattrname 节点中的属性名称,如果直接取节点值则可以忽略此参数。

@Param: dep 节点的参数的分隔符,默认为.

@Return: 第一个节点的值

-------------------------------------------------------------------------------}

function GetXMLNodeValue(strEntityEngineFile:String; xmlNodePath:String;

const xmlattrname:String=''; const dep:Char ='.'):String;

var

xmlDocument :IXMLDocument;

node :IXMLNode;

xmlnodeList :TStrings;

i :Integer;

urlcount :Integer;

begin

//xml节点路径

xmlnodeList:=TStringList.Create;

xmlnodeList.Delimiter:=dep;

xmlnodeList.DelimitedText:=xmlnodepath;

urlcount:=xmlnodeList.Count;

//xml对象

xmlDocument :=TXMLDocument.Create(nil);

xmlDocument.LoadFromFile(strEntityEngineFile);

xmlDocument.Active:=true;

try

node:= xmlDocument.DocumentElement;

if(node.NodeName = xmlnodeList[]) then begin

//扫描节点

for i :=  to urlcount- do begin

if(node<>nil) then

node := getnodefromIXMLNodeList(node.ChildNodes,xmlnodeList[i])

else Break;

end;

if(node=nil)then begin

result:='';

end else begin

//判断是取属性还是取节点内容

if(Trim(xmlattrname)='') then

result:=node.Text

else

result:=node.AttributeNodes.Nodes[xmlattrname].NodeValue;

end;

end else begin

result:='';

end;

except

result:='error';

end;

xmlDocument.Active:=false;

end;

{-------------------------------------------------------------------------------

Fun/Pro: SetXMLNodeValue

@Date: 2004.12.11

@Param: xmlFile xml文件

@Param: xmlnodepath 节点

@Param: xmlattrname 节点中的属性名称,如果直接取节点值则可以忽略此参数。

@Param: dep 节点的参数的分隔符,默认为.

@Return: 操作成功否

-------------------------------------------------------------------------------}

function setXmlNodeValue(strEntityEngineFile:String; xmlNodePath:String;

const xmlattrname:String=''; const value:String=''; const dep:Char ='.'):boolean;

var

xmlDocument :IXMLDocument;

node :IXMLNode;

xmlnodeList :TStrings;

i :Integer;

urlcount :Integer;

begin

//xml节点路径

xmlnodeList:=TStringList.Create;

xmlnodeList.Delimiter:=dep;

xmlnodeList.DelimitedText:=xmlnodepath;

urlcount:=xmlnodeList.Count;

//xml对象

xmlDocument :=TXMLDocument.Create(nil);

xmlDocument.LoadFromFile(strEntityEngineFile);

xmlDocument.Active:=true;

try

node:= xmlDocument.DocumentElement;

if(node.NodeName = xmlnodeList[]) then begin

//扫描节点

for i :=  to urlcount- do begin

if(node<>nil) then

node := getnodefromIXMLNodeList(node.ChildNodes,xmlnodeList[i])

else Break;

end;

if(node <> nil)then begin

if(Trim(xmlattrname)='') then

node.Text:=value

else

node.AttributeNodes.Nodes[xmlattrname].NodeValue:=value;

xmlDocument.SaveToFile(strEntityEngineFile);

end;

end;

result:=true;

except

result:=false;

end;

xmlDocument.Active:=false;

end;

但是上述两个函数有一个问题:它只能按节点名和属性名查找第一条记录。举例:如果要操作类似下述XML文件,节点和属性名相同的有多个,只是属性的值不一样,上面的读写函数就罢工了。

<colour name="normal attribute" red="" green="" blue=""/>

<colour name="good attribute" red="" green="" blue=""/>

<colour name="excellent attribute" red="" green="" blue=""/>

OK,程序员的最大乐趣就是自己动手了。我们来改造一下这两个函数。
在原有函数的基础上增加了两个参数: function TOperateXml.getnodefromIXMLNodeList(childnodes: IXMLNodeList; nodename: string):
IXMLNode;
var
i: Integer;
begin
for i := to childnodes.Count do
begin
if (childnodes.Get(i - ).NodeName = nodename) then
begin
result := childnodes[i - ];
exit;
end;
end;
end; {------------------------------------------------------------------------------- Fun/Pro: GetXMLNodeSpecialValue @Date: 2004.12.11 @Param: xmlFile xml文件 @Param: xmlnodepath 节点 @Param: xmlattrname 节点中的属性名称,如果直接取节点值则可以忽略此参数。 @Param: XMLSpecialName 要查找的节点中属性名 @Param: XMLSpecialValue 要查找的节点中某属性对应的值 @Param: dep 节点的参数的分隔符,默认为. @Return: 某属性的值 -------------------------------------------------------------------------------} function GetXMLNodeSpecialValue(strEntityEngineFile:String; XMLNodePath:String; const XMLAttrName:String=''; const XMLSpecialName:String=''; const XMLSpecialValue:String=''; const dep:Char ='.'):String; var xmlDocument :IXMLDocument; node :IXMLNode; xmlnodeList :TStrings; i :Integer; urlcount :Integer; begin //xml节点路径 xmlnodeList:=TStringList.Create; xmlnodeList.Delimiter:=dep; xmlnodeList.DelimitedText:=xmlnodepath; urlcount:=xmlnodeList.Count; //xml对象 xmlDocument :=TXMLDocument.Create(nil); xmlDocument.LoadFromFile(strEntityEngineFile); xmlDocument.Active:=true; try node:= xmlDocument.DocumentElement; if(node.NodeName = xmlnodeList[]) then begin //扫描节点 for i := to urlcount- do begin if(node<>nil) then begin node := getnodefromIXMLNodeList(node.ChildNodes,xmlnodeList[i]); end else Break; end; if(node=nil)then begin result:=''; end else begin //判断是取属性还是取节点内容 if(Trim(xmlattrname)='') then result:=node.Text else begin result := node.AttributeNodes.Nodes[XMLSpecialName].NodeValue; //这里不想再声明一个临时变量了,就用result来比较,可能有隐患。 while ((result <> XMLSpecialValue)) do begin node := node.NextSibling; while (node.NodeName = '#comment') do begin node:= node.NextSibling; end; result := node.AttributeNodes.Nodes[XMLSpecialName].NodeValue; end; result:=node.AttributeNodes.Nodes[XMLAttrName].NodeValue; end; end; end else begin result:=''; end; except result:='error'; end; xmlDocument.Active:=false; end; 写函数 {------------------------------------------------------------------------------- Fun/Pro: SetXMLNodeSpecialValue @Date: 2004.12.11 @Param: xmlFile xml文件 @Param: xmlnodepath 节点 @Param: xmlattrname 节点中的属性名称,如果直接取节点值则可以忽略此参数。 @Param: XMLSpecialName 要查找的节点中属性名 @Param: XMLSpecialValue 要查找的节点中某属性对应的值 @Param: dep 节点的参数的分隔符,默认为. @Return: 操作成功与否 -------------------------------------------------------------------------------} function SetXMLNodeSpecialValue(strEntityEngineFile:String; xmlNodePath:String; const xmlattrname:String=''; const value:String=''; const XMLSpecialName:String=''; const XMLSpecialValue:String=''; const dep:Char ='.'):boolean; var xmlDocument :IXMLDocument; node :IXMLNode; xmlnodeList :TStrings; i :Integer; urlcount :Integer; CMPValue :String; begin //xml节点路径 xmlnodeList:=TStringList.Create; xmlnodeList.Delimiter:=dep; xmlnodeList.DelimitedText:=xmlnodepath; urlcount:=xmlnodeList.Count; //xml对象 xmlDocument :=TXMLDocument.Create(nil); xmlDocument.LoadFromFile(strEntityEngineFile); xmlDocument.Active:=true; try node:= xmlDocument.DocumentElement; if(node.NodeName = xmlnodeList[]) then begin //扫描节点 for i := to urlcount- do begin if(node<>nil) then node := getnodefromIXMLNodeList(node.ChildNodes,xmlnodeList[i]) else Break; end; if(node <> nil)then begin {if(Trim(xmlattrname)='') then node.Text:=value else node.AttributeNodes.Nodes[xmlattrname].NodeValue:=value; } if (Trim(XMLAttrName)='') then node.Text := value else begin CMPValue := node.AttributeNodes.Nodes[XMLSpecialName].NodeValue; while (CMPValue <> XMLSpecialValue) do begin node := node.NextSibling; while (node.NodeName = '#comment') do begin node:= node.NextSibling; end; CMPValue := node.AttributeNodes.Nodes[XMLSpecialName].NodeValue; end; node.AttributeNodes.Nodes[XMLAttrName].NodeValue:=value; end; xmlDocument.SaveToFile(strEntityEngineFile); end; end; result:=true; except result:=false; end; xmlDocument.Active:=false; end;

Delphi直接读取XmL的更多相关文章

  1. Delphi中解析Xml的控件-SimDesign NativeXml

    Delphi中解析Xml的控件-SimDesign NativeXml 正在学习,感觉应用很方便.无源代码的版本还是免费的. SimDesign.NativeXml是一个delphi和bcb的XML控 ...

  2. 读取xml数据装配到字典中之应用场景

    前段时间看到支付宝设置里面有个多语言这个功能,蛮有意思的,就想双休没事的话做个相关的demo玩玩,可是礼拜六被妹子拽出去玩了一天,来大上海有大半年了,基本没有出去玩过,妹子说我是超级宅男,也不带她出去 ...

  3. 自己动手之使用反射和泛型,动态读取XML创建类实例并赋值

    前言: 最近小匹夫参与的游戏项目到了需要读取数据的阶段了,那么觉得自己业余时间也该实践下数据相关的内容.那么从哪入手呢?因为用的是Unity3d的游戏引擎,思来想去就选择了C#读取XML文件这个小功能 ...

  4. MFC如何读取XML

    <?xml version="1.0" encoding="utf-8"?> <Cases> <case> <No&g ...

  5. 使用dom4j读取xml连接数据库与之单例模式

    使用dom4j读取xml ,加入jar包 dom4j-1.6.1.jar jaxen-1.1-beta-6.jar public class XmlConfigReader { //懒汉式,延迟加载 ...

  6. java DOM4J 读取XML

    最近学习Java,在处理XML文档的时候,查阅相关资料,发现了DOM4J这个jre库,相对C#的XML处理来说,功能还算是跟得上 下面展示一篇我自己写的一个XML读取测试 import java.ut ...

  7. C#中常用的读取xml的几种方法(转)

    本文完全来源于http://blog.csdn.net/tiemufeng1122/article/details/6723764,仅作个人学习之用. XML文件是一种常用的文件格式,例如WinFor ...

  8. wcf序列化大对象时报错:读取 XML 数据时,超出最大

    错误为: 访问服务异常:格式化程序尝试对消息反序列化时引发异常: 尝试对参数 http://tempuri.org/ 进行反序列化时出 错: request.InnerException 消息是“反序 ...

  9. C#中常用的几种读取XML文件的方法

    1.C#中常用的几种读取XML文件的方法:http://blog.csdn.net/tiemufeng1122/article/details/6723764/

随机推荐

  1. python的map、reduce和filter(过滤器)函数(廖雪峰老师python基础)

    1.map 语法: map(func,Iterable) map()函数接收两个参数,一个是函数,一个是Iterable,map将传入的函数依次作用到序列的每个元素,并把结果作为新的Iterator返 ...

  2. 51单片机的idata,xdata,pdata,data的详解

    data: 固定指前面0x00-0x7f的128个RAM,可以用acc直接读写的,速度最快,生成的代码也最小. bit :是指0x20-0x2f的可位寻址区idata:固定指前面0x00-0xff的2 ...

  3. jenkins-参数化构建插件:Choice Parameter

    参考: 谢谢大佬的总结: https://www.cnblogs.com/zhaojingyu/p/9862371.html 使用方式 step1: 添加参数,选择Choice Parameter,并 ...

  4. Flink容错机制(checkpoint)

    checkpoint是Flink容错的核心机制.它可以定期地将各个Operator处理的数据进行快照存储( Snapshot ).如果Flink程序出现宕机,可以重新从这些快照中恢复数据. 1. ch ...

  5. QTP 保留对象

    1. 常用保留对象(Utility Objects) 保留对象:所谓QTP保留对象就是QTP本身预留的一些可用对象. 通俗些讲就是,当打开QTP时它就已经把这些对象给实例化了,直到关闭QTP后,这些保 ...

  6. 用vim写go代码——vim-go插件

    GoImport:导入包 GoImport!:导入远程包 GoImportAs: 导入包并且重命名

  7. Mybatis的分支选择和In循环

    Mybatis的分支选择: <choose> <when test="patientNo != null and patientNo != ''"> and ...

  8. JPA、Hibernate、Spring Data JPA 的关系,你懂吗?

    来源:https://my.oschina.net/u/3080373/blog/1828589 什么是JPA? 全称Java Persistence API,可以通过注解或者XML描述[对象-关系表 ...

  9. BCrypt密码加密

    快速入门 (1)我们从官网下载源码 BCrypt 官网 http://www.mindrot.org/projects/jBCrypt/ (2)新建工程,将源码类BCrypt拷贝到工程 (3)新建测试 ...

  10. MySQL的共享锁与排它锁编码演示

    一.行锁之MySQL  使用SELECT ... FOR UPDATE 做事务写入前的确认 以MySQL 的InnoDB 为例,预设的Tansaction isolation level 为REPEA ...