new XMLParse,but don't have test.

This commit is contained in:
hyzboy 2020-08-20 21:26:49 +08:00
parent 4d40765bb4
commit 2002532b63
2 changed files with 146 additions and 69 deletions

View File

@ -2,6 +2,10 @@
#define HGL_XML_PARSE_INCLUDE
#include<hgl/type/BaseString.h>
#include<hgl/type/Map.h>
#include<hgl/type/StrChar.h>
#include<hgl/CodePage.h>
extern "C"
{
/**
@ -22,7 +26,107 @@ namespace hgl
}//namespace io
/**
* XML解析器()<br>
* XML节点解析器
*/
class XMLElementParse
{
public:
virtual bool StartElement(const char *element_name)=0;
virtual void Attr(const char *flag,const char *info){};
virtual void CharData(const char *str,int str_length){};
virtual void EndElement(const char *element_name){};
};//class XMLElementParse
class XMLElementParseKV:public XMLElementParse
{
protected:
using AttrsMap=Map<AnsiString,AnsiString>;
using AttrItem=Pair<AnsiString,AnsiString>;
AttrsMap attrs_map;
protected:
const AttrItem *GetAttrItem(const AnsiString &name);
template<typename T> const bool GetInteger (const AnsiString &name,T &value){const AttrItem *ai=GetAttrItem(name);return(ai?stoi(ai->right.c_str(),value):false);}
template<typename T> const bool GetUInteger (const AnsiString &name,T &value){const AttrItem *ai=GetAttrItem(name);return(ai?stou(ai->right.c_str(),value):false);}
template<typename T> const bool GetFloat (const AnsiString &name,T &value){const AttrItem *ai=GetAttrItem(name);return(ai?stof(ai->right.c_str(),value):false);}
public:
virtual void Attr(const char *flag,const char *info) override;
public:
const bool IsExist (const AnsiString &name)const{return attrs_map.KeyExist(name);}
const char * ToCString (const AnsiString &name){const AttrItem *ai=GetAttrItem(name);return(ai?ai->right.c_str():nullptr);}
const char * operator[] (const AnsiString &name){return ToCString(name);}
public:
const bool Get(const AnsiString &name,AnsiString &str)
{
const AttrItem *ai=GetAttrItem(name);
if(!ai)return(false);
str=ai->right;
return(true);
}
const bool Get(const AnsiString &name,UTF16String &str)
{
const AttrItem *ai=GetAttrItem(name);
if(!ai)return(false);
str=to_u16(ai->right);
return(true);
}
const bool Get(const AnsiString &name,char &ch)
{
const AttrItem *ai=GetAttrItem(name);
if(!ai)return(false);
ch=ai->right.GetBeginChar();
return(true);
}
const bool Get(const AnsiString &name,bool &value)
{
const AttrItem *ai=GetAttrItem(name);
return(ai?stob<char>(ai->right.c_str(),value):false);
}
const bool Get(const AnsiString &name, int8 &value){return GetInteger < int8 >(name,value);}
const bool Get(const AnsiString &name,uint8 &value){return GetUInteger<uint8 >(name,value);}
const bool Get(const AnsiString &name, int16 &value){return GetInteger < int16>(name,value);}
const bool Get(const AnsiString &name,uint16 &value){return GetUInteger<uint16>(name,value);}
const bool Get(const AnsiString &name, int32 &value){return GetInteger < int32>(name,value);}
const bool Get(const AnsiString &name,uint32 &value){return GetUInteger<uint32>(name,value);}
const bool Get(const AnsiString &name, int64 &value){return GetInteger < int64>(name,value);}
const bool Get(const AnsiString &name,uint64 &value){return GetUInteger<uint64>(name,value);}
const bool GetHexStr(const AnsiString &name,uint8 *data)
{
const AttrItem *ai=GetAttrItem(name);
if(!ai)return(false);
ParseHexStr(data,ai->right.c_str(),ai->right.Length());
return(true);
}
};//class XMLElementParseKV:public XMLElementParse
/**
* XML解析器<br>
*/
class XMLParse
{
@ -30,20 +134,18 @@ namespace hgl
XML_Parser xml;
uint buffer_size;
int buffer_size;
char *buffer;
protected:
XMLElementParse *element_parse;
virtual void StartParse();
public:
virtual void StartElement(const char *element_name,const char **atts)=0;
virtual void CharData(const char *str,int str_length){};
virtual void EndElement(const char *element_name){};
public:
XMLParse(const uint size=HGL_SIZE_1KB*128);
XMLParse(XMLElementParse *,const int size=HGL_SIZE_1KB*128);
virtual ~XMLParse();
virtual void Start(const char *charset="utf-8");
@ -53,27 +155,6 @@ namespace hgl
bool XMLParseFile(XMLParse *xml,const OSString &filename);
/**
* XML解析器()
*/
class XMLParseCB:public XMLParse
{
protected:
virtual void StartParse();
public:
DefEvent(void,OnStartElement,(const char *,const char **));
DefEvent(void,OnCharData,(const char *,int));
DefEvent(void,OnEndElement,(const char *));
public:
XMLParseCB();
virtual ~XMLParseCB()=default;
};//class XMLParseCB
#define XML_START_PARSE(name) while(*name) \
{ \
const char *flag=*name;++name; \

View File

@ -9,24 +9,51 @@ namespace hgl
{
namespace
{
void XMLStartElement(XMLParse *xml,const XML_Char *name,const XML_Char **atts)
void XMLStartElement(XMLElementParse *ep,const XML_Char *name,const XML_Char **atts)
{
xml->StartElement(name,atts);
if(!ep->StartElement(name))
return;
const char *flag;
const char *info;
while(*atts)
{
flag=*atts;++atts;
info=*atts;++atts;
ep->Attr(flag,info);
}
}
void XMLCharData(XMLParse *xml,const XML_Char *str,int len)
void XMLCharData(XMLElementParse *ep,const XML_Char *str,int len)
{
xml->CharData(str,len);
ep->CharData(str,len);
}
void XMLEndElement(XMLParse *xml,const XML_Char *name)
void XMLEndElement(XMLElementParse *ep,const XML_Char *name)
{
xml->EndElement(name);
ep->EndElement(name);
}
}//namespace
const XMLElementParseKV::AttrItem *XMLElementParseKV::GetAttrItem(const AnsiString &name)
{
const int pos=attrs_map.FindPos(name);
if(pos<0)return(false);
return attrs_map.GetItem(pos);
}
XMLParse::XMLParse(const uint size)
void XMLElementParseKV::Attr(const char *flag,const char *info)
{
attrs_map.Add(flag,info);
}
XMLParse::XMLParse(XMLElementParse *ep,const int size)
{
element_parse=ep;
xml=nullptr;
if(size<=0)
@ -65,7 +92,7 @@ namespace hgl
{
xml=XML_ParserCreate(charset);
XML_SetUserData(xml,this);
XML_SetUserData(xml,element_parse);
StartParse();
}
@ -157,35 +184,4 @@ namespace hgl
return xml->Parse(&fis);
}
namespace
{
void StartElementCB(XMLParseCB *xml,const XML_Char *name,const XML_Char **atts)
{
SafeCallEvent(xml->OnStartElement,(name,atts));
}
void CharDataCB(XMLParseCB *xml,const XML_Char *str,int len)
{
SafeCallEvent(xml->OnCharData,(str,len));
}
void EndElementCB(XMLParseCB *xml,const XML_Char *name)
{
SafeCallEvent(xml->OnEndElement,(name));
}
}
XMLParseCB::XMLParseCB()
{
OnStartElement=nullptr;
OnCharData=nullptr;
OnEndElement=nullptr;
}
void XMLParseCB::StartParse()
{
XML_SetElementHandler(xml,(XML_StartElementHandler)StartElementCB,(XML_EndElementHandler)EndElementCB);
XML_SetCharacterDataHandler(xml,(XML_CharacterDataHandler)CharDataCB);
}
}//namespace hgl