1 package org.opentrafficsim.core.egtf;
2
3 import java.util.LinkedHashMap;
4 import java.util.Map;
5
6 /**
7 * Data source for the EGTF. These are obtained using {@code EGTF.getDataSource()}.
8 * <p>
9 * Copyright (c) 2013-2020 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved. <br>
10 * BSD-style license. See <a href="http://opentrafficsim.org/node/13">OpenTrafficSim License</a>.
11 * <p>
12 * @version $Revision$, $LastChangedDate$, by $Author$, initial version 24 okt. 2018 <br>
13 * @author <a href="http://www.transport.citg.tudelft.nl">Wouter Schakel</a>
14 */
15 public final class DataSource
16 {
17 /** Unique name. */
18 private final String name;
19
20 /** Data stream of this data source. */
21 private final Map<String, DataStream<?>> streams = new LinkedHashMap<>();
22
23 /**
24 * Constructor.
25 * @param name String; unique name
26 */
27 DataSource(final String name)
28 {
29 this.name = name;
30 }
31
32 /**
33 * Returns the name.
34 * @return String; name
35 */
36 public String getName()
37 {
38 return this.name;
39 }
40
41 /**
42 * Add a non-speed stream for the quantity to this data source.
43 * @param quantity Quantity<T, ?>; quantity
44 * @param thetaCong T; standard deviation of this quantity of measurements in congestion by this data source
45 * @param thetaFree T; standard deviation of this quantity of measurements in free flow by this data source
46 * @param <T> implicit data type
47 * @return DataStream; the created data stream
48 * @throws IllegalArgumentException if the quantity is speed
49 */
50 public <T extends Number> DataStream<T> addStream(final Quantity<T, ?> quantity, final T thetaCong, final T thetaFree)
51 {
52 return addStreamSI(quantity, thetaCong.doubleValue(), thetaFree.doubleValue());
53 }
54
55 /**
56 * Add a stream for the quantity to this data source.
57 * @param quantity Quantity<T, ?>; quantity
58 * @param thetaCong double; standard deviation of this quantity of measurements in congestion by this data source in SI
59 * @param thetaFree double; standard deviation of this quantity of measurements in free flow by this data source in SI
60 * @param <T> implicit data type
61 * @return DataStream; the created data stream
62 */
63 public <T extends Number> DataStream<T> addStreamSI(final Quantity<T, ?> quantity, final double thetaCong,
64 final double thetaFree)
65 {
66 if (this.streams.containsKey(quantity.getName()))
67 {
68 throw new IllegalStateException(
69 String.format("Data source %s already has a stream for quantity %s.", this.name, quantity.getName()));
70 }
71 if (thetaCong <= 0.0 || thetaFree <= 0.0)
72 {
73 throw new IllegalArgumentException("Standard deviation must be positive and above 0.");
74 }
75 DataStream<T> dataStream = new DataStream<>(this, quantity, thetaCong, thetaFree);
76 this.streams.put(quantity.getName(), dataStream);
77 return dataStream;
78 }
79
80 /**
81 * Get a stream for the quantity of this data source. If no stream has been created, one will be created with 1.0 standard
82 * deviation.
83 * @param quantity Quantity<T, ?>; quantity
84 * @return DataStream<T>; stream for the quantity of this data source
85 * @param <T> implicit data type
86 */
87 @SuppressWarnings({"unchecked"})
88 public <T extends Number> DataStream<T> getStream(final Quantity<T, ?> quantity)
89 {
90 if (!this.streams.containsKey(quantity.getName()))
91 {
92 addStreamSI(quantity, 1.0, 1.0);
93 }
94 return (DataStream<T>) this.streams.get(quantity.getName());
95 }
96
97 /** {@inheritDoc} */
98 @Override
99 public int hashCode()
100 {
101 final int prime = 31;
102 int result = 1;
103 result = prime * result + ((this.name == null) ? 0 : this.name.hashCode());
104 return result;
105 }
106
107 /** {@inheritDoc} */
108 @Override
109 public boolean equals(final Object obj)
110 {
111 if (this == obj)
112 {
113 return true;
114 }
115 if (obj == null)
116 {
117 return false;
118 }
119 if (getClass() != obj.getClass())
120 {
121 return false;
122 }
123 DataSource../../../org/opentrafficsim/core/egtf/DataSource.html#DataSource">DataSource other = (DataSource) obj;
124 if (this.name == null)
125 {
126 if (other.name != null)
127 {
128 return false;
129 }
130 }
131 else if (!this.name.equals(other.name))
132 {
133 return false;
134 }
135 return true;
136 }
137
138 /** {@inheritDoc} */
139 @Override
140 public String toString()
141 {
142 return "DataSource [" + this.name + "]";
143 }
144
145 }