二叉查找树(通过外排思想处理大数据)

来源:互联网 发布:云计算为什么这么火 编辑:程序博客网 时间:2024/05/19 06:37

因为要读的文件很大 ,不能直接一次读进数组,需要通过读一部分,释放内存,再读的方式来解决, 因为直接插入二叉查找(排序)树,则不需要再将排序好的数据先放入别的文件。

#include <stdio.h>#include <windows.h>#include <stack>#include <iostream>using namespace std;typedef int ElementType; typedef struct TreeNode *Tree;typedef struct TreeNode *Position;#define N 250000    //行#define L 2     //列const char file_name[50] = "hjy123.txt";void InOrder( Tree T);Tree Delete(ElementType X,Tree T);Tree Insert(ElementType X,Tree T);Position Find( ElementType X,Tree T);Position FindMin( Tree T);struct TreeNode{    ElementType Data;    Tree Left,Right;};Tree BST = NULL;void main() {       system("color f0");    int i,j;    FILE *fp;    fp=fopen(file_name, "rb");    long count ;    //记数器,记录已读出的整数    long **data;    data=(long **)malloc(N * sizeof(long *));   //分配指向行的指针数组      for(i=0;i<N;i++) {        data[i]=(long *)malloc(L*sizeof(long));  //分配行指针所指向的数组        //动态二维数组的建立(行列限制内存大小)    }    long temp;    for(int a = 0; a < 200; a++){        long index[N] = {0};        count = 0;        while( 1 == fscanf(fp, "%d", &temp)     ) {            data [(index[count%L])++] [count%L] = temp;            count++;            if(count == 500000) break;        }         for(i = 0,j = 0; i < N ; i++ ) {            if(data[i][j] == 1) {                BST = Insert(data[i][j+1],BST);            } else if(data[i][j] == 2) {                 if(Find(data[i][j+1],BST) != NULL)                          printf("数据%d:查找成功!\n",data[i][j+1]);                else                        printf("数据%d:查找失败!\n",data[i][j+1]);            } else if(data[i][j] == 3) {                Delete(data[i][j+1],BST);                     printf("数据%d:删除成功!\n",data[i][j+1]);            } else if(data[i][j] == 0) {                fclose(fp);                printf("中序遍历结果如下:\n");                InOrder(BST);                printf("\n");                for(int k=0; k < L; k++){                       free(data[k]); //释放所有行空间                  }                  free(data); //释放行指针数组                 exit(0);            }         }    }}Position Find( ElementType X,Tree T) {  //查找    if(T != NULL){        if( X < T->Data )       return Find( X, T->Left);        else if( X > T->Data)   return Find( X, T->Right);        else                    return T;    }      else            return NULL;}Tree Insert(ElementType X,Tree T) {     //插入    if(T == NULL) { //当树为空树  初始化树根        T = (Tree)malloc(sizeof(struct TreeNode ));        T->Data = X;        T->Left = T->Right = NULL;    }    else if( X < T->Data)   T->Left = Insert(X, T->Left);    else if( X > T->Data)   T->Right = Insert(X, T->Right);    return T;}void InOrder(Tree T) {  //非递归中序遍历    stack<Tree> s;    Tree P = T;    while(P != NULL || !s.empty() ) {        while(P != NULL) {              s.push(P);  //压入            P = P->Left;        }        if(!s.empty()) {            P = s.top();    //取栈顶            printf("%d ",P->Data);            s.pop();            P = P->Right;        }    }}Position FindMin( Tree T) {     //非递归实现方法    if( T!=NULL)         while(T->Left != NULL)            T = T->Left;        return T;}Tree Delete(ElementType X, Tree T) {    //删除  分两种情况      Position Tmp;    if(X < T->Data )        T->Left = Delete( X, T->Left);    else if(X > T->Data)        T->Right = Delete( X, T->Right);    else{   //找到要删除的结点        if( T->Left && T->Right) {  //被删除结点有左右两个子结点            Tmp = FindMin( T->Right);   //在右子树中找最小元素填充删除元素            T->Data = Tmp->Data;            T->Right = Delete( T->Data, T->Right);            free( Tmp );            //大数据必须释放内存        } else {    //被删除结点有一个或无子结点            Tmp = T;            if( !T->Left )                T = T->Right;            else if( !T->Right)                T = T->Left;            free(Tmp);        }    }    return T;   }
原创粉丝点击