#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "DoubleLink.h"
#include "XML.h"
static int _XmlNewTreeNode (struct DoubleLinkStruct *node, void *data)
{
struct XML_Tree_Struct *Data;
Data = (struct XML_Tree_Struct *)data;
Data->link_flag++;
node->struct_content = (void *)Data;
return 0;
}
static int _XmlDelTreeNode (struct DoubleLinkStruct *node )
{
struct XML_Tree_Struct *Node;
Node = (struct XML_Tree_Struct *)(node->struct_content);
if(Node->link_flag == 0)
{
if(Node->data->name != NULL)
delete[] Node->data->name;
if(Node->data->value != NULL)
delete[] Node->data->value;
delete Node->data;
delete Node->subtree;
delete Node->attribtree;
delete Node;
}
else
Node->link_flag --;
return 0;
}
static int _XmlSearchTreeNode(struct DoubleLinkStruct *node, void *data)
{
struct XML_Tree_Struct *Node, *Data;
Node = (struct XML_Tree_Struct *)(node->struct_content);
Data = (struct XML_Tree_Struct *)data;
if( (Node->data->name == NULL) || (Data->data->name == NULL) )
return ERROR_DOUBLELINK_INVALID_NODE;
#ifndef XML_CHAR_CASEFLAG
if(strcmp(Node->data->name, Data->data->name) == 0)
#else
if(strcmpi(Node->data->name, Data->data->name) == 0)
#endif /* XML_CHAR_CASEFLAG */
return 0;
return ERROR_DOUBLELINK_INVALID_NODE;
}
static int _XmlNewAttribNode(struct DoubleLinkStruct *node, void *data)
{
struct XML_Data_Struct *Node, *Data;
Node = new struct XML_Data_Struct;
if(Node == NULL) return ERROR_DOUBLELINK_MEMORY;
memset(Node, 0, sizeof(struct XML_Data_Struct));
Data = (struct XML_Data_Struct *)data;
if(Data->name != NULL)
{
Node->name = new char[strlen(Data->name) + 1];
if(Node->name == NULL)
{
delete Node;
return ERROR_DOUBLELINK_MEMORY;
}
strcpy(Node->name, Data->name);
}
if(Data->value != NULL)
{
Node->value = new char[strlen(Data->value) + 1];
if(Node->value == NULL)
{
if(Node->name != NULL) delete[] Node->name;
delete Node;
return ERROR_DOUBLELINK_MEMORY;
}
strcpy(Node->value, Data->value);
}
node->struct_content = (void *)Node;
return 0;
}
static int _XmlDelAttribNode(struct DoubleLinkStruct *node)
{
struct XML_Data_Struct *Node;
Node = (struct XML_Data_Struct *)(node->struct_content);
if(Node->name != NULL) delete[] Node->name;
if(Node->value != NULL) delete[] Node->value;
delete Node;
return 0;
}
static int _XmlSearchAttribNode(struct DoubleLinkStruct *node, void *data)
{
struct XML_Data_Struct *Node, *Data;
Node = (struct XML_Data_Struct *)(node->struct_content);
Data = (struct XML_Data_Struct *)data;
if( (Node->name == NULL) || (Data->name == NULL) )
return ERROR_DOUBLELINK_INVALID_NODE;
#ifndef XML_CHAR_CASEFLAG
if(strcmp(Node->name, Data->name) == 0)
#else
if(strcmpi(Node->name, Data->name) == 0)
#endif /* XML_CHAR_CASEFLAG */
return 0;
return ERROR_DOUBLELINK_INVALID_NODE;
}
XML::XML()
{
this->_tree = NULL;
}
XML::~XML()
{
XML::Close();
}
int XML::Init(char *name, char *value)
{
int Rcode;
XML::Close();
Rcode = XML::_SetXmlTreeStruct();
if(Rcode)
{
this->Close();
return Rcode;
}
Rcode = XML::_SetXmlStructName(_tree, name);
if(Rcode)
{
this->Close();
return Rcode;
}
Rcode = XML::_SetXmlStructValue(_tree, value);
if(Rcode)
{
this->Close();
return Rcode;
}
return Rcode;
}
int XML::Init(char *name , char value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%c", value);
return XML::Init(name, buffer);
}
int XML::Init(char *name , int value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%d", value);
return XML::Init(name, buffer);
}
int XML::Init(char *name , long value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%ld", value);
return XML::Init(name, buffer);
}
int XML::Init(char *name , double value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%g", value);
return XML::Init(name, buffer);
}
void XML::Close(void)
{
if(this->_tree == NULL) return;
XML::_CloseTree();
this->_tree = NULL;
//虽然已经释放所有分配的空间,但此时_tree是个不定值,所以要将它复位,以便继续使用。
}
XML &XML::operator=(XML &object)
{
object._tree->link_flag++;
this->_tree = object._tree;
return *this;
}
int XML::Parent(XML &object)
{
object.Close();
if(this->_tree == NULL || this->_tree->parent == NULL)
return ERROR_XML_INVALID_NODE;
object._tree = this->_tree->parent;
object._tree->link_flag ++;
return 0;
}
int XML::_Copy(struct XML_Tree_Struct *object, struct XML_Tree_Struct *data)
{
int Rcode, n, count;
struct XML_Tree_Struct *temp;
XML Data;
count = data->subtree->Count();
for(n = 0; n < count; n++)
{
temp = (struct XML_Tree_Struct *)data->subtree->LocationNode(n);
if(temp == NULL) break;
Rcode = Data.Init(temp->data->name, temp->data->value);
if(Rcode) return Rcode;
Rcode = temp->attribtree->Copy(*Data._tree->attribtree);
if(Rcode) return Rcode;
if(temp->subtree->Count() != 0)
{
Rcode = XML::_Copy(Data._tree, temp);
if(Rcode) return Rcode;
}
//append for Parent()
Data._tree->parent = object;
Rcode = object->subtree->InsertNode(DOUBLELINK_END, Data._tree);
if(Rcode) return Rcode;
}
return 0;
}
/*
在进行COPY操作时,只进行本结点数据,属性结点,子结点的操作
不进行本结点的引用值,父结点的操作。
子结点操作时则只不对引用值操作。
*/
int XML::Copy(XML &object)
{
int Rcode;
Rcode = object.Init(this->_tree->data->name, this->_tree->data->value);
if(Rcode)
{
object.Close();
return Rcode;
}
Rcode = this->_tree->attribtree->Copy(*object._tree->attribtree);
if(Rcode)
{
object.Close();
return Rcode;
}
Rcode = XML::_Copy(object._tree, this->_tree);
if(Rcode)
{
object.Close();
return Rcode;
}
return Rcode;
}
int XML::Add(char *name, char *value)
{
int Rcode;
XML temp;
if(this->_tree->data->value != NULL)
{
Rcode = temp.Init((char *)NULL, this->_tree->data->value);
if(Rcode) return Rcode;
Rcode = XML::SetValue((char *)NULL);
if(Rcode) return Rcode;
Rcode = XML::Add(temp);
if(Rcode) return Rcode;
}
Rcode = temp.Init(name, value);
if(Rcode) return Rcode;
//append for Parent()
temp._tree->parent = this->_tree;
return this->_tree->subtree->InsertNode(DOUBLELINK_END, temp._tree);
}
int XML::Add(char *name, char value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%c", value);
return XML::Add(name, buffer);
}
int XML::Add(char *name, int value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%d", value);
return XML::Add(name, buffer);
}
int XML::Add(char *name, long value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%ld", value);
return XML::Add(name, buffer);
}
int XML::Add(char *name, double value)
{
char buffer[XML_BUFFER_MAX_LEN];
sprintf(buffer, "%g", value);
return XML::Add(name, buffer);
}
int XML::Add(XML &object)
{
int Rcode;
XML temp;
if(this->_tree->data->value != NULL)
{
Rcode = temp.Init((char *)NULL, this->_tree->data->value);
if(Rcode) return Rcode;
Rcode = XML::SetValue((char *)NULL);
if(Rcode) return Rcode;
Rcode = XML::Add(temp);
if(Rcode) return Rcode;
}
//append for Parent()
object._tree->parent = this->_tree;
return this->_tree->subtree->InsertNode(DOUBLELINK_END, object._tree);
}
int XML::Del(char *name)
{
int n;
struct XML_Tree_Struct data_tree;
struct XML_Data_Struct data_attrib;
memset(&data_tree, 0, sizeof(data_tree));
memset(&data_attrib, 0, sizeof(data_attrib));
data_attrib.name = name;
data_tree.data = &data_attrib;
if(this->_tree->subtree->SearchNode(n, &data_tree) == NULL)
return ERROR_XML_INVALID_KEYWORD;
return this->_tree->subtree->DeleteNode(n);
}
int XML::Del(int n)
{
if(this->_tree->subtree->LocationNode(n) == NULL)
return ERROR_XML_INVALID_KEYWORD;
return this->_tree->subtree->DeleteNode(n);
}
int XML::Element(char *name, XML &object)
{
int n;
struct XML_Tree_Struct data_tree;
struct XML_Data_Struct data_attrib;
memset(&data_tree, 0, sizeof(data_tree));
memset(&data_attrib, 0, sizeof(data_attrib))