最近写了一个C程序统计计算web log中的ip每个IP出现的次数,于是采用数据结构中的二叉树进行实现,具体代码如下:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <sys/time.h>
struct tnode {
    char *word;
    int count;
    struct tnode *left;
    struct tnode *right;
};
/* 记录时间 */
static double mytime(void)
{
    struct timeval tv;
    if(gettimeofday(&tv, NULL) == -1) return 0.0;
    return (double)tv.tv_sec + (double)tv.tv_usec / 1000000.0;
}
/* 构建二叉树 */
static struct tnode *addtree(struct tnode *p, char *w)
{
    int cond;
    /* 判断是否为空 如果为空树,构建根节点 */
    if (p == NULL) {
        p = (struct tnode *) malloc(sizeof(struct tnode));
        if (p == NULL) {
            fprintf(stderr, "Cannot alloc memory!");
            exit(-1);
        }
        p->word = strdup(w);
        p->count = 1;
        p->left = p->right = NULL;
    } else if ((cond = strcmp(w, p->word)) == 0)  /* 是否存在叶子节点中*/
        p->count++;                                          /* 如果存在叶子节点计数加一  */
    else if (cond < 0)
        p->left = addtree(p->left, w);                  /* 如果不存在叶子节点且比叶子节点少,则添加左叶子节点 */
    else
        p->right = addtree(p->right, w);              /* 如果存在叶子节点且比叶子节点大,则添加右叶子节点 */
    return p;
}
/* 打印二叉树 */
static void print(struct tnode *p)
{
    if (p != NULL) {
        print(p->left);
        fprintf(stdout, "%s:t%dn", p->word, p->count);
        print(p->right);
    }
}
int main(int argc, char *argv[])
{
    FILE    *fp;
    char    ip[32] = {}, buf[512] = {};
    int     i;
    struct  tnode *root = NULL;
    /* 打开log文件 */
    fp = fopen("access.log", "rb");
    if (fp == NULL) {
        fprintf(stderr, "Cannot open file login.log");
        exit(-1);
    }
    /* 记录当前的时间 */
    double stime = mytime();
    /* 按行读取文件 */
    while (fgets(buf, sizeof(buf), fp)) {
        /* 遇到空格跳出 */
        for (i = 0; i < 16 && buf[i] != '