⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 xml.cpp

📁 提供windows和unix下各种级别日志,包括 xml
💻 CPP
📖 第 1 页 / 共 2 页
字号:
      strcpy(name,p->getTag());
   else
      name[0]=0;
   return 1;
}

TXMLElem *TXMLElem::GetSubElem(int index)
{
   int i=0;
   for(TXMLElem* p=child; p!=NULL; p=p->brother)
   {
      if(i == index)
         return p;
      i++;
   }
   return NULL;
}

TXMLElem *TXMLElem::GetSubElem(const char *tag1, const char *attrName, const char *attrValue)
{
   for(TXMLElem* p=child; p!=NULL; p=p->brother)
   {
      if(!tag1 || stricmp(tag1, p->getTag()) == 0)
      {
         char* value=p->GetAttrValue(attrName);
         if(value && strcmp(value,attrValue)==0)
            return p;
      }
   }
   return NULL;
}

TXMLElem *TXMLElem::GetSubElem(const char *tag1, int index)
{
   int i=0;
   for(TXMLElem* p=child; p!=NULL; p=p->brother)
   {
      if(stricmp(tag1, p->getTag()) == 0)
      {
         if(i == index)
            return p;
         i++;
      }
   }
   return NULL;
}

int TXMLElem::deleteChild(TXMLElem* pElement)
{
   TXMLElem* p=child;
   if(p==NULL)
      return -2;
  
   if(p==pElement)
   {
      child=pElement->brother;
      delete pElement;
      return 0;
   }

   int i=1;
   while(p!=NULL && p->brother!=pElement)
   {
      p=p->brother;
      i++;
   }
   if(p==NULL)
      return -3;

   p->brother=pElement->brother;
   delete pElement;
   return i;
}

void TXMLElem::addChild(TXMLElem* pElement, int mode)
{
   pElement->parent=this;
   if(child==NULL)
   {
      child=pElement;
      return;
   }

   if(mode==1)
   {
      TXMLElem* p=child;
      while(p->brother!=NULL)
         p=p->brother;
      p->brother=pElement;
   }
   else
   {
      pElement->brother=child;
      child=pElement;
   }
}

void TXMLElem::setAttr(const char *name,const char *value)
{
   if(name==NULL || value==NULL) return ;

   if(attr==NULL)
   {
      attr=new TXMLAttr;
      attr->setName(name);
      attr->setValue(value);
      return;
   }

   if(strcmp(attr->getName(),name)==0)
   {
      attr->setValue(value);
      return;
   }

   TXMLAttr* p=attr;
   while(1)
   { 
      if(strcmp(p->getName(),name)==0)
      {
         p->setValue(value);
         return;
      }
      if(p->brother==NULL)
      {
         p->brother=new TXMLAttr;
         p->brother->setName(name);
         p->brother->setValue(value);
         return;
      }
      p=p->brother;
   }
};

void TXMLElem::addAttr(const char *name,const char *value)
{
   if(name==NULL || value==NULL) return ;
   TXMLAttr* p=new TXMLAttr;
   p->setName(name);
   p->setValue(value);
   addAttr(p);
};

// mode: 0, add elder brother;  1, add younger brother
void TXMLElem::addBrother(TXMLElem* pElement, int mode)
{
   pElement->parent=parent;   //if over write operator = ?

   if(mode==1)
   {
      pElement->brother=brother;
      brother=pElement;
   }
   else
   {
      TXMLElem* p=parent->child; 
      if(p==this)
      {
         pElement->brother=p;
         parent->child=pElement;
      }
      else
      {
         while(p!=NULL && p->brother!=this)
            p=p->brother;

         pElement->brother=p->brother;
         p->brother=pElement;
      }
   }
}

void TXMLElem::Read()
{
   int bIncludeContent = ReadBeginTag();
   
   if(bIncludeContent)
   {
      ReadContent();
      ReadEndTag();
   }
}

int TXMLElem::ReadBeginTag()
{
   lineNo = lineNumber;
   ASSERT_TOKEN(XML_TOKEN_START);

   GetToken(); //name
   ASSERT_TOKEN(XML_TOKEN_NAME);
   if(strlen(tokenValue) > TAG_LENGTH)
   {
       XMLERROR("line %d, col %d, too long tag,the max length is %d",lineNumber, colNumber,TAG_LENGTH); 
   }
   strcpy(m_strTag,tokenValue);
   
   GetToken();
   while(tokenType != XML_TOKEN_END && tokenType != XML_TOKEN_END2)
   {
      ReadAttribute();
   }
   int bIncludeContent = (tokenType == XML_TOKEN_END);
   GetToken(); 
   return bIncludeContent;
}

void TXMLElem::ReadAttribute()
{
   ASSERT_TOKEN(XML_TOKEN_NAME);
   TXMLAttr* pAttr=new TXMLAttr;
   ASSERT(pAttr);

   if(strlen(tokenValue) > ATTRNAME_LENGTH)
   {
      XMLERROR("line %d, col %d, too long attribute name,the max length is %d", lineNumber, colNumber,ATTRNAME_LENGTH); 
   }
   pAttr->setName(tokenValue);

   pAttr->lineNo = lineNumber;
   addAttr(pAttr);

   GetToken();
   ASSERT_TOKEN(XML_TOKEN_EQUAL);

   GetToken();
   ASSERT_TOKEN(XML_TOKEN_STRING);
   pAttr->setValue(tokenValue);

   GetToken();
}

void TXMLElem::ReadEndTag()
{
   ASSERT_TOKEN(XML_TOKEN_START2);

   GetToken(); //name
   ASSERT_TOKEN(XML_TOKEN_NAME);
   if(strcmp(getTag(), tokenValue) != 0)
      XMLERROR("line %d, col %d, tag %s not match %s", lineNumber, colNumber, tokenValue, getTag()); 

   GetToken(); 
   ASSERT_TOKEN(XML_TOKEN_END);
   
   GetToken(); 
}

void TXMLElem::ReadContent()
{
   char textBuf[MAX_TEXT_LEN+1];
   textBuf[0] = 0;
   while(tokenType != XML_TOKEN_START2)
   {
      if(tokenType == XML_TOKEN_TEXT)
      {
         if(strlen(textBuf) + strlen(textValue) > MAX_TEXT_LEN)
            XMLERROR("line %d, col %d, too long text", lineNumber, colNumber); 
         strcat(textBuf, textValue);
         GetToken();
      }
      else if(tokenType == XML_TOKEN_START)
      {
         TXMLElem* pChild = new TXMLElem();
         ASSERT(pChild);
         addChild(pChild);
         pChild->Read();
      }
      else if(tokenType == XML_TOKEN_CDATA)
      {
         TXMLElem* pCData= new TXMLElem();
         pCData->setTag("CDATA");
         pCData->setContent(textValue);
         addChild(pCData);
         GetToken();
      }
      else
      {
         XMLERROR("line %d, col %d, invalid token", lineNumber, colNumber); 
      }
   }

   TrimAll(textBuf);
   setContent(textBuf);
}

char* TXMLElem::toStr()
{
   int attrNum=GetAttrNum();
   int childNum=GetSubElemNum();

   typedef char* PCHAR;
   PCHAR* attrStr=new PCHAR[attrNum];
   PCHAR* childStr=new PCHAR[childNum];

   int totalLen=0;
   int i=0;
   TXMLAttr* pAttr=attr;
   while(pAttr!=NULL)
   {
      attrStr[i]=pAttr->toStr();
      totalLen+=strlen(attrStr[i])+1;
      pAttr=pAttr->brother;
      i++;
   }

   i=0;
   TXMLElem* pChild=child;
   while(pChild!=NULL)
   {
      childStr[i]=pChild->toStr();
      totalLen+=strlen(childStr[i]);
      pChild=pChild->brother;
      i++;
   }
   totalLen+=strlen(m_strTag)*2+2+3+1+(strlen(m_strContent)*6);
    
   char* s=new char[totalLen];

   s[0]=0;
   strcat(s,"<");
   
   strcat(s,m_strTag);
   for(i=0;i<attrNum;i++)
   {
      strcat(s," ");
      strcat(s,attrStr[i]);
      delete attrStr[i];
   }
   strcat(s,">");

   if(m_strContent)
   {
      char* encodeResult=xmlTextEncode(m_strContent);
      strcat(s,encodeResult);
      delete encodeResult;
   }

   for(i=0;i<childNum;i++)
   {
      strcat(s,childStr[i]);
      delete childStr[i];
   }
   
   strcat(s,"</");
   strcat(s,m_strTag);
   strcat(s,">");

   delete attrStr;
   delete childStr;

   return s;
}

TXMLElem* ParseXML(char* s)
{
   bReadTag = 0;
   tokenType = XML_TOKEN_EOF;
   tokenValue[0] = 0;
   pCurrent = s;
   pBuffer = s;
   pLast = s;
   lineNumber = 1;
   colNumber = 1;

   GetToken();
   TXMLElem *pRoot = new TXMLElem();
   
   ASSERT(pRoot);
   try 
   {
      pRoot->Read();
      return pRoot;
   } 
   catch(TXMLExcept e)
   {
      delete pRoot;
      throw e;
   }
}

void ASSERT_TOKEN(int x) 
{ 
   if (tokenType != x)
   {
      if(tokenType == XML_TOKEN_INVALID)
         XMLERROR("line %d, col %d, \"%s\", Syntax Error", 
            lineNumber, colNumber, tokenValue);
      else
         XMLERROR("line %d, col %d, \"%s\" should be token type \"%s\"", 
            lineNumber, colNumber, tokenValue, tokenTypeStrings[x]);
   }
}

void XMLERROR(const char* fmt, ...)
{
   char buffer[4096];
   va_list args;
   va_start(args, fmt);
   vsprintf(buffer, fmt, args);
   va_end(args);

   throw TXMLExcept(buffer); 
}

void xmlTextDecode(char* xmlText)
{
   char* r=xmlText;
   char* w=xmlText;
   while(*r!=0)
   {
      if(*r=='&')
      {
         if(strncmp(r+1,"amp;",4)==0)
         {
            r+=5;
            *w='&';
            w++;
            continue;
         }
         if(strncmp(r+1,"lt;",3)==0)
         {
            r+=4;
            *w='<';
            w++;
            continue;
         }
         if(strncmp(r+1,"gt;",3)==0)
         {
            r+=4;
            *w='>';
            w++;
            continue;
         }
         if(strncmp(r+1,"apos;",5)==0)
         {
            r+=6;
            *w='\'';
            w++;
            continue;
         }
         if(strncmp(r+1,"quot;",5)==0)
         {
            r+=6;
            *w='"';
            w++;
            continue;
         }
      }
      *w=*r;
      w++;
      r++;
   }
   *w=0;
}

char* xmlTextEncode(char* xmlText)
{
   char* xmlTextResult=new char[strlen(xmlText)*6+1];
   char* r=xmlText;
   char* w=xmlTextResult;
   while(*r!=0)
   {
      if(*r=='&')
      {
         memcpy(w,"&amp;",5);
         w+=5;
         r++;
         continue;
      }
      if(*r=='<')
      {
         memcpy(w,"&lt;",4);
         w+=4;
         r++;
         continue;
      }
      if(*r=='>')
      {
         memcpy(w,"&gt;",4);
         w+=4;
         r++;
         continue;
      }
      if(*r=='\'')
      {
         memcpy(w,"&apos;",6);
         w+=6;
         r++;
         continue;
      }
      if(*r=='"')
      {
         memcpy(w,"&quot;",6);
         w+=6;
         r++;
         continue;
      }
      *w=*r;
      w++;
      r++;
   }
   *w=0;
   return xmlTextResult;
}

void TrimAll(char* sour)
{
   char* p=sour;
   if(*p==0)
      return;
   
   for(;;)
   {
      if(*p >0x20 || *p ==0)
         break;
      p++;
   }
   strcpy(sour,p);
   
   if(*p ==0)
      return;
   
   p=sour+strlen(sour);
   for(;;)
   {
      if(*p >0x20)
      {
         *(p+1)=0;
         return;
      }
      p--;
   }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -