1 package org.opentrafficsim.road.od;
2
3 import java.io.Serializable;
4 import java.util.ArrayList;
5 import java.util.List;
6
7 import org.djutils.exceptions.Throw;
8
9
10
11
12
13
14
15
16
17
18
19
20 public class Category implements Serializable
21 {
22
23
24 public static final Category UNCATEGORIZED = new Category(Categorization.UNCATEGORIZED);
25
26
27 private static final long serialVersionUID = 20160921L;
28
29
30 private final Categorization categorization;
31
32
33 private final List<Object> objects = new ArrayList<>();
34
35
36
37
38 private Category(final Categorization categorization)
39 {
40 Throw.whenNull(categorization, "Categorization may not be null.");
41 this.categorization = categorization;
42 }
43
44
45
46
47
48
49
50
51 public Category(final Categorization categorization, final Object object1, final Object... objects)
52 {
53 this(categorization);
54 Throw.when(categorization.size() != objects.length + 1, IllegalArgumentException.class,
55 "Objects do not comply with the categorization; bad number of objects.");
56 Throw.whenNull(object1, "Objects may not be null.");
57 Throw.when(!categorization.get(0).isAssignableFrom(object1.getClass()), IllegalArgumentException.class,
58 "Objects do not comply with the categorization; object 1 is of type %s, should be %s.", object1.getClass(),
59 categorization.get(0));
60 for (int i = 1; i < categorization.size(); i++)
61 {
62 Throw.whenNull(objects[i - 1], "Objects may not be null.");
63 Throw.when(!categorization.get(i).isAssignableFrom(objects[i - 1].getClass()), IllegalArgumentException.class,
64 "Objects do not comply with the categorization; object %d is of type %s, should be %s.", i + 1,
65 objects[i - 1].getClass(), categorization.get(i));
66 }
67 this.objects.add(object1);
68 for (Object object : objects)
69 {
70 this.objects.add(object);
71 }
72 }
73
74
75
76
77
78
79
80 public final Object get(final int i)
81 {
82 Throw.when(i < 0 || i >= this.objects.size(), IndexOutOfBoundsException.class,
83 "Index %d is out of range for categorization of size %d", i, this.objects.size());
84 return this.objects.get(i);
85 }
86
87
88
89
90 public final Categorization getCategorization()
91 {
92 return this.categorization;
93 }
94
95
96
97
98
99
100
101 @SuppressWarnings("unchecked")
102 public final <T> T get(final Class<T> clazz)
103 {
104 Throw.when(!this.categorization.entails(clazz), RuntimeException.class,
105 "Trying to get a categorization object by class, with the class not belonging to the categorization.");
106 for (Object obj : this.objects)
107 {
108 if (clazz.isAssignableFrom(obj.getClass()))
109 {
110 return (T) obj;
111 }
112 }
113 throw new RuntimeException(
114 "Categorization contains no object assignable to given class, even though the categorization entails the class.");
115 }
116
117 @Override
118 public final int hashCode()
119 {
120 final int prime = 31;
121 int result = 1;
122 result = prime * result + ((this.categorization == null) ? 0 : this.categorization.hashCode());
123 result = prime * result + ((this.objects == null) ? 0 : this.objects.hashCode());
124 return result;
125 }
126
127 @Override
128 public final boolean equals(final Object obj)
129 {
130 if (this == obj)
131 {
132 return true;
133 }
134 if (obj == null)
135 {
136 return false;
137 }
138 if (getClass() != obj.getClass())
139 {
140 return false;
141 }
142 Category other = (Category) obj;
143 if (this.categorization == null)
144 {
145 if (other.categorization != null)
146 {
147 return false;
148 }
149 }
150 else if (!this.categorization.equals(other.categorization))
151 {
152 return false;
153 }
154 if (this.objects == null)
155 {
156 if (other.objects != null)
157 {
158 return false;
159 }
160 }
161 else if (!this.objects.equals(other.objects))
162 {
163 return false;
164 }
165 return true;
166 }
167
168 @Override
169 public final String toString()
170 {
171 return "Category [" + this.objects + "]";
172 }
173
174 }