Ejemplo n.º 1
0
int postorder (const BiTreeNode *node, List *list)
{
    if (!bitree_is_eob(node)) {
        if (!bitree_is_eob(bitree_left(node))) {
            if (postorder(bitree_left(node), list) != 0) {
                return -1;
            }
        }

        if (!bitree_is_eob(bitree_right(node))) {
            if (postorder(bitree_right(node), list) != 0) {
                return 0;
            }
        }

        if (list_ins_next(list, list_tail(list), bitree_data(node)) != 0) {
            return -1;
        }
    }

    return 0;
}
Ejemplo n.º 2
0
int set_intersection(Set *seti, const Set *set1, const Set *set2)
{
    ListElmt *member;
    void *data;

    set_init(seti, set1->match, NULL);

    for (member = list_head(set1); member != NULL; member = list_next(member))
    {
        if (set_is_member(set2, list_data(member)))
        {
            data = list_data(member);
            if (list_ins_next(seti, list_tail(seti), data) != 0)
            {
                set_destroy(seti);
                return -1;
            }
        }
    }

    return 0;
}
int set_intersection(Set * seti, const Set * set1, const Set * set2)
{

    ListElmt *member;

    void *data;

    /*****************************************************************************
    *  Initialize the set for the intersection.                                  *
    *****************************************************************************/

    set_init(seti, set1->match, NULL);

    /*****************************************************************************
    *  Insert the members present in both sets.                                  *
    *****************************************************************************/

    for (member = list_head(set1); member != NULL;
            member = list_next(member)) {

        if (set_is_member(set2, list_data(member))) {

            data = list_data(member);

            if (list_ins_next(seti, list_tail(seti), data) != 0) {

                set_destroy(seti);
                return -1;

            }

        }

    }

    return 0;

}
int set_difference(Set * setd, const Set * set1, const Set * set2)
{

    ListElmt *member;

    void *data;

    /*****************************************************************************
    *  Initialize the set for the difference.                                    *
    *****************************************************************************/

    set_init(setd, set1->match, NULL);

    /*****************************************************************************
    *  Insert the members from set1 not in set2.                                 *
    *****************************************************************************/

    for (member = list_head(set1); member != NULL;
            member = list_next(member)) {

        if (!set_is_member(set2, list_data(member))) {

            data = list_data(member);

            if (list_ins_next(setd, list_tail(setd), data) != 0) {

                set_destroy(setd);
                return -1;

            }

        }

    }

    return 0;

}
Ejemplo n.º 5
0
int set_difference(Set *setd, const Set *set1, const Set *set2) {
    ListElem *member;
    void *data;

    //init union
    set_init(setd, set1->match, NULL);

    //insert members of the first set
    for (member = list_head(set1); member != NULL; member = list_next(member)) {

        if (!set_is_member(set2, list_data(member))) {
            data = list_data(member);

            if (list_ins_next(setd, list_tail(setd), data) != 0) {

                set_destroy(setd);
                return -1;
            }
        }
    }

    return 0;
};
Ejemplo n.º 6
0
/**
 * 后序遍历二叉树
 */
int postorder(const BiTreeNode *node, List *list){

	if(!bitree_is_eob(node)){
		if(!bitree_is_eob(bitree_left(node))){
			if(inorder(bitree_left(node), list) != 0){
				printf("%s\n","postorder() left tree order end");
				return -1;
			}
		}
		if(!bitree_is_eob(bitree_right(node))){
			if(inorder(bitree_right(node), list) != 0){
				printf("%s\n", "postorder() right tree order end");
				return -1;
			}
		}
		if(list_ins_next(list, list_tail(list), bitree_data(node)) != 0){
			printf("%s\n", "postorder() add node to list fail.");
			return -1;
		}
	}

    return 0;
}
Ejemplo n.º 7
0
Archivo: list-1.c Proyecto: whatot/ma_c
int main() {
	List list;
	ListElmt *element;

	int *data;
	int i;

	list_init(&list, free);
	element = list_head(&list);
	
	for (i = 10; i > 0; i--) {
		if ((data = (int *)malloc(sizeof(int))) == NULL) {
			return 1;
		}

		* data = i;

		if (list_ins_next(&list, NULL, data) != 0) {
			return 1;
		}
	}

	print_list(&list);

	element = list_head(&list);

	for (i = 0; i < 7; i++) {
		element = list_next(element);
	}

	data = list_data(element);
	fprintf(stdout, "Removing an element after the one containing %03d\n",
			*data);
	if (list_rem_next(&list, element, (void **)&data) != 0) {
		return 1;
	}

	print_list(&list);

	fprintf(stdout, "Inserting 011 at the tail of the list\n");
	*data = 11;
	if (list_ins_next(&list, list_tail(&list), data) != 0) {
		return 1;
	}

	print_list(&list);

	fprintf(stdout, "Removing an element after the first element\n");
	element = list_head(&list);
	if (list_rem_next(&list, element, (void **)&data) != 0) {
		return 1;
	}

	print_list(&list);

	fprintf(stdout, "Inserting 012 at the head of the list\n");
	*data = 12;
	if (list_ins_next(&list, NULL, data) != 0) {
		return 1;
	}

	print_list(&list);

	fprintf(stdout, "Iterating and removing the fourth element\n");
	element = list_head(&list);
	element = list_next(element);
	element = list_next(element);
	if(list_rem_next(&list, element, (void **)&data) != 0) {
		return 1;
	}

	print_list(&list);

	fprintf(stdout, "Inserting 013 after the first element\n");
	*data = 13;
	if (list_ins_next(&list, list_head(&list), data) != 0) {
		return 1;
	}

	print_list(&list);

	i = list_is_head(&list, list_head(&list));
	fprintf(stdout, "Testing list_is_head...Value=%d (1=OK)\n", i);
	i = list_is_head(&list, list_tail(&list));
	fprintf(stdout, "Testing list_is_head...Value=%d (1=OK)\n", i);
	i = list_is_tail(list_tail(&list));
	fprintf(stdout, "Testing list_is_head...Value=%d (1=OK)\n", i);
	i = list_is_tail(list_head(&list));
	fprintf(stdout, "Testing list_is_head...Value=%d (1=OK)\n", i);

	fprintf(stdout, "Destroying the list\n");
	list_destroy(&list);

	return 0;
}
Ejemplo n.º 8
0
/* 入队 */
int queue_enqueue(Queue *queue, const void *data) {
  /* 插入尾部 */
  return list_ins_next(queue, list_tail(queue), data);
}
Ejemplo n.º 9
0
int queue_enqueue(Queue *queue, const void *data)
{
	// enqueue the data

	return list_ins_next(queue, list_tail(queue), data);
}
Ejemplo n.º 10
0
/* queue push */
int queue_push(Queue *queue, void *data)
{
    return list_ins_next(queue, list_tail(queue), data);
}
Ejemplo n.º 11
0
int main(int argc, char **argv) {

	List               list;
	ListElmt           *element;

	int                *data,
					   i;

	/*****************************************************************************
	*                                                                            *
	*  Initialize the linked list.                                               *
	*                                                                            *
	*****************************************************************************/

	list_init(&list, free);

	/*****************************************************************************
	*                                                                            *
	*  Perform some linked list operations.                                      *
	*                                                                            *
	*****************************************************************************/

	element = list_head(&list);

	for (i = 10; i > 0; i--) {

	   if ((data = (int *)malloc(sizeof(int))) == NULL)
		  return 1;

	   *data = i;

	   if (list_ins_next(&list, NULL, data) != 0)
		  return 1;

	}

	print_list(&list);

	element = list_head(&list);

	for (i = 0; i < 7; i++)
	   element = list_next(element);

	data = list_data(element);
	fprintf(stdout, "Removing an element after the one containing %03d\n", *data);

	if (list_rem_next(&list, element, (void **)&data) != 0)
	   return 1;

	print_list(&list);

	fprintf(stdout, "Inserting 011 at the tail of the list\n");

	*data = 11;
	if (list_ins_next(&list, list_tail(&list), data) != 0)
	   return 1;

	print_list(&list);

	fprintf(stdout, "Removing an element after the first element\n");

	element = list_head(&list);
	if (list_rem_next(&list, element, (void **)&data) != 0)
	   return 1;

	print_list(&list);

	fprintf(stdout, "Inserting 012 at the head of the list\n");

	*data = 12;
	if (list_ins_next(&list, NULL, data) != 0)
	   return 1;

	print_list(&list);

	fprintf(stdout, "Iterating and removing the fourth element\n");

	element = list_head(&list);
	element = list_next(element);
	element = list_next(element);

	if (list_rem_next(&list, element, (void **)&data) != 0)
	   return 1;

	print_list(&list);

	fprintf(stdout, "Inserting 013 after the first element\n");

	*data = 13;
	if (list_ins_next(&list, list_head(&list), data) != 0)
	   return 1;

	print_list(&list);

	i = list_is_head(&list, list_head(&list));
	fprintf(stdout, "Testing list_is_head...Value=%d (1=OK)\n", i);
	i = list_is_head(&list, list_tail(&list));
	fprintf(stdout, "Testing list_is_head...Value=%d (0=OK)\n", i);
	i = list_is_tail(list_tail(&list));
	fprintf(stdout, "Testing list_is_tail...Value=%d (1=OK)\n", i);
	i = list_is_tail(list_head(&list));
	fprintf(stdout, "Testing list_is_tail...Value=%d (0=OK)\n", i);

	/*****************************************************************************
	*                                                                            *
	*  Destroy the linked list.                                                  *
	*                                                                            *
	*****************************************************************************/

	fprintf(stdout, "Destroying the list\n");
	list_destroy(&list);

	return 0;

}
Ejemplo n.º 12
0
int set_insert(Set *set, const void *data)
{
	if (set_is_member(set, data))
		return 1;
	return list_ins_next(set, list_tail(set), data);
}
Ejemplo n.º 13
0
Archivo: network.c Proyecto: hgn/ospfd
static int get_interface_addr(struct ospfd *ospfd)
{
	int ret;
	struct ifaddrs *ifaddr;

	/* First of all: remove all entries if any is available.
	 * This makes this method re-callable to refresh the interface address
	 * status.  */
	list_destroy(ospfd->network.rd_list);
	ospfd->network.rd_list = list_create(list_cmp_rd, list_free_rd);

	ret = getifaddrs(&ifaddr);
	if (ret < 0) {
		err_sys("failed to query interface addresses");
		return FAILURE;
	}

	while (ifaddr != NULL) {

		struct rd *rd;
		struct ip_addr *ip_addr;
		struct sockaddr_in *in4;
		struct sockaddr_in6 *in6;

		if (!ifaddr->ifa_addr)
			goto next;

		switch (ifaddr->ifa_addr->sa_family) { /* only IPv{4,6} */
			case AF_INET:
			case AF_INET6:
				break;
			default:
				goto next;
				break;
		}

		/* We know it is a IPv4 or IPv6 address.
		 * Now we search the routing domain list for
		 * this interface. If we found is we add the new
		 * IP address, if not we add a new routing domain
		 * and also add the IP address */
		rd = list_lookup_match(ospfd->network.rd_list, ifname_cmp, ifaddr->ifa_name);
		if (rd == NULL) { /* new interface ... */
			rd = xzalloc(sizeof(struct rd));
			ret = list_ins_next(ospfd->network.rd_list, NULL, rd);
			if (ret != SUCCESS) {
				fprintf(stderr, "Failure in inserting rd\n");
				abort();
			}
			memcpy(rd->if_name, ifaddr->ifa_name,
					min((strlen(ifaddr->ifa_name) + 1), sizeof(rd->if_name)));
			rd->if_flags  = ifaddr->ifa_flags; /* see netdevice(7) for list of flags */
			rd->ip_addr_list = list_create(list_cmp_struct_ip_addr, free_ip_addr);
		}

		/* interface specific setup is fine, we can
		 * now carelessly add the new ip address to
		 * the interface */

		ip_addr = xzalloc(sizeof(struct ip_addr));
		ip_addr->family = ifaddr->ifa_addr->sa_family;
		switch (ip_addr->family) {
			case AF_INET:
				/* copy address */
				in4 = (struct sockaddr_in *)ifaddr->ifa_addr;
				memcpy(&ip_addr->ipv4.addr, &in4->sin_addr, sizeof(ip_addr->ipv4.addr));
				/* copy netmask */
				in4 = (struct sockaddr_in *)ifaddr->ifa_netmask;
				memcpy(&ip_addr->ipv4.netmask, &in4->sin_addr, sizeof(ip_addr->ipv4.netmask));
				/* copy broadcast */
				in4 = (struct sockaddr_in *)ifaddr->ifa_broadaddr;
				memcpy(&ip_addr->ipv4.broadcast, &in4->sin_addr, sizeof(ip_addr->ipv4.broadcast));
				break;
			case AF_INET6:
				/* copy address */
				in6 = (struct sockaddr_in6 *)ifaddr->ifa_addr;
				memcpy(&ip_addr->ipv6.addr, &in6->sin6_addr, sizeof(ip_addr->ipv6.addr));
				/* and scope too */
				ip_addr->ipv6.scope = in6->sin6_scope_id;
				/* copy netmask */
				in6 = (struct sockaddr_in6 *)ifaddr->ifa_netmask;
				memcpy(&ip_addr->ipv6.netmask, &in6->sin6_addr, sizeof(ip_addr->ipv6.netmask));
				break;
			default:
				err_msg("Programmed error - address (protocol) not supported: %d",
						ip_addr->family);
				return FAILURE;
				break;
		}

		/* and at the newly data at the end of the list */
		list_insert(rd->ip_addr_list, ip_addr);

next:
		ifaddr = ifaddr->ifa_next;

	}

	freeifaddrs(ifaddr);

#if 0
	list_for_each(ospfd->network.rd_list, print_all_interfaces);
#endif

	return SUCCESS;
}
Ejemplo n.º 14
0
void
resolve_symbols(int fd, list_t *list)
{
	int i, j;						/* loop counter 						*/
	int ret;						/* return value 						*/
	char *strings;				/* strtab entries 					*/
	char *string;				/* symbol table strtab entries 	*/
	Elf32_Sym *sym;			/* symbol entry 						*/
	Elf32_Sym *tmp_sym;		/* temporary symbol 					*/
	Elf32_Ehdr ehdr;			/* ELF header 							*/
	Elf32_Shdr *shdr;			/* section header 					*/
	Elf32_Shdr *strtab;		/* strtab section header 			*/
	Elf32_Shdr *tmp_shdr;	/* temporary section header 		*/
	Elf32_Shdr *text_shdr;	/* .text section header 			*/

	/*
	 * Read the ELF Header and display
	 */
	ret = read(fd, &ehdr, sizeof(ehdr));
	if(ret != sizeof(ehdr)) {
		perror("read");
		exit(-1);
	}

	/*
	 * Allocate memory for sections headers
	 */
	shdr = (Elf32_Shdr *) malloc(sizeof(Elf32_Shdr) * ehdr.e_shnum);
	if(!shdr) {
		perror("malloc");
		exit(-1);
	}

	ret = lseek(fd, ehdr.e_shoff, SEEK_SET);
	if(ret < 0) {
		perror("lseek");
		exit(-1);
	}

	ret = read(fd, shdr, sizeof(Elf32_Shdr) * ehdr.e_shnum);
	if(ret != sizeof(Elf32_Shdr) * ehdr.e_shnum) {
		perror("read");
		exit(-1);
	}

	/*
	 * Pull out the string table
	 */
   strtab = &shdr[ehdr.e_shstrndx];

	strings = (char *) malloc(strtab->sh_size);
	if(!strings) {
		perror("malloc");
		exit(-1);
	}

	ret = lseek(fd, strtab->sh_offset, SEEK_SET);
	if(ret < 0) {
		perror("lseek");
		exit(-1);
	}

	ret = read(fd, strings, strtab->sh_size);
	if(ret != strtab->sh_size) {
		perror("read");
		exit(-1);
	}

	/* 
	 * Iterate through sections headers, find symtab
	 */

	for(tmp_shdr = shdr, i = 0; i < ehdr.e_shnum; ++tmp_shdr, i++) {
		if(tmp_shdr->sh_type == SHT_SYMTAB) {

			Elf32_Shdr *strtab_hdr = &shdr[tmp_shdr->sh_link]; 
			
			string = (char *) malloc(strtab_hdr->sh_size);
			if(!string) {
				perror("malloc");
				exit(-1);
			}

			ret = lseek(fd, strtab_hdr->sh_offset, SEEK_SET);
			if(ret != strtab_hdr->sh_offset) {
				perror("lseek");
				exit(-1);
			}

			ret = read(fd, string, strtab_hdr->sh_size);
			if(ret != strtab_hdr->sh_size) {
				perror("read");
				exit(-1);
			}

			sym = (Elf32_Sym *) malloc(tmp_shdr->sh_size);
			if(!sym) {
				perror("malloc");
				exit(-1);
			}

			ret = lseek(fd, tmp_shdr->sh_offset, SEEK_SET);
			if(ret != tmp_shdr->sh_offset) {
				perror("lseek");
				exit(-1);
			}

			ret = read(fd, sym, tmp_shdr->sh_size);
			if(ret != tmp_shdr->sh_size) {
				perror("read");
				exit(-1);
			}

			for(tmp_sym = sym, j = 0; j < tmp_shdr->sh_size; j += sizeof(Elf32_Sym), ++tmp_sym) {
				text_shdr = &shdr[tmp_sym->st_shndx];

				if(tmp_sym->st_shndx > ehdr.e_shnum)
					continue;

				if(!strcmp(&strings[text_shdr->sh_name], ".text")) {
					bpx_t *bpx;

					if(strlen(&string[tmp_sym->st_name]) <= 0)
						continue;

					if(!tmp_sym->st_size)
						continue;

					bpx = (bpx_t *) malloc(sizeof(bpx_t));

					bpx->name = &string[tmp_sym->st_name];

					bpx->addr = tmp_sym->st_value;
					bpx->value = 0;

					list_ins_next(list, list_tail(list), bpx);
				}
			}

			break;
		}
	}
}
Ejemplo n.º 15
0
int queue_enqueue(Queue *queue, const void *data){
  return list_ins_next(queue, queue->tail, data);
}
Ejemplo n.º 16
0
void verifyInterSection(uint8_t** set,uint8_t** recved,int32_t setSize, List* L){
    
    int32_t* setC = setToInt(set, setSize);
    int32_t* setS= setToInt(recved, setSize);
    
    CHTbl htbl;
    
    intHash_init(&htbl, setSize);
    
    for(int i=0;i<setSize;i++){
        //printf("%d,%d\n",i,setC[i]);
        intHash_insert(&htbl, setC[i]);
    }
    
    List L2;
    list_init(&L2, &free);
    
    for(int i=0;i<setSize;i++){
        //in the intersection
        if(intHash_lookup(&htbl, setS[i])==0){
            list_ins_next(&L2, NULL, recved[i]);
        };
    }
    
    printf("size of L2=%d\n",list_size(&L2));
    printf("size of L1=%d\n",list_size(L));
    
    if(list_size(&L2)!=list_size(L)){
        printf("Incorrect intersection!\n");
        abort();
    }
    
    uint8_t** int1=(uint8_t**)calloc(list_size(L), sizeof(uint8_t*));
    uint8_t** int2=(uint8_t**)calloc(list_size(&L2), sizeof(uint8_t*));
    
    ListElmt * e1 = L->head;
    ListElmt * e2= L2.head;
    
    for(int i=0;i<list_size(&L2);i++){
        int1[i]=(uint8_t*)e1->data;
        int2[i]=(uint8_t*)e2->data;
        e1=e1->next;
        e2=e2->next;
    }
    
    
    for(int i=0;i<list_size(&L2);i++){
        if(!contains(int1,int2[i],list_size(&L2),defaultDatalen)){
            printf("Incorrect intersection!\n");
            //abort();
        }
    }
    
    printf("Intersection correct!\n");
    printf("Should contain:\n");
    for(int i=0;i<list_size(&L2);i++){
        printBytes(int2[i], defaultDatalen);
    }
    
    printf("Contains:\n");
    for(int i=0;i<list_size(&L2);i++){
        printBytes(int1[i], defaultDatalen);
    }
    
}
Ejemplo n.º 17
0
int bfs(Graph *graph, BfsVertex *start, List *hops) {

Queue              queue;

AdjList            *adjlist,
                   *clr_adjlist;

BfsVertex          *clr_vertex,
                   *adj_vertex;

ListElmt           *element,
                   *member;

/*****************************************************************************
*                                                                            *
*  Initialize all of the vertices in the graph.                              *
*                                                                            *
*****************************************************************************/

for (element = list_head(&graph_adjlists(graph)); element != NULL; element =
   list_next(element)) {

   clr_vertex = ((AdjList *)list_data(element))->vertex;

   if (graph->match(clr_vertex, start)) {

      /***********************************************************************
      *                                                                      *
      *  Initialize the start vertex.                                        *
      *                                                                      *
      ***********************************************************************/

      clr_vertex->color = gray;
      clr_vertex->hops = 0;

      }

   else {

      /***********************************************************************
      *                                                                      *
      *  Initialize vertices other than the start vertex.                    *
      *                                                                      *
      ***********************************************************************/

      clr_vertex->color = white;
      clr_vertex->hops = -1;

   }

}

/*****************************************************************************
*                                                                            *
*  Initialize the queue with the adjacency list of the start vertex.         *
*                                                                            *
*****************************************************************************/

queue_init(&queue, NULL);

if (graph_adjlist(graph, start, &clr_adjlist) != 0) {

   queue_destroy(&queue);
   return -1;

}

if (queue_enqueue(&queue, clr_adjlist) != 0) {

   queue_destroy(&queue);
   return -1;

}

/*****************************************************************************
*                                                                            *
*  Perform breadth-first search.                                             *
*                                                                            *
*****************************************************************************/

while (queue_size(&queue) > 0) {

   adjlist = queue_peek(&queue);

   /**************************************************************************
   *                                                                         *
   *  Traverse each vertex in the current adjacency list.                    *
   *                                                                         *
   **************************************************************************/

   for (member = list_head(&adjlist->adjacent); member != NULL; member =
      list_next(member)) {

      adj_vertex = list_data(member);

      /***********************************************************************
      *                                                                      *
      *  Determine the color of the next adjacent vertex.                    *
      *                                                                      *
      ***********************************************************************/

      if (graph_adjlist(graph, adj_vertex, &clr_adjlist) != 0) {

         queue_destroy(&queue);
         return -1;

      }

      clr_vertex = clr_adjlist->vertex;

      /***********************************************************************
      *                                                                      *
      *  Color each white vertex gray and enqueue its adjacency list.        *
      *                                                                      *
      ***********************************************************************/

      if (clr_vertex->color == white) {

         clr_vertex->color = gray;
         clr_vertex->hops = ((BfsVertex *)adjlist->vertex)->hops + 1;

         if (queue_enqueue(&queue, clr_adjlist) != 0) {

            queue_destroy(&queue);
            return -1;

         }

      }

   }

   /**************************************************************************
   *                                                                         *
   *  Dequeue the current adjacency list and color its vertex black.         *
   *                                                                         *
   **************************************************************************/

   if (queue_dequeue(&queue, (void **)&adjlist) == 0) {

      ((BfsVertex *)adjlist->vertex)->color = black;

      }

   else {

      queue_destroy(&queue);
      return -1;

   }

}

queue_destroy(&queue);

/*****************************************************************************
*                                                                            *
*  Pass back the hop count for each vertex in a list.                        *
*                                                                            *
*****************************************************************************/

list_init(hops, NULL);

for (element = list_head(&graph_adjlists(graph)); element != NULL; element =
   list_next(element)) {

   /**************************************************************************
   *                                                                         *
   *  Skip vertices that were not visited (those with hop counts of -1).     *
   *                                                                         *
   **************************************************************************/

   clr_vertex = ((AdjList *)list_data(element))->vertex;

   if (clr_vertex->hops != -1) {

      if (list_ins_next(hops, list_tail(hops), clr_vertex) != 0) {

         list_destroy(hops);
         return -1;

      }

   }

}

return 0;

}
Ejemplo n.º 18
0
int list_push_back(struct linked_list* list, const void* data) {
  return list_ins_next(list, list->tail, data);
}
Ejemplo n.º 19
0
/* this is O(1) but is included for convencience */
void list_append(List *list, void *data){
  ListElmt *node = list->tail;
  list_ins_next(list,list->tail,data);
  printf("new list size after append: %d\n", list->size);
  return;
}
Ejemplo n.º 20
0
Archivo: dfs.c Proyecto: whatot/ma_c
static int dfs_main(Graph * graph, AdjList * adjlist, List * ordered)
{

	AdjList *clr_adjlist;

	DfsVertex *clr_vertex, *adj_vertex;

	ListElmt *member;

/*****************************************************************************
*                                                                            *
*  Color the vertex gray and traverse its adjacency list.                    *
*                                                                            *
*****************************************************************************/

	((DfsVertex *) adjlist->vertex)->color = gray;

	for (member = list_head(&adjlist->adjacent); member != NULL; member =
	     list_next(member)) {

   /**************************************************************************
   *                                                                         *
   *  Determine the color of the next adjacent vertex.                       *
   *                                                                         *
   **************************************************************************/

		adj_vertex = list_data(member);

		if (graph_adjlist(graph, adj_vertex, &clr_adjlist) != 0)
			return -1;

		clr_vertex = clr_adjlist->vertex;

   /**************************************************************************
   *                                                                         *
   *  Move one vertex deeper when the next adjacent vertex is white.         *
   *                                                                         *
   **************************************************************************/

		if (clr_vertex->color == white) {

			if (dfs_main(graph, clr_adjlist, ordered) != 0)
				return -1;

		}

	}

/*****************************************************************************
*                                                                            *
*  Color the current vertex black and make it first in the list.             *
*                                                                            *
*****************************************************************************/

	((DfsVertex *) adjlist->vertex)->color = black;

	if (list_ins_next(ordered, NULL, (DfsVertex *) adjlist->vertex) != 0)
		return -1;

	return 0;

}
Ejemplo n.º 21
0
int stack_push (Stack *stack, const void *data)
{
  /* Push the data onto the stack.  */
  return list_ins_next (stack, NULL, data);
}
Ejemplo n.º 22
0
/*--------------------------------------------------------------*/
int shortest(Graph *graph, Heap *H, double *A_weights, const PathVertex *start, List *paths, int (*match)
   (const void *key1, const void *key2), int gw, int gh) {

AdjList            *adjlist;

PathVertex         *pth_vertex,
                   *adj_vertex;

ListElmt           *element,
                   *member;

int                found,
                   i;


/*PairHeap			H;
Position			*P;	*/

/*Heap				*H;				*/	/* A_weights binary heap, used for priority queue */
/*double				*A_weights;	*/		/* array of weights to be min-heapified */

CoordData			Index2Coord[(gw*gh*2)+1];
int					Coord2Index[gw][gh][2];

int					index;
AdjList				*Coord2Vertex[gw][gh][2];


/*****************************************************************************
*                                                                            *
*  Initialize all of the vertices in the graph.                              *
*                                                                            *
*****************************************************************************/

found = 0;
index = 1;

for (element = list_head(&graph_adjlists(graph)); element != NULL; element =
   list_next(element)) {

   pth_vertex = ((AdjList *)list_data(element))->vertex;
   

   if (match(pth_vertex, start)) {
	   short   int x,y,z;

      /***********************************************************************
      *                                                                      *
      *  Initialize the start vertex.                                        *
      *                                                                      *
      ***********************************************************************/

	   x = ((CoordData*)((PathVertex*)pth_vertex)->data)->x;
	   y = ((CoordData*)((PathVertex*)pth_vertex)->data)->y;
	   z = ((CoordData*)((PathVertex*)pth_vertex)->data)->z;
	   Coord2Vertex[x][y][z] = list_data(element);
	   
	   
	  pth_vertex->color = white;
      pth_vertex->d = 0;
      pth_vertex->parent = NULL;
      found = 1;
	  

	  A_weights[index] = pth_vertex->d;

	  Coord2Index[x][y][z] = index;
	  Index2Coord[index].x = x;
	  Index2Coord[index].y = y;
	  Index2Coord[index].z = z;
	  index++;

      }

   else {
	   short   int x,y,z;

      /***********************************************************************
      *                                                                      *
      *  Initialize vertices other than the start vertex.                    *
      *                                                                      *
      ***********************************************************************/

	   x = ((CoordData*)((PathVertex*)pth_vertex)->data)->x;
	   y = ((CoordData*)((PathVertex*)pth_vertex)->data)->y;
	   z = ((CoordData*)((PathVertex*)pth_vertex)->data)->z;
	   Coord2Vertex[x][y][z] = list_data(element);

	   
	   
      pth_vertex->color = white;
      pth_vertex->d = DBL_MAX;
      pth_vertex->parent = NULL;

	  A_weights[index] = pth_vertex->d;
	  
	  Coord2Index[x][y][z] = index;
	  Index2Coord[index].x = x;
	  Index2Coord[index].y = y;
	  Index2Coord[index].z = z;
	  index++;


   }
}

/*****************************************************************************
*                                                                            *
*  Return if the start vertex was not found.                                 *
*                                                                            *
*****************************************************************************/

if (!found)
   return -1;


binheap_build(H,A_weights,gw*gh*2);		/* build the heap */

/*****************************************************************************
*                                                                            *
*  Use Dijkstra's algorithm to compute shortest paths from the start vertex. *
*                                                                            *
*****************************************************************************/

i = 0;

while (i < graph_vcount(graph)) {
	short   int x,y,z;

   /**************************************************************************
   *                                                                         *
   *  Select the white vertex with the smallest shortest-path estimate.      *
   *                                                                         *
   **************************************************************************/


	index = binheap_indexofmin(H);			/* get index of minimum-weight edge */
	binheap_extract(H);						/* remove it from the heap */
	
	x = Index2Coord[index].x;
	y = Index2Coord[index].y;
	z = Index2Coord[index].z;
	adjlist = Coord2Vertex[x][y][z];
	
	/**************************************************************************
   *                                                                         *
   *  Color the selected vertex black.                                       *
   *                                                                         *
   **************************************************************************/

   ((PathVertex *)adjlist->vertex)->color = black;
	

   /**************************************************************************
   *                                                                         *
   *  Traverse each vertex adjacent to the selected vertex.                  *
   *                                                                         *
   **************************************************************************/

   for (member = list_head(&adjlist->adjacent); member != NULL; member =
      list_next(member)) {
	   short   int		px,py,pz;

      adj_vertex = list_data(member);
	  
	  px = ((CoordData*)((PathVertex*)adj_vertex)->data)->x;
	  py = ((CoordData*)((PathVertex*)adj_vertex)->data)->y;
	  pz = ((CoordData*)((PathVertex*)adj_vertex)->data)->z;

      /***********************************************************************
      *                                                                      *
      *  Find the adjacent vertex in the list of adjacency-list structures.  *
      *                                                                      *
      ***********************************************************************/
	   
	  pth_vertex = ((AdjList*)Coord2Vertex[px][py][pz])->vertex;
					
	  /*****************************************************************
	  *                                                                *
	  *  Relax the adjacent vertex in the list of adjacency-list       *
	  *  structures.                                                   *
	  *                                                                *
	  *****************************************************************/

	  if (relax(adjlist->vertex, pth_vertex, adj_vertex->weight)) {
		  
		  /* update pth_vertex->d in FH */
		  binheap_decrease_key(H, Coord2Index[px][py][pz] , pth_vertex->d);
		}
   }

   /**************************************************************************
   *                                                                         *
   *  Prepare to select the next vertex.                                     *
   *                                                                         *
   **************************************************************************/

   i++;

}

/* destroy binary heap */
/*binheap_destroy(H);*/
/*free(A_weights);*/

/*****************************************************************************
*                                                                            *
*  Load the vertices with their path information into a list.                *
*                                                                            *
*****************************************************************************/


list_init(paths, NULL);

for (element = list_head(&graph_adjlists(graph)); element != NULL; element =
   list_next(element)) {

   /**************************************************************************
   *                                                                         *
   *  Load each black vertex from the list of adjacency-list structures.     *
   *                                                                         *
   **************************************************************************/

   pth_vertex = ((AdjList *)list_data(element))->vertex;

   if (pth_vertex->color == black) {

      if (list_ins_next(paths, list_tail(paths), pth_vertex) != 0) {
         printf("Problem inserting!\n");
         list_destroy(paths);
         return -1;
      }
   }
}

return 0;

}
Ejemplo n.º 23
0
Archivo: mst.c Proyecto: rjose/products
int mst(Graph *graph, const MstVertex *start, List *span,
                               int (*match)(const void *key1, const void *key2))
{
        AdjList *adjlist = NULL;

        MstVertex *mst_vertex, *adj_vertex;

        ListElmt *element, *member;

        double minimum;

        int found, i;

        found = 0;

        for (element = list_head(&graph_adjlists(graph)); element != NULL;
                                                 element = list_next(element)) {
                mst_vertex = ((AdjList *)list_data(element))->vertex;

                if (match(mst_vertex, start)) {
                        mst_vertex->color = white;
                        mst_vertex->key = 0;
                        mst_vertex->parent = NULL;
                        found = 1;
                }
                else {
                        mst_vertex->color = white;
                        mst_vertex->key = DBL_MAX;
                        mst_vertex->parent = NULL;
                }
        } 

        if (!found)
                return -1;

        /*
         * Use Prim's algorithm
         */
        i = 0;

        /* Select white vertex with the smallest value */
        while (i < graph_vcount(graph)) {
                minimum = DBL_MAX;

                for (element = list_head(&graph_adjlists(graph));
                                element != NULL; element = list_next(element)) {
                        mst_vertex = ((AdjList *)list_data(element))->vertex;

                        if (mst_vertex->color == white &&
                                                    mst_vertex->key < minimum) {
                                minimum = mst_vertex->key;
                                adjlist = list_data(element);
                        }
                }

                /* Color the selected vertex black */
                ((MstVertex *)adjlist->vertex)->color = black;

                for (member = list_head(&adjlist->adjacent); member != NULL;
                                                   member = list_next(member)) {
                        adj_vertex = list_data(member);

                        for(element = list_head(&graph_adjlists(graph));
                                element != NULL; element = list_next(element)) {
                                mst_vertex = ((AdjList *)list_data(element))->vertex;

                                if (match(mst_vertex, adj_vertex)) {
                                        if (mst_vertex->color == white &&
                                          adj_vertex->weight < mst_vertex->key) {
                                           mst_vertex->key = adj_vertex->weight;
                                           mst_vertex->parent = adjlist->vertex;
                                        }
                                        break;
                                }
                        }

                }

                i++;
        }

        list_init(span, NULL);

        for (element = list_head(&graph_adjlists(graph)); element != NULL;
                                                 element = list_next(element)) {
                mst_vertex = ((AdjList *)list_data(element))->vertex;
                if (mst_vertex->color == black) {
                        if (list_ins_next(span, list_tail(span), mst_vertex)
                                                                         != 0) {
                                list_destroy(span);
                                return -1;
                        }
                }
        }

        return 0;
}
Ejemplo n.º 24
0
Archivo: mst.c Proyecto: whatot/ma_c
/* mst */
int mst(Graph *graph, const MstVertex *start, List *span,
	int (*match)(const void *key1, const void *key2))
{
	AdjList *adjlist;
	MstVertex *mst_vertex, *adj_vertex;
	ListElmt *element, *member;
	double minimum;
	int found, i;

	/* Initialize all of the vertices in the graph. */
	found = 0;

	for (element = list_head(&graph_adjlists(graph));
	     element != NULL; element = list_next(element)) {
		mst_vertex = ((AdjList *)list_data(element))->vertex;

		if (match(mst_vertex, start)) {
			/* Initialize the start vertex. */
			mst_vertex->color = white;
			mst_vertex->key = 0;
			mst_vertex->parent = NULL;
			found = 1;
		} else {
			/* Initialize vertices other than the start vertex. */
			mst_vertex->color = white;
			mst_vertex->key = DBL_MAX;
			mst_vertex->parent = NULL;
		}
	}
	/* Return if the start vertex was not found. */
	if (!found) {
		return -1;
	}

	/* Use Prim's algorithm to compute a minimum spanning tree. */
	i = 0;

	while (i < graph_vcount(graph)) {
		/* Select the white vertex with the smallest key value. */
		minimum = DBL_MAX;

		for (element = list_head(&graph_adjlists(graph));
		     element != NULL; element = list_next(element)) {
			mst_vertex = ((AdjList *)list_data(element))->vertex;

			if (mst_vertex->color == white
			    && mst_vertex->key < minimum) {
				minimum = mst_vertex->key;
				adjlist = list_data(element);
			}
		}
		/* color the selected vertex black. */
		((MstVertex *)adjlist->vertex)->color = black;

		/* traverse each vertex adjacent to the selected vertex. */
		for (member = list_head(&adjlist->adjacent);
		     member != NULL; member = list_next(member)) {
			adj_vertex = list_data(member);

			/* Find the adjacent vertex in the list of
			 * adjacency-list structures. */
			for (element = list_head(&graph_adjlists(graph));
			     element != NULL; element = list_next(element)) {
				mst_vertex = ((AdjList *)
					      list_data(element))->vertex;

				if (match(mst_vertex, adj_vertex)) {
					/* decide whether to change the key
					 * value and parent of the adjacent
					 * vertex in the list of
					 * adjacency-list structures.*/
					if (mst_vertex->color == white
					    && adj_vertex->weight
						< mst_vertex->key) {

						mst_vertex->key
							= adj_vertex->weight;
						mst_vertex->parent
							= adjlist->vertex;
					}
					break;
				}
			}
		}
		/* prepare to select the next vertex. */
		i++;
	}

	/* Load the minimum spanning tree into a list. */
	list_init(span, NULL);

	for (element = list_head(&graph_adjlists(graph));
	     element != NULL ; element = list_next(element)) {
		/* Load each black vertex from the list of
		 * adjacency-list structures. */
		mst_vertex = ((AdjList *)list_data(element))->vertex;

		if (mst_vertex->color == black) {
			if (list_ins_next(span, list_tail(span),
					  mst_vertex) != 0) {
				list_destroy(span);
				return -1;
			}
		}
	}

	return 0;
}
Ejemplo n.º 25
0
/*--------------------------------------------------------------*/
void SPElement2sPath(SPElement *path, List *sPath, CoordData *start) {
	int			s,p,v;			/* "pointers" to vertices in path */
	sPathData 	*newElement;	
	CoordData	*vCoord,*pCoord;
	int 		done;
	
	
	list_init(sPath, (void*)sPath_vertex_free);
	
	/* find end vertex in path (root of list, parent == -1) */
	s = 0;
	while ( path[s].parent != -1 )
		s++;
	
	
	/* find startd vertex in path */
	v = 0;
	while (!(( path[v].c.x == start->x )&&( path[v].c.y == start->y )&&( path[v].c.z == start->z )))
		v++;
		
	p = path[v].parent;
	
	done = 0;	
	/* follow v back to root (when v == s) */
	while (!done) {	
		
		/* allocate some memory */
		newElement = (sPathData*) malloc(sizeof(sPathData));
		vCoord = (CoordData*) malloc(sizeof(CoordData));
		pCoord = (CoordData*) malloc(sizeof(CoordData));
		
		if ((newElement == NULL)||(vCoord == NULL)||(pCoord == NULL)) {
			printf("shortest.c : mem allocation error\n");
			fflush(stdout);
			exit(1);
		}
		
		/* set current vertex coords */
		vCoord->x = path[v].c.x;
		vCoord->y = path[v].c.y;
		vCoord->z = path[v].c.z;
		
		/* set parent vertex coords */
		pCoord->x = path[p].c.x;
		pCoord->y = path[p].c.y;
		pCoord->z = path[p].c.z;
		
		/* set the new element to list */
		newElement->vertex = vCoord;
		newElement->parent = pCoord;
		newElement->d = path[v].d;
		
		/* insert the element into the list */
		if (list_ins_next(sPath, list_tail(sPath), newElement) != 0) {
			printf("Problem inserting into sPath!\n");
			list_destroy(sPath);
			exit(1);
		}
		
		
		/* next vertex */
		if (path[p].parent == -1) {
			done = 1;
			
			/*insert one more element starting with parent */
			newElement = (sPathData*) malloc(sizeof(sPathData));
			vCoord = (CoordData*) malloc(sizeof(CoordData));
			
			if ((newElement==NULL)||(vCoord==NULL)) {
				printf("helper.c : memory allocation error\n");
				fflush(stdout);
				exit(1);
			}
			vCoord->x = path[p].c.x;
			vCoord->y = path[p].c.y;
			vCoord->z = path[p].c.z;
			newElement->vertex = vCoord;
			newElement->parent = NULL;
			newElement->d = 0;
			
			if (list_ins_next(sPath, list_tail(sPath), newElement) != 0){
				printf("Problem inserting into sPath!\n");
				list_destroy(sPath);
				exit(1);
			}
		}
		else {
			v = p;
			p = path[p].parent;
		}
	}
	
}
Ejemplo n.º 26
0
int gridSteinerFH(Graph *grid_graph, AdjList**** Edge2Adj, int width, int height, CoordData *term, int no_terminals, double *L,int
	net_num, int *edge_count_OUT, int **SteinerTree_OUT, int l, int K) {
    int i,j;
	/* globals */
	
	int				GRID_WIDTH, GRID_HEIGHT, NO_TERMINALS;
	
	
	Graph			ND;					/* distance network of terminals */
	
	/*used to generate grid graph */
	PathVertex      *path_vertex;
	
	sPathData		*sPath_vertex;
	
	CoordData       *coord;
	
	/* used in shortest paths computations */
	PathVertex      **terminals;        /* a (1D) array of terminal (pointers) */
	List            *tempPaths,			/* tempporary */
					**sPaths;			/* 2d array of shortest path lists */
	ListElmt        *element;           /* temp, used to traverse a list */	
	
	/* used in computing MST of ND */
	MstVertex		*mst_start,
					*mst_vertex,
					*mst_vertex1,
					*mst_vertex2;
	List			TD;					/* spanning tree of ND */
										/* used in final steps of algorithm */
	
	Graph			NTD;				/* complete distance network */
	
	List			T;					/* spanning tree of NTD (eventually the steiner tree)*/
	int				isSteiner;			/* boolean flag */
	double			tree_cost;			/* total cost of the steiner tree (unused, this is computed after*/
	

			
	GRID_WIDTH = width;
	GRID_HEIGHT = height;
	NO_TERMINALS = no_terminals;
	
	mst_start = NULL;
	
	/*-----------------------------------------------*/
	/* If the number of terminals is two, then we    */
	/* only need to perform one call of Dijkstra to  */
	/* get the Steiner Tree                          */
	/*-----------------------------------------------*/
	if (NO_TERMINALS == 2) {
		PathVertex	*v1,*v2;	/* the two terminals*/
		CoordData	*c1,*c2;	/* coordinates of the two terminals*/
		List		P;			/* P-Array in Dijkstra's*/
		ListElmt	*e;			/* list counter*/
		List		T;			/* steiner tree*/
		double		tree_cost;
		int			j;
		int			first_edge,last_edge;
		
		PathVertex	*u;
			
		u = NULL;
	
		/* allocate vertices */
		v1 = (PathVertex*) malloc(sizeof(PathVertex));
		v2 = (PathVertex*) malloc(sizeof(PathVertex));
		c1 = (CoordData*) malloc(sizeof(CoordData));
		c2 = (CoordData*) malloc(sizeof(CoordData));		
		
		/* set terminal data */
		c1->x = term[0].x; 		c1->y = term[0].y;		c1->z = term[0].z;
		c2->x = term[1].x; 		c2->y = term[1].y;		c2->z = term[1].z;		
		v1->data = c1;
		v2->data = c2;
		
		/* compute shortest path from v1 */
		if (shortest(grid_graph, v1 , &P, match_coord,GRID_WIDTH,GRID_HEIGHT) != 0)
			return 1;

		/* initialize the tree */
		list_init(&T,NULL);
		
		/* find the end vertex (v2)*/
		for (e = list_head(&P); e != NULL; e = list_next(e)) 
			if ( match_coord(v2,list_data(e)))
				u = (PathVertex*)list_data(e);
		
		
		first_edge = 1;
		last_edge = 0;
		/* follow the end vertex back to the start vertex*/
		while (u->parent != NULL) {
			int			ux,uy,uz,upx,upy,upz;
			AdjList		*a;
			ListElmt	*ee;
			
			/*current vertex*/
			ux = ((CoordData*)((PathVertex*)u)->data)->x;
			uy = ((CoordData*)((PathVertex*)u)->data)->y;
			uz = ((CoordData*)((PathVertex*)u)->data)->z;
			
			/*connecting vertex (parent)*/
			upx = ((CoordData*)((PathVertex*)u->parent)->data)->x;
			upy = ((CoordData*)((PathVertex*)u->parent)->data)->y;
			upz = ((CoordData*)((PathVertex*)u->parent)->data)->z;
			
			
			/* get the index of the edge that connects (ux,uy,uz) and its parent*/
			a = Edge2Adj[ux][uy][uz];
			for (ee = list_head(&a->adjacent); ee != NULL; ee = list_next(ee)) {
				PathVertex	*v;
				int			*i;
				int			vx,vy,vz;
				
				v = (PathVertex*)list_data(ee);
				vx = ((CoordData*)v->data)->x;
				vy = ((CoordData*)v->data)->y;
				vz = ((CoordData*)v->data)->z;
				
				/* found it*/
				if (( vx == upx ) && ( vy == upy ) && ( vz == upz )) {
					
					/*don't insert if its a via*/
					if (first_edge) {
						first_edge = 0;
						if (v->index > ((grid_graph->ecount / 2) - (grid_graph->vcount/2)))
							continue;
					}
						
					/*check if its the last edge*/
					if (u->parent != NULL)
						if (u->parent->parent == NULL)
							last_edge = 1;
							
					/* don't insert if its a via*/
					if (last_edge)
						if (v->index > ((grid_graph->ecount / 2) - (grid_graph->vcount/2)))
							continue;
					
					i = (int*) malloc(sizeof(int));
					tree_cost += v->weight;
					*i = v->index;
					list_ins_next(&T, list_tail(&T),i);
				}
			}
			
			/* next */
			u = u->parent;
		}
		
		/* count total edges*/
		*edge_count_OUT = list_size(&T);

		/* write the solution (including vias)*/
		if ((*(SteinerTree_OUT) = (int*) malloc(sizeof(int)*(list_size(&T))))==NULL) {
			printf("gsFH.h : SteinerTree_OUT mem allocation error\n");
			fflush(stdout);
			exit(1);
		}
		
		e = list_head(&T);
		for (j = 0; ((j < list_size(&T))&&(e!=NULL)); j++,e=list_next(e)) 
			(*SteinerTree_OUT)[j] = *((int*)list_data(e));
		
		
		/* free up some temps*/
		free(v1->data); free(v1);
		free(v2->data); free(v2);
		list_destroy(&P);
		list_destroy(&T);
		
		return 0;
	}
	
	/*--------------------------------------------------------*/
	/* General case of 3 or more terminals begins here.  The  */
	/* above code for 2 terminals or less can be removed      */
	/* without affecting the block solution.   However, it is */
	/* faster with the special case                           */
	/*--------------------------------------------------------*/	
	
	/* Create Path Vertices out of the original terminal set */
	if ((terminals = (PathVertex**) malloc(sizeof(PathVertex*)*NO_TERMINALS))==NULL) {
		printf("gsFH.h : terminals mem allocation error\n");
		fflush(stdout);
		exit(1);
	}	
	for (i = 0; i < NO_TERMINALS; i++) {
		int x,y,z;
		
		x = term[i].x;
		y = term[i].y;
		z = term[i].z;
		
		path_vertex = (PathVertex*) malloc(sizeof(PathVertex));
		coord = (CoordData*) malloc(sizeof(CoordData));
		
		if ((path_vertex == NULL)||(coord == NULL)) {
			printf("gsFH.h : terminal[i] mem allocation error\n");
			fflush(stdout);
			exit(1);
		}

		
		coord->x = x;
		coord->y = y;
		coord->z = z;
		path_vertex->data = coord;
		
		terminals[i] = path_vertex;
	}

    

	/* inialize an array of list pointers used in extracting shortest paths from Dijkstra */
	sPaths = (List**) malloc(sizeof(List*)*NO_TERMINALS);
	if (sPaths == NULL) {
		printf("gsFH.h : sPaths mem allocation error\n");
		fflush(stdout);
		exit(1);
	}
	if ((tempPaths = (List*) malloc(sizeof(List)*NO_TERMINALS))==NULL) {
		printf("gsFH.h : tempPaths mem allocation error\n");
		fflush(stdout);
		exit(1);
	}	
	for (i = 0; i < NO_TERMINALS; i++)
		if ((sPaths[i] = (List*) malloc(sizeof(List)*NO_TERMINALS))==NULL) {
			printf("gsFH.h : sPaths[i] mem allocation error\n");
			fflush(stdout);
			exit(1);
		}



    
    /*--------------------------------------------------------------------------------------*/
    /*                          COMPUTE THE SHORTEST PATHS                                  */
    /*  Shortest paths are computed using O(EV^2) version of Dijkstras Algorithm            */
    /*--------------------------------------------------------------------------------------*/
    
	
    
    /* for each terminal (stored as a path vertex), find the shortest path   */
    /* The shortest path for terminal[i] is stored in the List pointed to by */
    /* paths[i].                                                             */

	for (i = 0; i < NO_TERMINALS; i++) {
		
		if (shortest(grid_graph, terminals[i], &tempPaths[i], match_coord,GRID_WIDTH,GRID_HEIGHT) != 0)
			return 1;
		
		/* copy out the shortest path data, if we don't do this, it will get overwritten*/
		for (j = 0; j < NO_TERMINALS; j++) 
			if (i != j)
				copy_sPath(&tempPaths[i], &(sPaths[i][j]), (CoordData*)((PathVertex*)terminals[j])->data);
	}
			
	
			


	/*--------------------------------------------------------------------------------------------------*/
	/*                Generate complete distance network ND												*/
	/*--------------------------------------------------------------------------------------------------*/

	/* initialize the graph */
	graph_init(&ND, match_coord, (void*)mst_vertex_free);
	
	/* insert the verticies.  Verticies consist of all the terminals */
	for (i = 0; i < NO_TERMINALS; i++) {
		
		/* allocate space for a MST vertex */
		if ((mst_vertex = (MstVertex*) malloc(sizeof(MstVertex))) == NULL) {
			printf("Error allocating space for mst_vertex\n");
			printf("Terminating..\n");
			return 1;
		}
		
		/* if it's the first, make it the start.  It doesn't matter which one is the start */
		if (i == 1)
			mst_start = mst_vertex;
		
		/* set the data */
		if ((coord = (CoordData*) malloc(sizeof(CoordData)))==NULL) {
			printf("gsFH.h : coord mem allocation error\n");
			fflush(stdout);
			exit(1);
		}

		coord->x = ((CoordData*)(((PathVertex*)terminals[i])->data))->x;
		coord->y = ((CoordData*)(((PathVertex*)terminals[i])->data))->y;
		coord->z = ((CoordData*)(((PathVertex*)terminals[i])->data))->z;
		mst_vertex->data = coord;
		
		/* insert */
		if (graph_ins_vertex(&ND, mst_vertex) != 0) {
			printf("Error inserting vertex into mst_graph\n");
			printf("Terminating...\n");
			return 1;
		}
	}

	/*	now we must insert the edges into the distance network graph ND.  We do this by accessing the
		shortest path lists (sPath) computed in the previous step */
	for (i = 0; i < NO_TERMINALS; i++) {
		int ux,uy,uz;
		
		ux = ((CoordData*)((PathVertex*)terminals[i])->data)->x;
		uy = ((CoordData*)((PathVertex*)terminals[i])->data)->y;		
		uz = ((CoordData*)((PathVertex*)terminals[i])->data)->z;
				
		for (j = 0; j < NO_TERMINALS; j++) {
			int vx,vy,vz;
			
			/* shouldn't be an edge from a terminal to itself */
			if (i != j) {
				double weight;
				CoordData *v1,*v2;
				int eCode;
			
				vx = ((CoordData*)((PathVertex*)terminals[j])->data)->x;
				vy = ((CoordData*)((PathVertex*)terminals[j])->data)->y;
				vz = ((CoordData*)((PathVertex*)terminals[j])->data)->z;
				
			
				/* now we must find how far away vx is from vy.   we do this by looking
					for at the head element in sPath[i][j] */
				
				element = list_head(&(sPaths[i][j]));
				sPath_vertex = list_data(element);
				weight = ((sPathData*)sPath_vertex)->d;
				
				/* allocate an edge */				
				if ((v1 = (CoordData*) malloc(sizeof(CoordData))) == NULL) {
					printf("gsFH.h : v1 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				if ((v2 = (CoordData*) malloc(sizeof(CoordData))) == NULL) {
					printf("gsFH.h : v2 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				
				v1->x = ux;
				v1->y = uy;
				v1->z = uz;
				
				v2->x = vx;
				v2->y = vy;
				v2->z = vz;
				
				if ((mst_vertex1 = (MstVertex*) malloc(sizeof(MstVertex))) == NULL) {
					printf("gsFH.h : mst_vertex1 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
								
				if ((mst_vertex2 = (MstVertex*) malloc(sizeof(MstVertex))) == NULL) {
					printf("gsFH.h : mst_vertex2 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				mst_vertex1->data =v1;
				mst_vertex2->data = v2;
				mst_vertex2->weight = weight;
				
				if ((eCode = graph_ins_edge(&ND, mst_vertex1, mst_vertex2)) != 0) {
					printf("Error inserting edge into ND\n");
					printf("graph_ins_edge returned the value %d\n",eCode);
					return 1;
				}
				
				free(mst_vertex1->data);
				free(mst_vertex1);
				
			}/* endif i!=j */
		}/* endfor j */
	}/* endfor i */

/*--------------------------------------------------------------------------------------------------*/
/*		Copmute TD (Min Span Tree of ND)						    */
/*--------------------------------------------------------------------------------------------------*/

	if (mst(&ND, mst_start,&TD, match_coord) != 0) {
		printf("Error computing minimum spanning tree\n");
		return 1;
	}	
	
	/* set leaves */
	
	/* initialize */
	for ( element = list_head(&TD); element != NULL; element = list_next(element))
	{
	   mst_vertex = list_data(element);
	   mst_vertex->is_leaf = 1;
    }
    
    /* for each node, set the parent is_leaf to 0.   Then, all leaves will remain */
    for (element = list_head(&TD); element != NULL; element = list_next(element))
    {
        mst_vertex = list_data(element);
        
        if (mst_vertex->parent != NULL)
            mst_vertex->parent->is_leaf = 0;
    }
	

/*--------------------------------------------------------------------------------------------------*/
/*	         Find N[TD]									    */
/*--------------------------------------------------------------------------------------------------*/
	
	graph_init(&NTD,match_coord,(void*)mst_vertex_free);


    /* for each edge in TD */
	for (element = list_head(&TD); element != NULL; element = list_next(element)) {
		MstVertex	*nextVertex;
		int			v,p;

		p = -1;
		v = -1;

		nextVertex = list_data(element);
		
		/* if it is not the root */
		if (nextVertex->parent != NULL) {
			int vx,vy,vz,px,py,pz;
			ListElmt	*currentV, *nextV;
			int			done;
			
			
			vx = ((CoordData*)((MstVertex*)nextVertex)->data)->x;
			vy = ((CoordData*)((MstVertex*)nextVertex)->data)->y;
			vz = ((CoordData*)((MstVertex*)nextVertex)->data)->z;
			
			px = ((CoordData*)(MstVertex*)(nextVertex->parent)->data)->x;
			py = ((CoordData*)(MstVertex*)(nextVertex->parent)->data)->y;			
			pz = ((CoordData*)(MstVertex*)(nextVertex->parent)->data)->z;
			
			/* find terminal index of nextVertex and nextVertex->parent */
			for (i = 0; i < NO_TERMINALS; i++) {
				int tx,ty,tz;
				
				tx = ((CoordData*)((PathVertex*)terminals[i])->data)->x;
				ty = ((CoordData*)((PathVertex*)terminals[i])->data)->y;
				tz = ((CoordData*)((PathVertex*)terminals[i])->data)->z;
				
				if ((tx == vx)&&(ty == vy)&&(tz == vz))
					v = i;
				
				if ((tx == px)&&(ty == py)&&(tz == pz))
					p = i;
			}
			
			/* now, we must step through the list of sPathData elements found in sPaths[p][v].
			   For each element in the list, we must insert vertices for the vertex and parent, 
				then make an edge with the appropriate weight and insert it */
			
			currentV = list_head(&(sPaths[p][v]));
			nextV = list_next(currentV);
			done = 0;
			while ( !done ) {
				MstVertex	*u,*v, *mst_vertex1, *mst_vertex2;
				CoordData	*uc,*vc;
				sPathData	*currentVData, *nextVData;
				int			cvx,cvy,cvz,nvx,nvy,nvz;
				double		weight;

				/*---------------------------------------*/
				/* insert vertices u and v into NTD      */
				/*---------------------------------------*/
				
				/* make a vertex for currentV and nextV */
				u = (MstVertex*) malloc(sizeof(MstVertex));
				v = (MstVertex*) malloc(sizeof(MstVertex));
				uc = (CoordData*) malloc(sizeof(CoordData));
				vc = (CoordData*) malloc(sizeof(CoordData));
				
				if ((u == NULL)||(uc==NULL)||(v==NULL)||(vc==NULL)) {
					printf("gsFH.h : error allocating vertex for NTD\n");
					fflush(stdout);
					exit(1);
				}
				
				/* get vertices from the sPaths list */
				currentVData = list_data(currentV);
				nextVData = list_data(nextV);
				
				/* get vertex data */
				cvx = ((CoordData*)((sPathData*)currentVData)->vertex)->x;
				cvy = ((CoordData*)((sPathData*)currentVData)->vertex)->y;
				cvz = ((CoordData*)((sPathData*)currentVData)->vertex)->z;
				
				nvx = ((CoordData*)((sPathData*)nextVData)->vertex)->x;
				nvy = ((CoordData*)((sPathData*)nextVData)->vertex)->y;
				nvz = ((CoordData*)((sPathData*)nextVData)->vertex)->z;

								
				/* set vertex data */
				uc->x = cvx;
				uc->y = cvy;
				uc->z = cvz;
				
				vc->x = nvx;
				vc->y = nvy;
				vc->z = nvz;
				
				u->data = uc;
				v->data = vc;
				
				/* calculate weight between u and v */
				weight = currentVData->d - nextVData->d;

				
				/* try and insert u, if it exists, then delete the memory we allocated for it */
				if ( graph_ins_vertex(&NTD, u) == 1 ) {
					free(uc);
					free(u);
				}
				else {
					/* doesnt' matter which one is the start */
					mst_start = u;
				}

				/* try and insert v, if it exists, then delete the memorr we allocated for it */
				if ( graph_ins_vertex(&NTD, v) == 1) {
					free(vc);
					free(v);
				}
				
				/* now the vertices u and v are in the graph.   we now have to make an edge for uv */
				
				/* make edge going forward */				
				if ((uc = (CoordData*)malloc(sizeof(CoordData))) == NULL) {
					printf("gsFH.h : uc mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				if ((vc = (CoordData*)malloc(sizeof(CoordData))) == NULL) {
					printf("gsFH.h : vc mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				uc->x = cvx;
				uc->y = cvy;
				uc->z = cvz;

				vc->x = nvx;
				vc->y = nvy;
				vc->z = nvz;
				
				if ((mst_vertex1 = (MstVertex*) malloc(sizeof(MstVertex))) == NULL) {
					printf("gsFH.h : mst_Vertex1 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				if ((mst_vertex2 = (MstVertex*)malloc(sizeof(MstVertex))) == NULL) {
					printf("gsFH.h : mst_vertex2 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				mst_vertex1->data = uc;
				mst_vertex2->data = vc;
				mst_vertex2->weight = weight;
				
				/* try and insert, if it exists, free previously allocated mem */
				if ( graph_ins_edge(&NTD, mst_vertex1, mst_vertex2) == 1) {
					free(vc);
					free(mst_vertex2);
				}
				
				/* free the label */
				free(mst_vertex1->data);
				free(mst_vertex1);
				
				
				/* make edge going backward */				
				if ((uc = (CoordData*)malloc(sizeof(CoordData))) == NULL) {
					printf("gsFH.h : uc mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				if ((vc = (CoordData*)malloc(sizeof(CoordData))) == NULL) {
					printf("gsFH.h : vc mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				uc->x = cvx;
				uc->y = cvy;
				uc->z = cvz;
				
				vc->x = nvx;
				vc->y = nvy;
				vc->z = nvz;
				
				if ((mst_vertex1 = (MstVertex*) malloc(sizeof(MstVertex))) == NULL) {
					printf("gsFH.h : mst_Vertex1 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}

				if ((mst_vertex2 = (MstVertex*)malloc(sizeof(MstVertex))) == NULL) {
					printf("gsFH.h : mst_Vertex2 mem allocation error\n");
					fflush(stdout);
					exit(1);
				}
				
				mst_vertex1->data = vc;
				mst_vertex2->data = uc;
				mst_vertex2->weight = weight;
				
				/* try and insert, if it exists, free previously allocated mem */
				if ( graph_ins_edge(&NTD, mst_vertex1, mst_vertex2) == 1) {
					free(uc);
					free(mst_vertex2);
				}

				/* free the label */
				free(mst_vertex1->data);
				free(mst_vertex1);
								
				
				/* follow pointers */
				currentV = list_next(currentV);
				nextV = list_next(nextV);
				
				/* check to see if we're finished */
				if (nextV == NULL)
					done = 1;
			
			}
				
		 }
	}


/*----------------------------------------------------------------------------------------------------------*/
/*	Compute T (minimum spanning tree of NTD)							    */
/*----------------------------------------------------------------------------------------------------------*/

	/* call minimum spanning tree subroutine */
	if (mst(&NTD, mst_start,&T, match_coord) != 0) {
		printf("Error computing minimum spanning tree\n");
		return 1;
	}

	/* set leaves */	
	for ( element = list_head(&T); element != NULL; element = list_next(element))
	{
		mst_vertex = list_data(element);
		mst_vertex->is_leaf = 1;
    }
    
    /* for each node, set the parent is_leaf to 0.   Then, all leaves will remain */
    for (element = list_head(&T); element != NULL; element = list_next(element))
    {
        mst_vertex = list_data(element);
        
        if (mst_vertex->parent != NULL)
            mst_vertex->parent->is_leaf = 0;
    }
    
	
	
/*--------------------------------------------------------------------------------------*/
/*		Compute Steiner Tree Sk						 	*/
/*--------------------------------------------------------------------------------------*/

	isSteiner = 0;
	/* we remove all leaves that arent' terminals, when all leaves are terminals then we have a Steiner Tree */
	while (!isSteiner) {
		ListElmt	*prev;
		
		/* assume we have it */
		isSteiner = 1;
		
		/* check if each leaf is a terminal */
		prev = list_head(&T);
		element = list_next(prev);
		while (element != NULL) {
			int mx,my,mz;
			
			mst_vertex = list_data(element);
			mx = ((CoordData*)((MstVertex*)mst_vertex)->data)->x;
			my = ((CoordData*)((MstVertex*)mst_vertex)->data)->y;		
			mz = ((CoordData*)((MstVertex*)mst_vertex)->data)->z;					
			
			if (mst_vertex->is_leaf) {
				int found;
				
				found = 0;
				for (i = 0; i < NO_TERMINALS; i++) {
					int	tx,ty,tz;
					
					tx = ((CoordData*)((PathVertex*)terminals[i])->data)->x;
					ty = ((CoordData*)((PathVertex*)terminals[i])->data)->y;
					tz = ((CoordData*)((PathVertex*)terminals[i])->data)->z;
					
					if ( (tx==mx)&&(ty==my)&&(tz==mz))
						found = 1;
				}
				
				/* remove it if we can't find it */
				if (!found) {
					MstVertex	*junk;
					ListElmt *e;
					
					isSteiner = 0;		/* not done yet */
					
					list_rem_next(&T, prev, (void**)(&junk));
					
					/*reset leaves */
					/* initialize */
					for ( e = list_head(&T); e != NULL; e = list_next(e))
					{
						mst_vertex = list_data(e);
						mst_vertex->is_leaf = 1;
					}
					
					/* for each node, set the parent is_leaf to 0.   Then, all leaves will remain */
					for (e = list_head(&T); e != NULL; e = list_next(e))
					{
						mst_vertex = list_data(e);
						
						if (mst_vertex->parent != NULL)
							mst_vertex->parent->is_leaf = 0;
					}
					
					/* start over at beginning of list */
					prev = list_head(&T);
					element = list_next(prev);
					
					
				}
				else {
					prev = list_next(prev);
					element = list_next(element);
				}
			}
			else {
				prev = list_next(prev);
				element = list_next(element);
			}
		}
	}



	/* we can further eliminate vias that connect to a terminal leaf.   These are not neccessary*/
	isSteiner = 0;
	while (!isSteiner) {
		ListElmt	*prev;
		
		/* assume we have it */
		isSteiner = 1;
		
		/* check if each leaf is a terminal */
		prev = list_head(&T);
		element = list_next(prev);
		while (element != NULL) {
			int mx,my,mz;
			
			mst_vertex = list_data(element);
			mx = ((CoordData*)((MstVertex*)mst_vertex)->data)->x;
			my = ((CoordData*)((MstVertex*)mst_vertex)->data)->y;		
			mz = ((CoordData*)((MstVertex*)mst_vertex)->data)->z;					
			
			if (mst_vertex->is_leaf) {
				int remove;
				int	px,py;
				
				remove = 0;
				px = ((CoordData*)((MstVertex*)mst_vertex->parent)->data)->x;
				py = ((CoordData*)((MstVertex*)mst_vertex->parent)->data)->y;				
				
				if ((px == mx)&&(py == my))
					remove = 1;
				
				
				/* remove it if neccessary */
				if (remove) {
					MstVertex	*junk;
					ListElmt *e;
					
					isSteiner = 0;		/* not done yet */
					
					list_rem_next(&T, prev, (void**)(&junk));
					
					/*reset leaves */
					/* initialize */
					for ( e = list_head(&T); e != NULL; e = list_next(e))
					{
						mst_vertex = list_data(e);
						mst_vertex->is_leaf = 1;
					}
					
					/* for each node, set the parent is_leaf to 0.   Then, all leaves will remain */
					for (e = list_head(&T); e != NULL; e = list_next(e))
					{
						mst_vertex = list_data(e);
						
						if (mst_vertex->parent != NULL)
							mst_vertex->parent->is_leaf = 0;
					}
					
					/* start over at beginning of list */
					prev = list_head(&T);
					element = list_next(prev);
					
					
				}
				else {
					prev = list_next(prev);
					element = list_next(element);
				}
			}
			else {
				prev = list_next(prev);
				element = list_next(element);
			}
		}
	}



	/* get the total cost of the tree */
	tree_cost = 0;
	for (element = list_head(&T); element != NULL; element = list_next(element)) {
		
		CoordData *u, *v;
		
		mst_vertex = list_data(element);
		
		if (( mst_vertex->parent == NULL))
			continue;
		else {
			double temp;
			
			u = (CoordData*)mst_vertex->data;
			v = (CoordData*)mst_vertex->parent->data;
			
			/* look up cost of edge uv */
			temp = find_edge_weight(grid_graph,u,v);
			tree_cost += temp;
				
		}
	}
	
	

	*edge_count_OUT = list_size(&T)-1;
	if ((*(SteinerTree_OUT) = (int*) malloc(sizeof(int)*(list_size(&T)-1)))==NULL) {
		printf("gsFH.h : SteinerTree_OUT mem allocation error\n");
		fflush(stdout);
		exit(1);
	}


	i = 0;
	for ( element = list_head(&T); element != NULL; element = list_next(element))
	{
		int vx,vy,vz,px,py,pz;
		int tx,ty,tz;
		AdjList *a;
		ListElmt *e;
		int		edge_index;
		double	edge_weight;
		
		mst_vertex = list_data(element);
		
		vx = ((CoordData*)mst_vertex->data)->x;
		vy = ((CoordData*)mst_vertex->data)->y;
		vz = ((CoordData*)mst_vertex->data)->z;
		if (mst_vertex->parent != NULL) {
			px = ((CoordData*)mst_vertex->parent->data)->x;
			py = ((CoordData*)mst_vertex->parent->data)->y;		
			pz = ((CoordData*)mst_vertex->parent->data)->z;		
			edge_weight = mst_vertex->weight;
		}
		else {
			px = -1;
			py = -1;
			pz = -1;
		}
		

			
		a = (AdjList*)Edge2Adj[vx][vy][vz];
		
		tx = ((CoordData*)((PathVertex*)(a->vertex))->data)->x;
		ty = ((CoordData*)((PathVertex*)(a->vertex))->data)->y;
		tz = ((CoordData*)((PathVertex*)(a->vertex))->data)->z;
		
		for ( e = list_head(&(a->adjacent)); e != NULL; e = list_next(e) ) {
			PathVertex *p;
		
			p = (PathVertex*)list_data(e);
			
			tx = ((CoordData*)p->data)->x;
			ty = ((CoordData*)p->data)->y;
			tz = ((CoordData*)p->data)->z;
			
			if ((tx == px)&&(ty == py)&&(tz == pz)) {	/*found*/
				edge_index = p->index;
				(*SteinerTree_OUT)[i] = edge_index;
				i++;
			}
		}
	}


	

	/*-------------------------------------------------------------------------------------*/
	/*			Clean Up						       */
	/*-------------------------------------------------------------------------------------*/
	
	

	/* free our list of temporary paths*/
	for (i = 0; i < NO_TERMINALS; i++) 
		list_destroy(&tempPaths[i]);
	free(tempPaths);

	/* destroy distance network*/
	graph_destroy(&ND);
	
	/* deystroy all the shortest path lists*/
	for (i = 0; i < NO_TERMINALS; i++) 
	   for (j = 0; j < NO_TERMINALS; j++)
		   if ( i != j ) 
			   list_destroy(&sPaths[i][j]);
	
	/* destroy the pointers to the shortest path lists*/
	for (i = 0; i < NO_TERMINALS; i++) 
		free(sPaths[i]);
	free(sPaths);

	/* destroy the minimum spanning tree*/
	list_destroy(&TD);

	/* destroy grid spanning tree*/
	graph_destroy(&NTD);

	/* destroy the terminal list*/
	for (i = 0; i < NO_TERMINALS; i++) {
		path_vertex_free(terminals[i]);
	}
	free(terminals);
	
	/*destroy the steiner tree*/
	list_destroy(&T);

	return 0;
}
Ejemplo n.º 27
0
int tsp(List *vertices, const TspVertex *start, List *tour, int (*match)
   (const void *key1, const void *key2)) {

TspVertex          *tsp_vertex,
                   *tsp_start,
                   *selection;

ListElmt           *element;

double             minimum,
                   distance,
                   x,
                   y;

int                found,
                   i;

/*****************************************************************************
*                                                                            *
*  Initialize the list for the tour.                                         *
*                                                                            *
*****************************************************************************/

list_init(tour, NULL);

/*****************************************************************************
*                                                                            *
*  Initialize all of the vertices in the graph.                              *
*                                                                            *
*****************************************************************************/

found = 0;

for (element = list_head(vertices); element != NULL; element =
   list_next(element)) {

   tsp_vertex = list_data(element);

   if (match(tsp_vertex, start)) {

      /***********************************************************************
      *                                                                      *
      *  Start the tour at the start vertex.                                 *
      *                                                                      *
      ***********************************************************************/

      if (list_ins_next(tour, list_tail(tour), tsp_vertex) != 0) {

         list_destroy(tour);
         return -1;

      }

      /***********************************************************************
      *                                                                      *
      *  Save the start vertex and its coordinates.                          *
      *                                                                      *
      ***********************************************************************/

      tsp_start = tsp_vertex;
      x = tsp_vertex->x;
      y = tsp_vertex->y;

      /***********************************************************************
      *                                                                      *
      *  Color the start vertex black.                                       *
      *                                                                      *
      ***********************************************************************/

      tsp_vertex->color = black;
      found = 1;

      }

   else {

      /***********************************************************************
      *                                                                      *
      *  Color all other vertices white.                                     *
      *                                                                      *
      ***********************************************************************/

      tsp_vertex->color = white;

   }

}

/*****************************************************************************
*                                                                            *
*  Return if the start vertex was not found.                                 *
*                                                                            *
*****************************************************************************/

if (!found) {

   list_destroy(tour);
   return -1;

}

/*****************************************************************************
*                                                                            *
*  Use the nearest-neighbor heuristic to compute the tour.                   *
*                                                                            *
*****************************************************************************/

i = 0;

while (i < list_size(vertices) - 1) {

   /**************************************************************************
   *                                                                         *
   *  Select the white vertex closest to the previous vertex in the tour.    *
   *                                                                         *
   **************************************************************************/

   minimum = DBL_MAX;

   for (element = list_head(vertices); element != NULL; element =
      list_next(element)) {

      tsp_vertex = list_data(element);

      if (tsp_vertex->color == white) {

         distance = sqrt(pow(tsp_vertex->x-x,2.0) + pow(tsp_vertex->y-y,2.0));

         if (distance < minimum) {

            minimum = distance;
            selection = tsp_vertex;

         }

      }

   }

   /**************************************************************************
   *                                                                         *
   *  Save the coordinates of the selected vertex.                           *
   *                                                                         *
   **************************************************************************/

   x = selection->x;
   y = selection->y;

   /**************************************************************************
   *                                                                         *
   *  Color the selected vertex black.                                       *
   *                                                                         *
   **************************************************************************/

   selection->color = black;

   /**************************************************************************
   *                                                                         *
   *  Insert the selected vertex into the tour.                              *
   *                                                                         *
   **************************************************************************/

   if (list_ins_next(tour, list_tail(tour), selection) != 0) {

      list_destroy(tour);
      return -1;

   }

   /**************************************************************************
   *                                                                         *
   *  Prepare to select the next vertex.                                     *
   *                                                                         *
   **************************************************************************/

   i++;

}

/*****************************************************************************
*                                                                            *
*  Insert the start vertex again to complete the tour.                       *
*                                                                            *
*****************************************************************************/

if (list_ins_next(tour, list_tail(tour), tsp_start) != 0) {

   list_destroy(tour);
   return -1;

}

return 0;

}
Ejemplo n.º 28
0
/*--------------------------------------------------------------*/
int copy_sPath(List *path, List *sPath, CoordData *start) {
	ListElmt		*element;
	sPathData		*newElement;
	PathVertex		*path_vertex, *v, *p;
	int				done;
	
	list_init(sPath, (void*)sPath_vertex_free);
	
	v = NULL;
	
	/* find start vertex in path */
	for ( element = list_head(path); element != NULL; element = list_next(element)) {
		int  sx,sy,sz,px,py,pz;
		
		path_vertex = list_data(element);
		px = ((CoordData*)((PathVertex*)path_vertex)->data)->x;
		py = ((CoordData*)((PathVertex*)path_vertex)->data)->y;	
		pz = ((CoordData*)((PathVertex*)path_vertex)->data)->z;	
		sx = start->x;
		sy = start->y;
		sz = start->z;
		
		
		/* if found, set a pointer and skip to end of list */
		if ((px==sx)&&(py==sy)&&(pz==sz)) {
			v = path_vertex;
			element = list_tail(path);
		}
	}
	
	p = v->parent;
	done = 0;	
	/* follow v back to root (when parent == NULL) */
	while ( !done ) {
		CoordData		*vCoord, *pCoord;
		
		/* allocate some memory */
		newElement = (sPathData*) malloc(sizeof(sPathData));
		vCoord = (CoordData*) malloc(sizeof(CoordData));
		pCoord = (CoordData*) malloc(sizeof(CoordData));
		
		if ((newElement == NULL)||(vCoord == NULL)||(pCoord == NULL)) {
			printf("helper.c : mem allocation error\n");
			fflush(stdout);
			exit(1);
		}
		
		/* set current vertex coords */
		vCoord->x = ((CoordData*)((PathVertex*)v)->data)->x;
		vCoord->y = ((CoordData*)((PathVertex*)v)->data)->y;
		vCoord->z = ((CoordData*)((PathVertex*)v)->data)->z;
		
		/* set parent vertex coords */
		pCoord->x = ((CoordData*)((PathVertex*)p)->data)->x;
		pCoord->y = ((CoordData*)((PathVertex*)p)->data)->y;
		pCoord->z = ((CoordData*)((PathVertex*)p)->data)->z;
		
		/* set the new element to list */
		newElement->vertex = vCoord;
		newElement->parent = pCoord;
		newElement->d = ((PathVertex*)v)->d;
		
		/* insert the element into the list */
		if (list_ins_next(sPath, list_tail(sPath), newElement) != 0) {
			printf("Problem inserting into sPath!\n");
			list_destroy(sPath);
			return -1;
		}
		
		
		/* next vertex */
		if (p->parent == NULL) {
			done = 1;
			
			/*insert one more element starting with parent */
			newElement = (sPathData*) malloc(sizeof(sPathData));
			vCoord = (CoordData*) malloc(sizeof(CoordData));
			
			if ((newElement==NULL)||(vCoord==NULL)) {
				printf("helper.c : memory allocation error\n");
				fflush(stdout);
				exit(1);
			}
			vCoord->x = ((CoordData*)((PathVertex*)p)->data)->x;
			vCoord->y = ((CoordData*)((PathVertex*)p)->data)->y;
			vCoord->z = ((CoordData*)((PathVertex*)p)->data)->z;
			newElement->vertex = vCoord;
			newElement->parent = NULL;
			newElement->d = 0;
			
			if (list_ins_next(sPath, list_tail(sPath), newElement) != 0){
				printf("Problem inserting into sPath!\n");
				list_destroy(sPath);
				return -1;
			}
		}
		else {
			v = p;
			p = p->parent;
		}
	}
	return 0;
}
Ejemplo n.º 29
0
int stack_push(Stack *stack, const void *data)
{
    //push the data onto the stack/list top/head
    return list_ins_next(stack, NULL, data);
}
int set_union(Set * setu, const Set * set1, const Set * set2)
{

    ListElmt *member;

    void *data;

    /*****************************************************************************
    *  Initialize the set for the union.                                         *
    *****************************************************************************/

    set_init(setu, set1->match, NULL);

    /*****************************************************************************
    *  Insert the members of the first set.                                      *
    *****************************************************************************/

    for (member = list_head(set1); member != NULL;
            member = list_next(member)) {

        data = list_data(member);

        if (list_ins_next(setu, list_tail(setu), data) != 0) {

            set_destroy(setu);
            return -1;

        }

    }

    /*****************************************************************************
    *  Insert the members of the second set.                                     *
    *****************************************************************************/

    for (member = list_head(set2); member != NULL;
            member = list_next(member)) {

        if (set_is_member(set1, list_data(member))) {

            /***********************************************************************
            *  Do not allow the insertion of duplicates.                           *
            ***********************************************************************/

            continue;

        }

        else {

            data = list_data(member);

            if (list_ins_next(setu, list_tail(setu), data) != 0) {

                set_destroy(setu);
                return -1;

            }

        }

    }

    return 0;

}