邻接列表:路径计数器无功能

时间:2014-03-11 04:37:08

标签: c queue adjacency-matrix

我正在一个程序中为邻接矩阵实现一个队列,该程序找到两个节点之间的最短路径。但我的路径计数器没有增加,我不明白为什么。任何帮助将不胜感激。

这是程序绘制的文件adj.data:

1 2
2 3
3 4
2 5
5 6
6 3
6 7
4 8
5 8
8 1

这是代码。

//------------------------Preprocessor Instructions. ------------------------------------
#include <stdio.h>
#include <stdlib.h>
#include <strings.h>

#define MAX 128     //Max number of nodes in the graph. 
#define BUFFER 120  //Buffer length.


//------------------------Global Stuff. -------------------------------------------------
int adjacency[MAX][MAX]={0};
int visited[MAX]={0};
int queue[MAX];
int head=-1;
int tail=-1;
int hops;


//------------------------Function Defintions. ------------------------------------------
int path(int src, int dest);
void QueuePush(int num);
int QueuePop();
int IsEmpty();


//------------------------Main. ---------------------------------------------------------
/*
    Main writes the file data to the adjacency matrix, and parses command line args. 

*/
int main(int argc, char **argv)
{
    FILE *fp;   //File pointer.
    char buffer[BUFFER];    //Temporary storage
    int src;    //Location a
    int dest;   //Location b
    int retval;
    int tempa=0;    
    int tempb=0;    //Temporary variables for reading from file to array. 
    int i=0;
    int j=0;    //Loop counters.

//Command Line Argument Parsing: Assigns inputs to variables. 
    if (argc != 3){
        printf("Usage: %s #a #b. \n",argv[0]);  //Usage: *program* *# #*
        return(1);
    }

    if (1 != sscanf(argv[1],"%d", &src)){   //Parses first integer.
        printf("Usage: %s #a #b. \n",argv[0]);
        return(1);
    }
    if (1 != sscanf(argv[2], "%d", &dest)){ //Parses second integer.
        printf("Usage: %s #a #b. \n",argv[0]);
        return(1);
    }

    printf(" Source: %d \n Destination: %d \n", src, dest);

//File reading. 
    fp=fopen("adj.data","r");
    if(NULL==fp){
        printf("Error opening file. \n");
        exit(0);
    }       

//Save file to array.
    while(NULL != fgets(buffer, BUFFER, fp)){
        sscanf(buffer, "%d %d", &tempa, &tempb);
        adjacency[tempa][tempb]=1;  //Assign 1 to locations (Making the adjacency matrix)
    }
    fclose(fp);

//Printing list for convenience.
    for(i=0;i<MAX;i++){
        for(j=0;j<MAX;j++){
            if(1==adjacency[i][j]){
                printf(" %d --> %d \n", i, j);  //Prints the graph as list.
            }
        }
    }
    retval=path(src, dest);
    if(0==retval){
        printf("There is no path from %d to %d. \n", src, dest);
    }
    else{
        printf("%d is %d hops away from %d. \n", src, hops, dest);
    }

    printf("Path returned %d \n", retval);
}


//------------------------Path function. ------------------------------------------------
/*
    The path function is where the work is done for the Shortest Path algorithm. 
    Puts a source node onto the queue, and then adds the nodes directly connected.
    Checks to see if any of the nodes on the queue are the destination node, and
    if they are it returns the number of hops. Otherwise it keeps adding and checking 
    until it either finds a path or reaches the end of the queue.
*/
int path(int src, int dest)
{
    int node;
    int i;

    QueuePush(src); //Pushes source node onto queue.
//While the queue isn't empty,
    while(0==IsEmpty)
    {
        node=QueuePop();    //Pop the head of the queue
        hops=QueuePop();    //Pop the next number, which will be the hops value.

//If popped value is equal to target, we're done!
        if(node==dest){
            return 1;
        }
//If the node has been visited before, do nothing.
        if(visited[node]==1){}
        else {
//Otherwise, search for connected nodes and add them to queue. 
            hops=hops+1;
            for(i=0;i<MAX;i++){
                if(adjacency[node][i]==1){  //If one exists, push onto queue.
                    QueuePush(i);
                    visited[node]=1;
                }
            }
        }
    }
    return 0;
}



//------------------------Push function for Queue. --------------------------------------
void QueuePush(int num)
{
//If queue is empty,
    if(-1==head && -1==tail){   
        head=0;
        tail=0;
        queue[tail]=num;    //Add a node.
        tail++;             //Incremement the tail(Queue no longer empty)
        queue[tail]=hops;   //Place number of hops right after the node. 
    } 
//If tail is about to hit the end,
    else if((tail==(MAX) || (tail==(MAX-1)) && (head != 0 || head != 1))){
            tail=0; //Bring the tail to the  front. (Circular Queue)
            queue[tail]=num;    //Place node in last queue spot
            tail++;
            queue[tail]=num;    //Place number of hops right after the added node.
        }
//Otherwise,
        else{
            tail++;
            queue[tail]=num;
            tail++;
            queue[tail]=hops;
        }
}



//------------------------Pop function for Queue. ---------------------------------------
int QueuePop()
{
    int node;   //Will be the first thing on the queue.
    node=queue[head];
//If the head and tail are equal, the queue is empty. 
    if(head==tail){
        head=-1;
        tail=-1;
    }
//If the queue is at the end, loop it around. (Circular Queue)
    else {
        if(head==MAX){
            head=0;
        }
        else{ 
            head++;
        }
    }
    return(node);   //Returns the next node.
}


//------------------------Function to check if the queue is empty. ----------------------
int IsEmpty()
{
//If queue is empty,
    if(-1==head){
        return 1;
    }
//Otherwise,
    else {
        return 0;
    }
}

提前致谢。

2 个答案:

答案 0 :(得分:1)

以下行永远不会成立,因为IsEmpty是指向函数的指针,并且永远不会为0.

while(0==IsEmpty)

你想说的是

while(0==IsEmpty() )

调用函数并检查返回值。

答案 1 :(得分:0)

这与您的问题无关,但我建议您使用STL队列而不是编写自己的队列功能。通过这种方式,您可以避免做很多错误。

我认为你的队列已满的假设也是错误的。当 tail-head == MAX head-tail == 1 时,循环队列将为满。