1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159
|
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "xmlparse.h"
static XML_Parser parser = NULL;
typedef struct {
char *name;
double value;
} DataNode;
typedef struct {
const char *itemID;
const char *groupID;
int dataCount;
DataNode **datas;
} ItemNode;
typedef struct {
int itemCount;
ItemNode **items;
} ItemList;
typedef struct {
int listCount;
ItemList *lists;
} GroupedLists;
static ItemList *ItemList_create()
{
ItemList *d = (ItemList *) (malloc(sizeof(ItemList)));
d->itemCount = 0;
d->items = NULL;
return d;
}
static void ItemList_addItemNode(ItemList *d, ItemNode *n)
{
int i = d->itemCount++;
d->items = realloc(d->items, sizeof(ItemNode *) * d->itemCount);
d->items[i] = n;
}
static ItemNode *ItemNode_create()
{
ItemNode *i = (ItemNode *) (malloc(sizeof(ItemNode)));
i->itemID = NULL;
i->groupID = NULL;
i->dataCount = 0;
i->datas = NULL;
return i;
}
static void ItemNode_addDataNode(ItemNode *n, DataNode *d)
{
int i = n->dataCount++;
n->datas = realloc(n->datas, sizeof(DataNode *) * n->dataCount);
n->datas[i] = d;
}
static DataNode *DataNode_create()
{
DataNode *i = (DataNode *) (malloc(sizeof(DataNode)));
i->name = NULL;
i->value = 0.0;
return i;
}
static void startElement(void *userData, const char *name, const char **atts)
{
int i;
ItemList *currentList = (ItemList *) userData;
if (strcmp(name, "dataset") == 0) {
}
else if (strcmp(name, "item") == 0) {
ItemNode *currentItem = ItemNode_create();
for (;*atts; atts++) {
if (strcmp(*atts, "groupid") == 0) {
currentItem->groupID = strdup(*(atts + 1));
}
else if (strcmp(*atts, "itemid") == 0) {
currentItem->itemID = strdup(*(atts + 1));
}
}
ItemList_addItemNode(currentList, currentItem);
}
else {
ItemNode *currentItem = currentList->items[currentList->itemCount - 1];
DataNode *currentData = DataNode_create();
currentData->name = strdup(name);
for (;*atts; atts++) {
if (strcmp(*atts, "data") == 0) {
currentData->value = strtod(*(atts + 1), NULL);
}
}
ItemNode_addDataNode(currentItem, currentData);
}
}
static void endElement(void *userData, const char *name)
{
}
static int compareItems(const void *arg1, const void *arg2)
{
const ItemNode **item1 = (ItemNode **) arg1;
const ItemNode **item2 = (ItemNode **) arg2;
int result;
if ((result = strcmp((*item1)->groupID, (*item2)->groupID)) != 0) {
return result;
}
return strcmp((*item1)->itemID, (*item2)->itemID);
}
ItemList *getData(FILE *inputfp) {
int done = 0;
char buf[1000];
XML_Parser parser = XML_ParserCreate(NULL);
ItemList *list = ItemList_create();
XML_SetUserData(parser, list);
XML_SetElementHandler(parser, startElement, endElement);
do {
size_t len = fread(buf, 1, sizeof(buf), inputfp);
done = len < sizeof(buf);
if (!XML_Parse(parser, buf, len, done)) {
fprintf(stderr,
"%s at line %d\n",
XML_ErrorString(XML_GetErrorCode(parser)),
XML_GetCurrentLineNumber(parser));
return NULL;
}
} while (!done);
qsort((void *) (list->items), list->itemCount, sizeof(*(list->items)), &compareItems);
return list;
}
int main(int argc, char **argv)
{
int i, j;
ItemList *list = getData(stdin);
for (i = 0; i < list->itemCount; i++) {
printf("item %s %s\n",
list->items[i]->groupID,
list->items[i]->itemID);
for (j = 0; j < list->items[i]->dataCount; j++) {
printf("data %s %f\n",
list->items[i]->datas[j]->name,
list->items[i]->datas[j]->value);
}
}
}
|