数据结构 散列表7.12 三角形游戏

#include<stdio.h>
#include<stdlib.h>
#include<algorithm>
using namespace std;

typedef struct TNode *Position;
typedef Position BinTree;
typedef long long int ElementType;
struct TNode{
    ElementType Data;
    BinTree Left;
    BinTree Right;
    int Height; 
    int times;
};


Position FindMin( BinTree BST ){
    if(!BST || !BST->Left)return BST;
    return FindMin(BST->Left);
}

Position FindMax( BinTree BST ){
    if(!BST || !BST->Right)return BST;
    return FindMax(BST->Right); 
}

BinTree Delete(BinTree BST,ElementType X)
{
    Position Tmp;
    if(!BST)
        printf("要删除的元素未找到");
    else 
    {
        if(X < BST->Data)
            BST->Left = Delete(BST->Left,X);//左子树递归删除
        else if(X > BST->Data)
            BST->Right = Delete(BST->Right,X);//右子树递归删除
        else{//BST就是要删除的点 
            //如果被删除的结点有左右两个子结点 
            if(BST->Left&&BST->Right)
            {
                Tmp = FindMin(BST->Right);
                BST->Data = Tmp->Data;
                BST->Right = Delete(BST->Right,BST->Data); 
             } 
            else{//被删除的结点只有一个或无子节点 
                Tmp = BST;
                if(!BST->Left)
                    BST = BST->Right;
                else
                    BST = BST->Left; 
                free(Tmp);
            }
        } 
    } 
    return BST;
}

int Max( int a,int b)
{
    return a > b ? a : b; 
}

int Height(BinTree t)
 {
     int hl,hr;
     if(!t)return -1;
     hl=Height(t->Left);
     hr=Height(t->Right);
     if(hl>hr) return ++hl;
     else return ++hr;
 }
 
 int GetHeight(BinTree T){
     if(!T)return 0;
     return T->Height;
 }

BinTree SingleLeftRotation(BinTree A)
{  //注意 A必须有一个左子结点B
   //将A和B做左单旋,更新A和B的高度,返回新的结点B
    BinTree B = A->Left;
    A->Left = B->Right ;
    B->Right = A;
    A->Height = Max( GetHeight(A->Left),GetHeight(A->Right))+1;
    B->Height = Max( GetHeight(B->Left),A->Height)+1;
    return B;    
 } 

BinTree SingleRightRotation(BinTree A)
{
    BinTree B = A->Right ;
    A->Right = B->Left;
    B->Left = A; 
    A->Height = Max( GetHeight(A->Left),GetHeight(A->Right))+1;
    B->Height = Max( GetHeight(B->Right),A->Height)+1;
    return B;
}

BinTree DoubleLeftRightRotation(BinTree A)
{
    /* 注意:A必须有一个左子结点B,且B必须有一个右子结点C */
  /* 将A、B与C做两次单旋,返回新的根结点C */
  /* 将B与C做右单旋,C被返回 */
    A->Left = SingleRightRotation(A->Left);
     /* 将A与C做左单旋,C被返回 */
    return SingleLeftRotation(A);
}

BinTree DoubleRightLeftRotation(BinTree A)
{
    A->Right = SingleLeftRotation(A->Right);
    return SingleRightRotation(A);
}

BinTree Insert(BinTree BST,ElementType X)
{
    if(!BST)
    {//若原树为空,生成并返回一个结点的二叉搜索树
        BST = (BinTree)malloc(sizeof(struct TNode));
        BST->Data = X;
        BST->Left = BST->Right =NULL;
        BST->times = 1; 
    }
    else //开始查找要插入的的元素的位置 
    { 
        if( X < BST->Data )
        {
            BST->Left = Insert(BST->Left,X);//递归插入左子树
            if(GetHeight(BST->Left) - GetHeight(BST->Right) == 2)
            {
                if( X < BST->Left->Data )
                BST = SingleLeftRotation(BST);
                else 
                BST = DoubleLeftRightRotation(BST);
             } 
        }
        else if(X > BST->Data)
        {
            BST->Right = Insert(BST->Right,X);//递归插入右子树 
            if(GetHeight(BST->Left) - GetHeight(BST->Right)== -2)
            {
                if(X > BST->Right->Data )
                BST = SingleRightRotation(BST);
                else
                BST = DoubleRightLeftRotation(BST); 
            } 
        }
        //else X已经存在,什么都不做 
        else
        {
            BST->times++;
        }
    }
    BST->Height = Max(GetHeight(BST->Left),GetHeight(BST->Right)) + 1;
    return BST;
}

BinTree MakeTree(int n){
    BinTree bt = NULL; 
    int bian[3];
    for(int i=0;i<n;i++)
    {
        for(int j=0;j<3;j++)
        {
            scanf("%d",&bian[j]);
        }
        sort(bian,bian+3); 
//        printf("%lld\n",((((long long int)bian[0] * 1000000+bian[1])*1000000)+bian[2]));
        bt = Insert(bt, ((((long long int)bian[0] * 1000000+bian[1])*1000000)+bian[2]));
    }
    return bt;
}

Position Find( BinTree BST, ElementType X ){
    if(!BST||BST->Data==X)return BST;
    return Find((X>BST->Data?BST->Right:BST->Left),X); 
}


void traveinorder(BinTree bt)
{
    if(bt){
    printf("%lld %d\n",bt->Data,bt->times);
    traveinorder(bt->Left);
    traveinorder(bt->Right);
    }
 } 
 
 void Search(int m,BinTree bt){
     int bian[3];
    for(int i=0;i<m;i++)
    {
        for(int j=0;j<3;j++)
        {
            scanf("%d",&bian[j]);
        }
        sort(bian,bian+3); 
//        printf("%lld\n",((((long long int)bian[0] * 1000000+bian[1])*1000000)+bian[2]));
        BinTree temp = Find(bt, ((((long long int)bian[0] * 1000000+bian[1])*1000000)+bian[2]));
        if(temp == NULL)printf("0\n");
        else printf("%d\n",temp->times); 
    }
 }
 
int main()
{
    int n,m;
    scanf("%d",&n);
    BinTree bt = NULL; 
    bt = MakeTree(n);
    scanf("%d",&m);
//    traveinorder(bt);
    Search(m,bt); 
} 

 

 

 

数据结构 散列表7.12 三角形游戏

★实验任务

给定n个三角形,用a,b,c表示三角形的三条边(三角形可能有重复)。之后有m次询问,每次询问一个三角形在给定的n个三角形中出现的次数。

★数据输入

第一行为n,之后n行,每行有a,b,c三个数字表示三角形的三条边;接下来一行为m,之后有m行询问,每行有a,b,c三个数字,表示要询问的三角形的三边。 数据保证a,b,c为正整数且可以构成一个三角形,且a,b,c不一定有序 对于40%的数据,n<=100,m<=100,a,b,c<=100 对于70%的数据,n<=1000,m<=1000,a,b,c<=1000 对于100%的数据,n<=5,000,m<=100,000,a,b,c<=999999

★数据输出

对于每次询问,输出此三角形在之前给定的n个三角形中出现的次数

输入示例
3
2 2 3
3 3 4
2 3 2
3
2 3 2
3 3 4
1 1 1
 

 

 

输出示例
2
1
0

posted on 2020-11-07 15:24  xwwer  阅读(483)  评论(0)    收藏  举报