001/* 002MIT License 003 004Copyright (c) 2020 earlygrey 005 006Permission is hereby granted, free of charge, to any person obtaining a copy 007of this software and associated documentation files (the "Software"), to deal 008in the Software without restriction, including without limitation the rights 009to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 010copies of the Software, and to permit persons to whom the Software is 011furnished to do so, subject to the following conditions: 012 013The above copyright notice and this permission notice shall be included in all 014copies or substantial portions of the Software. 015 016THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 017IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 018FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 019AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 020LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 021OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 022SOFTWARE. 023 */ 024package squidpony.squidai.graph; 025 026import java.io.Serializable; 027 028/** 029 * The most-commonly-used class that represents an edge between nodes on a Graph. Different kinds of graph will use 030 * different subclasses of this to represent their edges: {@link DirectedConnection} or {@link UndirectedConnection}. 031 * These subclasses don't add new functionality, but they compare differently during hashing and equality checks. 032 * @param <V> the vertex type; often {@link squidpony.squidmath.Coord} 033 * @author earlygrey 034 */ 035public class Connection<V> extends Edge<V> implements Serializable { 036 private static final long serialVersionUID = 1L; 037 038 //================================================================================ 039 // Fields and constants 040 //================================================================================ 041 042 protected static final float DEFAULT_WEIGHT = 1; 043 044 protected Node<V> a, b; 045 protected float weight = DEFAULT_WEIGHT; 046 047 //================================================================================ 048 // Constructor 049 //================================================================================ 050 051 public Connection() { 052 } 053 054 public Connection(Node<V> a, Node<V> b) { 055 this.a = a; 056 this.b = b; 057 } 058 059 public Connection(Node<V> a, Node<V> b, float weight) { 060 this.a = a; 061 this.b = b; 062 this.weight = weight; 063 } 064 065 @Override 066 protected void set(Node<V> a, Node<V> b, float weight) { 067 this.a = a; 068 this.b = b; 069 this.weight = weight; 070 } 071 072 //================================================================================ 073 // Internal methods 074 //================================================================================ 075 076 @Override 077 protected Node<V> getInternalNodeA() { 078 return a; 079 } 080 081 @Override 082 protected Node<V> getInternalNodeB() { 083 return b; 084 } 085 086 //================================================================================ 087 // Public methods 088 //================================================================================ 089 090 @Override 091 public V getA() { 092 return a.object; 093 } 094 095 @Override 096 public V getB() { 097 return b.object; 098 } 099 100 @Override 101 public float getWeight() { 102 return weight; 103 } 104 105 @Override 106 public void setWeight(float weight) { 107 this.weight = weight; 108 } 109 110 public Node<V> getNodeA() { 111 return a; 112 } 113 114 public Node<V> getNodeB() { 115 return b; 116 } 117 118 //================================================================================ 119 // Subclasses 120 //================================================================================ 121 122 /** 123 * A Connection that treats A-to-B as a different edge from B-to-A. 124 * @param <V> the vertex type; often {@link squidpony.squidmath.Coord} 125 */ 126 public static class DirectedConnection<V> extends Connection<V> { 127 128 @Override 129 public boolean equals(Object o) { 130 if (this == o) return true; 131 if (o == null || getClass() != o.getClass()) return false; 132 Connection edge = (Connection) o; 133 // this assumes a and b are non-null when equals() is called. 134 return a.equals(edge.a) && b.equals(edge.b); 135 } 136 137 @Override 138 public int hashCode() { 139 return (int) (a.hashCode() * 0xC13FA9A902A6328FL + b.hashCode() * 0x91E10DA5C79E7B1DL >>> 32); 140 } 141 142 @Override 143 public String toString() { 144 return "{" + a + " -> " + b +'}'; 145 } 146 147 } 148 /** 149 * A Connection that treats A-to-B and B-to-A as the same edge. 150 * @param <V> the vertex type; often {@link squidpony.squidmath.Coord} 151 */ 152 public static class UndirectedConnection<V> extends Connection<V> { 153 154 @Override 155 public boolean equals(Object o) { 156 if (this == o) return true; 157 if (o == null || getClass() != o.getClass()) return false; 158 Connection edge = (Connection) o; 159 // this assumes a and b are non-null when equals() is called. 160 return (a.equals(edge.a) && b.equals(edge.b)) 161 || (a.equals(edge.b) && b.equals(edge.a)); 162 } 163 164 @Override 165 public int hashCode() { 166 return (int) ((a.hashCode() + b.hashCode()) * 0x9E3779B97F4A7C15L >>> 32); 167 } 168 169 @Override 170 public String toString() { 171 return "{" + a + " <> " + b +'}'; 172 } 173 } 174 175}