我在C程序中使用minixml。当我使用mxmlSaveFile(bkp_tree, fp, MXML_NO_CALLBACK);函数将minixml树保存到文件中时,我将整个xml数据保存在一个块中。没有组织在文件中显示xml结构(换行,缩进...)。

xml数据以这种方式保存

<B1><BB1>BBB1</BB1></B1><B2><BB2>BBB2</BB2></B2><B3><BB3>BBB3</BB3></B3>

如何通过以下方式使minixml保存xml数据?
<B1>
    <BB1>BBB1</BB1>
</B1>
<B2>
    <BB2>BBB2</BB2>
</B2>
<B3>
    <BB3>BBB3</BB3>
</B3>

最佳答案

minixml documentation复制:

对于每个元素节点,您的回调函数将最多调用四次,并带有指向该节点的指针和MXML_WS_BEFORE_OPENMXML_WS_AFTER_OPENMXML_WS_BEFORE_CLOSEMXML_WS_AFTER_CLOSE的“where”值。如果不添加空格,则回调函数应返回NULL,否则应插入字符串(空格,制表符,回车和换行符)。

以下空白回调可用于将空白添加到XHTML输出中,以使其在标准文本编辑器中更具可读性:

const char *
whitespace_cb(mxml_node_t *node,
              int where)
{
  const char *name;

 /*
  * We can conditionally break to a new line
  * before or after any element. These are
  * just common HTML elements...
  */

  name = mxmlGetElement(node);

  if (!strcmp(name, "html") ||
      !strcmp(name, "head") ||
      !strcmp(name, "body") ||
  !strcmp(name, "pre") ||
      !strcmp(name, "p") ||
  !strcmp(name, "h1") ||
      !strcmp(name, "h2") ||
      !strcmp(name, "h3") ||
  !strcmp(name, "h4") ||
      !strcmp(name, "h5") ||
      !strcmp(name, "h6"))
  {
   /*
* Newlines before open and after
    * close...
*/

if (where == MXML_WS_BEFORE_OPEN ||
        where == MXML_WS_AFTER_CLOSE)
  return ("\n");
  }
  else if (!strcmp(name, "dl") ||
           !strcmp(name, "ol") ||
           !strcmp(name, "ul"))
  {
   /*
* Put a newline before and after list
    * elements...
*/

return ("\n");
  }
  else if (!strcmp(name, "dd") ||
           !strcmp(name, "dt") ||
           !strcmp(name, "li"))
  {
   /*
* Put a tab before <li>'s, * <dd>'s,
    * and <dt>'s, and a newline after them...
*/

if (where == MXML_WS_BEFORE_OPEN)
  return ("\t");
else if (where == MXML_WS_AFTER_CLOSE)
  return ("\n");
  }

 /*
  * Return NULL for no added whitespace...
  */

  return (NULL);
}

要使用此回调函数,只需在调用任何保存函数时使用名称:
FILE *fp;
mxml_node_t *tree;

fp = fopen("filename.xml", "w");
mxmlSaveFile(tree, fp, whitespace_cb);
fclose(fp);

09-19 10:36