typedef struct _xmlNode xmlNode;
typedef xmlNode *xmlNodePtr;
struct _xmlNode {
void *_private; /* application data */
xmlElementType type; /* type number, must be second ! */
const xmlChar *name; /* the name of the node, or the entity */
struct _xmlNode *children; /* parent->childs link */
struct _xmlNode *last; /* last child link */
struct _xmlNode *parent; /* child->parent link */
struct _xmlNode *next; /* next sibling link */
struct _xmlNode *prev; /* previous sibling link */
struct _xmlDoc *doc; /* the containing document */
/* End of common part */
xmlNs *ns; /* pointer to the associated namespace */
xmlChar *content; /* the content */
...
}
有一个类似于上面的节点,并且假设一个节点具有xmlNode node
(而不是NULL
(
想要访问node->next->children->next->next->content
,但由于每个指针都可以是NULL
,因此必须检查所有指针。
if(node == NULL || node->next == NULL || node->next->children == NULL ...)
fprintf(stderr, "err");
有没有一种方法可以自动检查指针是否为NULL?如
#define CHECK(ptr) BOOST_PP_????(...) ??
if (CHECK(node->next->children->next->next->content))
...
_xmlNode
来自libxml2,由于我访问HTML解析数据中的成员以获取爬行网站的特定元素,所以访问不能像下面这样是常规的。
bool go_next(xmlNode n, int num) {
for(; num; --num) {
if(n==NULL) return false;
n = n->next;
}
return true;
}
使用enum
和复合文字是微不足道的,比如:
enum {END, PREV, NEXT, CHILDREN, CONTENTS};
int check_node(xmlNode node, int test[])
{
while ((node != NULL) && (*test != END))
{
switch (*test)
{
case PREV:
node = node->prev;
break;
case NEXT:
node = node->next;
break;
case CHILDREN:
node = node->children;
break;
case CONTENTS:
node = node->contents;
break;
default:
return 0;
}
test++;
}
return (node != NULL);
}
if (!check_node(node, (int []){NEXT, CHILDREN, NEXT, NEXT, CONTENTS, END}))
{
fprintf(stderr, "err");
}