11package com .jwetherell .algorithms .data_structures ;
22
33import java .util .ArrayList ;
4+ import java .util .Arrays ;
45import java .util .Collection ;
56import java .util .Iterator ;
67import java .util .List ;
@@ -24,6 +25,7 @@ public enum TYPE {
2425 DIRECTED , UNDIRECTED
2526 }
2627
28+ /** Defaulted to undirected */
2729 private TYPE type = TYPE .UNDIRECTED ;
2830
2931 public Graph () { }
@@ -32,30 +34,47 @@ public Graph(TYPE type) {
3234 this .type = type ;
3335 }
3436
37+ /** Deep copies **/
3538 public Graph (Graph <T > g ) {
36- // Deep copies
37-
3839 type = g .getType ();
3940
40- // Copy the vertices ( which copies the edges)
41- for (Vertex <T > v : g .getVerticies ())
41+ // Copy the vertices which also copies the edges
42+ for (Vertex <T > v : g .getVertices ())
4243 this .allVertices .add (new Vertex <T >(v ));
4344
44- // New edges are created in the above loop, now add them to the graph's list
45- for (Vertex <T > v : this .allVertices ) {
46- for (Edge <T > e : v .getEdges ())
45+ for (Vertex <T > v : this .getVertices ()) {
46+ for (Edge <T > e : v .getEdges ()) {
4747 this .allEdges .add (e );
48+ }
4849 }
4950 }
5051
51- public Graph (Collection <Vertex <T >> verticies , List <Edge <T >> edges ) {
52- this (TYPE .UNDIRECTED , verticies , edges );
52+ /**
53+ * Creates a Graph from the vertices and edges. This defaults to an undirected Graph
54+ *
55+ * NOTE: Duplicate vertices and edges ARE allowed.
56+ * NOTE: Copies the vertex and edge objects but does NOT store the Collection parameters itself.
57+ *
58+ * @param vertices Collection of vertices
59+ * @param edges Collection of edges
60+ */
61+ public Graph (Collection <Vertex <T >> vertices , Collection <Edge <T >> edges ) {
62+ this (TYPE .UNDIRECTED , vertices , edges );
5363 }
5464
55- public Graph (TYPE type , Collection <Vertex <T >> verticies , List <Edge <T >> edges ) {
65+ /**
66+ * Creates a Graph from the vertices and edges.
67+ *
68+ * NOTE: Duplicate vertices and edges ARE allowed.
69+ * NOTE: Copies the vertex and edge objects but does NOT store the Collection parameters itself.
70+ *
71+ * @param vertices Collection of vertices
72+ * @param edges Collection of edges
73+ */
74+ public Graph (TYPE type , Collection <Vertex <T >> vertices , Collection <Edge <T >> edges ) {
5675 this (type );
5776
58- this .allVertices .addAll (verticies );
77+ this .allVertices .addAll (vertices );
5978 this .allEdges .addAll (edges );
6079
6180 for (Edge <T > e : edges ) {
@@ -78,7 +97,7 @@ public TYPE getType() {
7897 return type ;
7998 }
8099
81- public List <Vertex <T >> getVerticies () {
100+ public List <Vertex <T >> getVertices () {
82101 return allVertices ;
83102 }
84103
@@ -121,13 +140,29 @@ public boolean equals(Object g1) {
121140 if (!edgesSizeEquals )
122141 return false ;
123142
124- final boolean verticesEquals = this .allVertices .equals (g .allVertices );
125- if (!verticesEquals )
126- return false ;
143+ // Vertices can contain duplicates and appear in different order but both arrays should contain the same elements
144+ final Object [] ov1 = this .allVertices .toArray ();
145+ Arrays .sort (ov1 );
146+ final Object [] ov2 = g .allVertices .toArray ();
147+ Arrays .sort (ov2 );
148+ for (int i =0 ; i <ov1 .length ; i ++) {
149+ final Vertex <T > v1 = (Vertex <T >) ov1 [i ];
150+ final Vertex <T > v2 = (Vertex <T >) ov2 [i ];
151+ if (!v1 .equals (v2 ))
152+ return false ;
153+ }
127154
128- final boolean edgesEquals = this .allEdges .equals (g .allEdges );
129- if (!edgesEquals )
130- return false ;
155+ // Edges can contain duplicates and appear in different order but both arrays should contain the same elements
156+ final Object [] oe1 = this .allEdges .toArray ();
157+ Arrays .sort (oe1 );
158+ final Object [] oe2 = g .allEdges .toArray ();
159+ Arrays .sort (oe2 );
160+ for (int i =0 ; i <oe1 .length ; i ++) {
161+ final Edge <T > e1 = (Edge <T >) oe1 [i ];
162+ final Edge <T > e2 = (Edge <T >) oe2 [i ];
163+ if (!e1 .equals (e2 ))
164+ return false ;
165+ }
131166
132167 return true ;
133168 }
@@ -158,13 +193,11 @@ public Vertex(T value, int weight) {
158193 this .weight = weight ;
159194 }
160195
161- /** Deep copies edges **/
196+ /** Deep copies the edges along with the value and weight **/
162197 public Vertex (Vertex <T > vertex ) {
163198 this (vertex .value , vertex .weight );
164199
165- this .edges = new ArrayList <Edge <T >>();
166- for (Edge <T > e : vertex .edges )
167- this .edges .add (new Edge <T >(e ));
200+ this .edges .addAll (vertex .edges );
168201 }
169202
170203 public T getValue () {
@@ -226,6 +259,16 @@ public boolean equals(Object v1) {
226259 if (!valuesEquals )
227260 return false ;
228261
262+ final Iterator <Edge <T >> iter1 = this .edges .iterator ();
263+ final Iterator <Edge <T >> iter2 = v .edges .iterator ();
264+ while (iter1 .hasNext () && iter2 .hasNext ()) {
265+ // Only checking the cost
266+ final Edge <T > e1 = iter1 .next ();
267+ final Edge <T > e2 = iter2 .next ();
268+ if (e1 .cost != e2 .cost )
269+ return false ;
270+ }
271+
229272 return true ;
230273 }
231274
@@ -234,9 +277,33 @@ public boolean equals(Object v1) {
234277 */
235278 @ Override
236279 public int compareTo (Vertex <T > v ) {
237- if (this .value == null || v .value == null )
280+ final int valueComp = this .value .compareTo (v .value );
281+ if (valueComp != 0 )
282+ return valueComp ;
283+
284+ if (this .weight < v .weight )
238285 return -1 ;
239- return this .value .compareTo (v .value );
286+ if (this .weight > v .weight )
287+ return 1 ;
288+
289+ if (this .edges .size () < v .edges .size ())
290+ return -1 ;
291+ if (this .edges .size () > v .edges .size ())
292+ return 1 ;
293+
294+ final Iterator <Edge <T >> iter1 = this .edges .iterator ();
295+ final Iterator <Edge <T >> iter2 = v .edges .iterator ();
296+ while (iter1 .hasNext () && iter2 .hasNext ()) {
297+ // Only checking the cost
298+ final Edge <T > e1 = iter1 .next ();
299+ final Edge <T > e2 = iter2 .next ();
300+ if (e1 .cost < e2 .cost )
301+ return -1 ;
302+ if (e1 .cost > e2 .cost )
303+ return 1 ;
304+ }
305+
306+ return 0 ;
240307 }
241308
242309 /**
@@ -260,7 +327,7 @@ public static class Edge<T extends Comparable<T>> implements Comparable<Edge<T>>
260327
261328 public Edge (int cost , Vertex <T > from , Vertex <T > to ) {
262329 if (from == null || to == null )
263- throw (new NullPointerException ("Both 'to' and 'from' Verticies need to be non-NULL." ));
330+ throw (new NullPointerException ("Both 'to' and 'from' vertices need to be non-NULL." ));
264331
265332 this .cost = cost ;
266333 this .from = from ;
@@ -310,12 +377,12 @@ public boolean equals(Object e1) {
310377 if (!costs )
311378 return false ;
312379
313- final boolean froms = this .from .equals (e .from );
314- if (!froms )
380+ final boolean from = this .from .equals (e .from );
381+ if (!from )
315382 return false ;
316383
317- final boolean tos = this .to .equals (e .to );
318- if (!tos )
384+ final boolean to = this .to .equals (e .to );
385+ if (!to )
319386 return false ;
320387
321388 return true ;
@@ -330,6 +397,15 @@ public int compareTo(Edge<T> e) {
330397 return -1 ;
331398 if (this .cost > e .cost )
332399 return 1 ;
400+
401+ final int from = this .from .compareTo (e .from );
402+ if (from != 0 )
403+ return from ;
404+
405+ final int to = this .to .compareTo (e .to );
406+ if (to != 0 )
407+ return to ;
408+
333409 return 0 ;
334410 }
335411
0 commit comments