GRASS Programmer's Manual 6.4.1(2011)
|
00001 /* LIBDGL -- a Directed Graph Library implementation 00002 * Copyright (C) 2002 Roberto Micarelli 00003 * 00004 * This program is free software; you can redistribute it and/or modify 00005 * it under the terms of the GNU General Public License as published by 00006 * the Free Software Foundation; either version 2 of the License, or 00007 * (at your option) any later version. 00008 * 00009 * This program is distributed in the hope that it will be useful, 00010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00012 * GNU General Public License for more details. 00013 * 00014 * You should have received a copy of the GNU General Public License 00015 * along with this program; if not, write to the Free Software 00016 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 00017 */ 00018 00019 /* 00020 * Source best viewed with tabstop=4 00021 */ 00022 00023 #include <stdio.h> 00024 #include <string.h> 00025 #include <sys/types.h> 00026 #include <sys/stat.h> 00027 #include <unistd.h> 00028 #include <stdlib.h> 00029 #include <fcntl.h> 00030 #include <time.h> 00031 #include <errno.h> 00032 00033 #include "../type.h" 00034 #include "../graph.h" 00035 00036 #include "opt.h" 00037 00038 extern int errno; 00039 00040 00041 00042 int main(int argc, char **argv) 00043 { 00044 FILE *fp; 00045 dglGraph_s graph; 00046 char sz[1024]; 00047 char c; 00048 int nret, fd; 00049 int version, attrsize; 00050 dglInt32_t nodeid, from, to, cost, user, xyz[3]; 00051 dglInt32_t opaqueset[16] = { 00052 360000, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 00053 }; 00054 00055 /* program options 00056 */ 00057 char *pszFilein; 00058 char *pszFileout; 00059 00060 GNO_BEGIN /* short long default variable help */ 00061 GNO_OPTION("f", "file", NULL, &pszFilein, 00062 "Input Graph definition file") 00063 GNO_OPTION("g", "graph", NULL, &pszFileout, "Output Graph file") 00064 GNO_END if (GNO_PARSE(argc, argv) < 0) 00065 { 00066 return 1; 00067 } 00068 /* 00069 * options parsed 00070 */ 00071 00072 if (pszFilein == NULL) { 00073 GNO_HELP("Incomplete parameters"); 00074 return 1; 00075 } 00076 00077 if ((fp = fopen(pszFilein, "r")) == NULL) { 00078 perror("fopen"); 00079 return 1; 00080 } 00081 00082 reread_first_line: 00083 if (fgets(sz, sizeof(sz), fp) == NULL) { 00084 fprintf(stderr, "unexpected EOF\n"); 00085 return 1; 00086 } 00087 00088 if (sz[0] == '#' || strlen(sz) == 0) 00089 goto reread_first_line; 00090 00091 sscanf(sz, "%d %d", &version, &attrsize); 00092 00093 /* 00094 * initialize the graph 00095 */ 00096 dglInitialize(&graph, /* graph context to initialize */ 00097 version, /* version */ 00098 sizeof(xyz), /* node attributes size */ 00099 0, /* edge attributes size */ 00100 opaqueset /* opaque graph parameters */ 00101 ); 00102 00103 /* 00104 * generate edge cost prioritizing 00105 */ 00106 dglSet_Options(&graph, DGL_GO_EdgePrioritize_COST); 00107 00108 00109 /* add arcs and X/Y/Z node attributes 00110 */ 00111 while (fgets(sz, sizeof(sz), fp) != NULL) { 00112 if (sz[0] == '#') 00113 continue; 00114 00115 if (strlen(sz) == 0) 00116 continue; 00117 00118 if (sz[0] == 'A') { /* add a edge */ 00119 sscanf(sz, "%c %ld %ld %ld %ld", &c, &from, &to, &cost, &user); 00120 00121 nret = dglAddEdge(&graph, from, to, cost, user); 00122 00123 00124 if (nret < 0) { 00125 fprintf(stderr, "dglAddArc error: %s\n", dglStrerror(&graph)); 00126 return 1; 00127 } 00128 } 00129 else if (sz[0] == 'V') { /* add a node */ 00130 sscanf(sz, "%c %ld", &c, &nodeid); 00131 00132 printf("add node: %ld\n", nodeid); 00133 00134 nret = dglAddNode(&graph, nodeid, NULL, 0); 00135 00136 if (nret < 0) { 00137 fprintf(stderr, "dglAddNode error: %s\n", 00138 dglStrerror(&graph)); 00139 return 1; 00140 } 00141 } 00142 else if (sz[0] == 'N') { /* set attributes for a (already inserted) node */ 00143 sscanf(sz, "%c %ld %ld %ld %ld", &c, &nodeid, &xyz[0], &xyz[1], 00144 &xyz[2]); 00145 00146 dglNodeSet_Attr(&graph, dglGetNode(&graph, nodeid), xyz); 00147 } 00148 } 00149 fclose(fp); 00150 00151 00152 #if 0 /* show edges */ 00153 { 00154 dglEdgeTraverser_s t; 00155 dglInt32_t *pEdge; 00156 00157 nret = 00158 dglEdge_T_Initialize(&t, &graph, dglGet_EdgePrioritizer(&graph)); 00159 if (nret < 0) { 00160 fprintf(stderr, "\ndglEdge_T_Initialize error: %s\n", 00161 dglStrerror(&graph)); 00162 return 1; 00163 } 00164 for (pEdge = dglEdge_T_First(&t); pEdge; pEdge = dglEdge_T_Next(&t)) { 00165 printf("edge: id=%ld cost=%ld\n", 00166 dglEdgeGet_Id(&graph, pEdge), 00167 dglEdgeGet_Cost(&graph, pEdge)); 00168 } 00169 dglEdge_T_Release(&t); 00170 } 00171 #endif 00172 00173 /* 00174 * flatten the graph (make it serializable) 00175 */ 00176 nret = dglFlatten(&graph); 00177 00178 if (nret < 0) { 00179 fprintf(stderr, "dglFlatten error: %s\n", dglStrerror(&graph)); 00180 return 1; 00181 } 00182 00183 /* 00184 * store the graph 00185 */ 00186 if ((fd = open(pszFileout, O_WRONLY | O_CREAT, 0666)) < 0) { 00187 perror("open"); 00188 return 1; 00189 } 00190 00191 nret = dglWrite(&graph, fd); 00192 00193 if (nret < 0) { 00194 fprintf(stderr, "dglWrite error: %s\n", dglStrerror(&graph)); 00195 return 1; 00196 } 00197 00198 close(fd); 00199 00200 /* 00201 * finish 00202 */ 00203 dglRelease(&graph); 00204 00205 return 0; 00206 }