123

#include<iostream>
using namespace std;
#define LEN 50

typedef struct stations{
    char name[20];
    int len;
    int roads[50];
    struct stations *left ;
    struct stations *right ;
}Stations;

typedef struct etree{
    int value;
    int roadNum;
    struct etree *father;
    int childnum;
}ETree;

typedef struct queue{
        ETree *tie;
        struct queue *next;
}Queue;

void pushQueue(Queue &head , ETree *&etree){
    Queue *p = head.next , *q = &head ;
    while( p!=NULL && (p->tie->value < etree->value) ){
        q = p ;
        p = p->next ;
    }
    q->next = (Queue*)malloc(sizeof(Queue)) ;
    q->next->tie = etree ;
    q->next->next = p ;
}
void freeEtree(ETree *q){
    ETree *p;
    while(q->childnum==0){
        p = q;
        q = q->father;
        free(p);
        if(q!=NULL)
            q->childnum--;
        else
            break;
    }
}


void freeAll(Stations * &head){
    if(head!=NULL){
        freeAll(head->left);
        freeAll(head->right);
        free(head);
    }
}
void showBest(ETree *h,int price[][LEN],char roadName[][20],int roadNum){
    if(h!=NULL){
        if(h->father==NULL){
            printf("%s",roadName[h->roadNum]);
        }
        else{
            int j;
            j = h->roadNum ;
            if( h->value == ( price[j][j] + h->father->value ) ){
                showBest(h->father,price,roadName,roadNum);
                if(price[j][roadNum]){
                    printf("-(%s,%s)",roadName[j],roadName[price[j][roadNum]-1]);
                }
                else
                    printf("-%s",roadName[j]);
            }
            else{
                showBest(h->father->father,price,roadName,roadNum);
                printf("-(%s,%s)",roadName[h->father->roadNum],roadName[j]);
            }            
        }
    }
}


inline int compares(char s1[],int n1 , char s2[] ,int n2){
    if(n1!=n2)
        return n1-n2;
    return strcmp(s1,s2);
}

bool findStation(Stations* &head , Stations* &p , char s[]){
    int len = strlen(s);
    int t;
    Stations *q;
    p=head;    
    while(p!=NULL){
        q = p;
        t=compares(s,len,p->name,p->len);
        if(t<0)
            p=p->left;
        else
            if(t>0)
                p=p->right;
            else
                return true;
    }
    p = q;
    return false;
}

void insert(Stations* &head,char s[] , int road,int price[][LEN]){
    Stations *p,*q;
    int t;
    t=strlen(s);
    if(s[t-1]=='\n')
        s[t-1] = '\0';
    if(head==NULL){
        p = (Stations *)malloc(sizeof(Stations));
        p->left = NULL;
        p->right = NULL;
        strcpy( p->name , s );
        p->len = strlen(s);

        p->roads[0] = 1;
        p->roads[1] = road;

        head = p;
    }
    else{
        if( findStation(head,p,s) ){
            p->roads[0]++;
            t=p->roads[0];
            p->roads[t] = road ;
            for(t--; t >0 ; t--){
                price[p->roads[t]][road] = -1;
                price[road][p->roads[t]] = -1;
            }
        }
        else{
            q = p ;
            p = (Stations *)malloc(sizeof(Stations));
            p->left = NULL;
            p->right = NULL;
            strcpy( p->name , s );
            p->len = strlen(s);

            p->roads[0] = 1;
            p->roads[1] = road;

            t = compares(s,p->len,q->name,q->len);
            
            if(t<0)
                q->left = p;
            else
                q->right = p;
        }
    }
}
int GetRoadNum(char *r,char roadName[][20],int roadNum){
    for(int i=0 ; i<roadNum ; i++)
        if(strcmp(roadName[i],r)==0)
            return i;
    return 0;
}


void main()
{

    //[roadnum][roadnum+1]
    int price[LEN][LEN]={0}; 
    char roadName[LEN][20];

    int i,j,k,t;
    char line[20];
    int roadNum;

    Stations *head=NULL;

    FILE *fp;

    if((fp=fopen("stations.txt","r"))==NULL){
        printf("找不到stations文件\n");
        return;
    }
    
    roadNum = 0 ;
    while(!feof(fp)){
        fscanf(fp,"%s%*c",roadName[roadNum]);
        fgets(line,19,fp);
        while( !feof(fp) && line[0]!='\n'){
            insert(head,line,roadNum,price);
            fgets(line,19,fp);
        }
        roadNum++;
    }
    insert(head,line,roadNum-1,price);
    fclose(fp);


    if((fp=fopen("price.txt","r"))==NULL){
        printf("找不到price文件");    
    }

    while(!feof(fp)){
        fscanf(fp,"%s",line);
        fscanf(fp,"%d",&k);
        for(t=0; line[t]!='\0' && line[t]!= ',' ; t++ );
        if(line[t]==','){
            line[t] = '\0' ;
            i = GetRoadNum(line,roadName,roadNum);
            j = GetRoadNum(line+t+1,roadName,roadNum);
            price[i][j] = k;
            price[j][i] = k;
            if(price[i][i] > k ){
                price[i][i] = k;
                price[i][roadNum]=j+1;
            }
            if(price[j][j] > k ){
                price[j][j] = k;
                price[j][roadNum]=i+1;
            }
        }
        else{
            i = GetRoadNum(line,roadName,roadNum);
            price[i][i] = k;
        }
    }

    fclose(fp);


    char starts[20]={"五棵松"},ends[20]={"奥体中心"};


    Stations* sroad,*eroad;
    Queue Qhead, *h;
    ETree *p,*q;

    while(true){

        char Flag[LEN]={0}; // 为-1表示目标 为0表示尚未发生过扩展

        Qhead.next = NULL;
        Qhead.tie = NULL;

        scanf("%[^,\n]s",starts);
        if(getchar()!=',')
            break;
        scanf("%[^\n]s",ends);
        getchar();
        if(!findStation(head,sroad,starts)){
            printf("未找到%s的匹配项\n",starts);
            continue;
        }
        if(!findStation(head,eroad,ends)){
            printf("未找到%s的匹配项\n",ends);
            continue;
        }

        for( i = 1 ; i <= sroad->roads[0] ; i++ ){
            p = (ETree*)malloc(sizeof(ETree));
            p->father = NULL ;
            p->childnum = 0 ;
            p->roadNum = sroad->roads[i];
            p->value = price[p->roadNum][p->roadNum] ;            
            pushQueue(Qhead,p);
        }

        for( i = 1 ; i <= eroad->roads[0] ; i++ ){
            Flag[eroad->roads[i]] = -1 ;
        }

        while( Qhead.next != NULL ){
            h =Qhead.next;
            q = h->tie ;
            if(Flag[q->roadNum]==-1){
                break;
            }
            Qhead.next = Qhead.next->next;
            i = q->roadNum;
            if(Flag[i]!=1){
                for(j=0 ; j<roadNum ; j++ ){
                    if(price[i][j]){                        
                        q->childnum++;

                        p = (ETree*)malloc(sizeof(ETree));
                        p->father = q ;
                        p->childnum = 0 ;
                        p->roadNum = j ;
                        k = price[j][j] + q->value ;
                        if(price[i][j]>0 ){
                            if(q->father!=NULL)
                                t = price[i][j] + q->father->value ;
                            else
                                t = price[i][j] ;
                            if(k>t)
                                k = t;
                        }
                        p->value = k ;
                        pushQueue(Qhead,p);
                    }
                }
                Flag[i] = 1;
            }
            freeEtree(h->tie);
            free(h);
        }
        
        if(Qhead.next!=NULL){
            showBest(q,price,roadName,roadNum);
            printf(" = %d\n",q->value);
        }
        else
            printf("此路不通\n");

        for(  ; Qhead.next!=NULL ; ){
            h = Qhead.next;
            Qhead.next = Qhead.next->next;
            freeEtree(h->tie);
            free(h);
        }
    }

    freeAll(head);
}

 

posted on 2013-07-09 22:41  wwjyt  阅读(269)  评论(0编辑  收藏  举报