第七十三课 图的存储结构(下)
Posted wanmeishenghuo
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了第七十三课 图的存储结构(下)相关的知识,希望对你有一定的参考价值。
增加新顶点的时候只能在链表的末尾进行,其他的顶点的编号不能打乱了。
添加ListGraph.h文件:
1 #ifndef LISTGRAPH_H 2 #define LISTGRAPH_H 3 4 #include "Graph.h" 5 #include "LinkList.h" 6 #include "Exception.h" 7 #include "DynamicArray.h" 8 9 namespace DTLib 10 { 11 12 template < typename V, typename E > 13 class ListGraph : public Graph<V, E> 14 { 15 protected: 16 struct Vertex : public Object //定义顶点 17 { 18 V* data; 19 LinkList< Edge<E> > edge; 20 21 Vertex() 22 { 23 data = NULL; 24 } 25 }; 26 27 LinkList<Vertex*> m_list; //真正的邻接链表 28 public: 29 ListGraph(unsigned int n = 0) 30 { 31 for(unsigned int i = 0; i < n; i++) 32 { 33 addVertex(); 34 } 35 } 36 37 int addVertex() 38 { 39 int ret = -1; 40 Vertex* v = new Vertex(); 41 42 if( v != NULL ) 43 { 44 m_list.insert(v); 45 46 ret = m_list.length() - 1; //返回新增加的顶点的编号 47 } 48 else 49 { 50 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to create Vertex object..."); 51 } 52 53 return ret; 54 } 55 56 int addVertex(const V& value) 57 { 58 int ret = addVertex(); 59 60 if( ret >= 0 ) 61 { 62 setVertex(ret, value); 63 } 64 65 return ret; 66 } 67 68 bool setVertex(int i, const V& value) 69 { 70 int ret = ((0 <= i) && (i < vCount())); 71 72 if( ret ) 73 { 74 Vertex* vertex = m_list.get(i); 75 V* data = vertex->data; 76 77 if( data == NULL ) 78 { 79 data = new V(); 80 } 81 82 if( data != NULL ) 83 { 84 *data = value; 85 86 vertex->data = data; 87 } 88 else 89 { 90 THROW_EXCEPTION(NoEnoughMemoryException, "Bo memory to create Vertex value..."); 91 } 92 } 93 94 return ret; 95 } 96 97 V getVertex(int i) 98 { 99 V ret; 100 101 if( !getVertex(i, ret) ) 102 { 103 THROW_EXCEPTION(InvalidParameterException, "Index i is invalid..."); 104 } 105 106 return ret; 107 } 108 109 bool getVertex(int i, V& value) 110 { 111 int ret = ((0 <= i) && (i < vCount())); 112 113 if( ret ) 114 { 115 Vertex* v = m_list.get(i); 116 117 if( v->data != NULL ) 118 { 119 value = *(v->data); 120 } 121 else 122 { 123 THROW_EXCEPTION(InvalidOperationException, "No value assigned to this vertex..."); 124 } 125 } 126 127 return ret; 128 } 129 130 void removeVertex() //删除最近添加的顶点,只能从后面的顶点开始删除 131 { 132 if( m_list.length() > 0 ) 133 { 134 int index = m_list.length() - 1; 135 Vertex* v = m_list.get(index); 136 137 if( m_list.remove(index) ) 138 { 139 for(int i=(m_list.move(0), 0); !m_list.end(); i++, m_list.next()) 140 { 141 int pos = m_list.current()->edge.find(Edge<E>(i, index)); 142 143 if( pos >= 0 ) 144 { 145 m_list.current()->edge.remove(pos); 146 } 147 } 148 149 delete v->data; 150 delete v; 151 } 152 } 153 else 154 { 155 THROW_EXCEPTION(InvalidOperationException, "No vertex in current graph..."); 156 } 157 } 158 159 SharedPointer< Array<int> > getAdjacent(int i) 160 { 161 DynamicArray<int>* ret = NULL; 162 163 if( (0 <= i) && (i < vCount()) ) 164 { 165 Vertex* vertex = m_list.get(i); 166 167 ret = new DynamicArray<int>(vertex->edge.length()); 168 169 if( ret != NULL ) 170 { 171 for(int k=(vertex->edge.move(0), 0); !vertex->edge.end(); k++, vertex->edge.next()) 172 { 173 ret->set(k, vertex->edge.current().e); 174 } 175 } 176 else 177 { 178 THROW_EXCEPTION(NoEnoughMemoryException ,"No memory to create DynamicArray<int>..."); 179 } 180 } 181 else 182 { 183 THROW_EXCEPTION(InvalidParameterException, "Index i is invalid..."); 184 } 185 186 return ret; 187 } 188 189 E getEdge(int i, int j) 190 { 191 E ret; 192 193 if( !getEdge(i, j, ret) ) 194 { 195 THROW_EXCEPTION(InvalidParameterException, "Edge<i, j> is invalid..."); 196 } 197 198 return ret; 199 } 200 201 bool getEdge(int i, int j, E& value) 202 { 203 int ret = ( (0 <= i) && (i < vCount()) && 204 (0 <= j) && (j < vCount()) ); 205 206 if( ret ) 207 { 208 Vertex* vertex = m_list.get(i); 209 int pos = vertex->edge.find(Edge<E>(i, j)); 210 211 if( pos >= 0 ) 212 { 213 value = vertex->edge.get(pos).data; 214 } 215 else 216 { 217 THROW_EXCEPTION(InvalidOperationException, "No value assigned to this edge..."); 218 } 219 } 220 221 return ret; 222 } 223 224 bool setEdge(int i, int j, const E& value) 225 { 226 int ret = ( (0 <= i) && (i < vCount()) && 227 (0 <= j) && (j < vCount()) ); 228 229 if( ret ) 230 { 231 Vertex* vertex = m_list.get(i); 232 int pos = vertex->edge.find(Edge<E>(i, j)); 233 234 if( pos >= 0 ) 235 { 236 ret = vertex->edge.set(pos, Edge<E>(i, j, value)); 237 } 238 else 239 { 240 ret = vertex->edge.insert(0, Edge<E>(i, j, value)); 241 } 242 } 243 244 return ret; 245 } 246 247 bool removeEdge(int i, int j) 248 { 249 int ret = ( (0 <= i) && (i < vCount()) && 250 (0 <= j) && (j < vCount()) ); 251 252 if( ret ) 253 { 254 Vertex* vertex = m_list.get(i); 255 int pos = vertex->edge.find(Edge<E>(i, j)); 256 257 if( pos >= 0 ) 258 { 259 ret = vertex->edge.remove(pos); 260 } 261 } 262 263 return ret; 264 } 265 266 int vCount() 267 { 268 return m_list.length(); 269 } 270 271 int eCount() 272 { 273 int ret = 0; 274 275 for(m_list.move(0); !m_list.end(); m_list.next()) 276 { 277 ret += m_list.current()->edge.length(); 278 } 279 280 return ret; 281 } 282 283 int ID(int i) 284 { 285 int ret = 0; 286 287 if( (0 <= i) && (i < vCount()) ) 288 { 289 for(m_list.move(0); !m_list.end(); m_list.next()) 290 { 291 LinkList< Edge<E> >& edge = m_list.current()->edge; 292 293 for(edge.move(0); !edge.end(); edge.next()) 294 { 295 if( edge.current().e == i ) 296 { 297 ret++; 298 break; 299 } 300 } 301 } 302 } 303 else 304 { 305 THROW_EXCEPTION(InvalidParameterException, "Index i is invalid..."); 306 } 307 308 return ret; 309 } 310 311 int OD(int i) 312 { 313 int ret = 0; 314 315 if( (0 <= i) && (i < vCount()) ) 316 { 317 ret = m_list.get(i)->edge.length(); 318 } 319 else 320 { 321 THROW_EXCEPTION(InvalidParameterException, "Index i is invalid..."); 322 } 323 324 return ret; 325 } 326 327 ~ListGraph() 328 { 329 while( m_list.length() > 0 ) 330 { 331 Vertex* toDel = m_list.get(0); 332 333 m_list.remove(0); 334 335 delete toDel->data; 336 delete toDel; 337 } 338 } 339 }; 340 341 } 342 343 #endif // LISTGRAPH_H
测试程序如下:
1 #include <iostream> 2 #include "BTreeNode.h" 3 #include "ListGraph.h" 4 5 using namespace std; 6 using namespace DTLib; 7 8 9 int main() 10 { 11 ListGraph<char, int> g; 12 13 g.addVertex(‘A‘); 14 g.addVertex(‘B‘); 15 g.addVertex(‘C‘); 16 g.addVertex(‘D‘); 17 18 for(int i=0; i< g.vCount(); i++) 19 { 20 cout << i << " : " << g.getVertex(i) << endl; 21 } 22 23 g.setEdge(0, 1, 5); 24 g.setEdge(0, 3, 5); 25 g.setEdge(1, 2, 8); 26 g.setEdge(2, 3, 2); 27 g.setEdge(3, 1, 9); 28 29 cout << "W(0, 1) : " << g.getEdge(0, 1) << endl; 30 cout << "W(0, 3) : " << g.getEdge(0, 3) << endl; 31 cout << "W(1, 2) : " << g.getEdge(1, 2) << endl; 32 cout << "W(2, 3) : " << g.getEdge(2, 3) << endl; 33 cout << "W(3, 1) : " << g.getEdge(3, 1) << endl; 34 35 cout << "eCount : " << g.eCount() << endl; 36 37 SharedPointer< Array<int> > aj = g.getAdjacent(0); 38 39 for(int i=0; i<aj->length(); i++) 40 { 41 cout << (*aj)[i] << endl; 42 } 43 44 cout << "ID(1) : " << g.ID(1) << endl; 45 cout << "OD(1) : " << g.OD(1) << endl; 46 cout << "TD(1) : " << g.TD(1) << endl; 47 48 g.removeVertex(); 49 50 cout << "eCount : " << g.eCount() << endl; 51 52 cout << "W(0, 1) : " << g.getEdge(0, 1) << endl; 53 cout << "W(1, 2) : " << g.getEdge(1, 2) << endl; 54 55 return 0; 56 }
结果如下:
小结:
以上是关于第七十三课 图的存储结构(下)的主要内容,如果未能解决你的问题,请参考以下文章