001 /*
002 * Java Genetic Algorithm Library (jenetics-3.8.0).
003 * Copyright (c) 2007-2017 Franz Wilhelmstötter
004 *
005 * Licensed under the Apache License, Version 2.0 (the "License");
006 * you may not use this file except in compliance with the License.
007 * You may obtain a copy of the License at
008 *
009 * http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 *
017 * Author:
018 * Franz Wilhelmstötter (franz.wilhelmstoetter@gmx.at)
019 */
020 package org.jenetics;
021
022 import static org.jenetics.util.ISeq.toISeq;
023
024 import java.io.IOException;
025 import java.io.ObjectInputStream;
026 import java.io.ObjectOutputStream;
027 import java.io.Serializable;
028 import java.util.List;
029
030 import javax.xml.bind.annotation.XmlAccessType;
031 import javax.xml.bind.annotation.XmlAccessorType;
032 import javax.xml.bind.annotation.XmlAttribute;
033 import javax.xml.bind.annotation.XmlElement;
034 import javax.xml.bind.annotation.XmlRootElement;
035 import javax.xml.bind.annotation.XmlType;
036 import javax.xml.bind.annotation.adapters.XmlAdapter;
037 import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;
038
039 import org.jenetics.internal.util.Equality;
040 import org.jenetics.internal.util.Hash;
041
042 import org.jenetics.util.ISeq;
043 import org.jenetics.util.LongRange;
044 import org.jenetics.util.MSeq;
045
046 /**
047 * Numeric chromosome implementation which holds 64 bit integer numbers.
048 *
049 * @author <a href="mailto:franz.wilhelmstoetter@gmx.at">Franz Wilhelmstötter</a>
050 * @since 1.6
051 * @version 3.2
052 */
053 @XmlJavaTypeAdapter(LongChromosome.Model.Adapter.class)
054 public class LongChromosome
055 extends AbstractBoundedChromosome<Long, LongGene>
056 implements
057 NumericChromosome<Long, LongGene>,
058 Serializable
059 {
060 private static final long serialVersionUID = 1L;
061
062
063 protected LongChromosome(final ISeq<LongGene> genes) {
064 super(genes);
065 }
066
067 /**
068 * Create a new random {@code LongChromosome}.
069 *
070 * @param min the min value of the {@link LongGene}s (inclusively).
071 * @param max the max value of the {@link LongGene}s (inclusively).
072 * @param length the length of the chromosome.
073 * @throws NullPointerException if one of the arguments is {@code null}.
074 * @throws IllegalArgumentException if the {@code length} is smaller than
075 * one.
076 */
077 public LongChromosome(final Long min, final Long max, final int length) {
078 this(LongGene.seq(min, max, length));
079 _valid = true;
080 }
081
082 /**
083 * Create a new random {@code LongChromosome} of length one.
084 *
085 * @param min the minimal value of this chromosome (inclusively).
086 * @param max the maximal value of this chromosome (inclusively).
087 * @throws NullPointerException if one of the arguments is {@code null}.
088 */
089 public LongChromosome(final Long min, final Long max) {
090 this(min, max, 1);
091 }
092
093 /**
094 * Returns an long array containing all of the elements in this chromosome
095 * in proper sequence. If the chromosome fits in the specified array, it is
096 * returned therein. Otherwise, a new array is allocated with the length of
097 * this chromosome.
098 *
099 * @since 3.0
100 *
101 * @param array the array into which the elements of this chromosomes are to
102 * be stored, if it is big enough; otherwise, a new array is
103 * allocated for this purpose.
104 * @return an array containing the elements of this chromosome
105 * @throws NullPointerException if the given {@code array} is {@code null}
106 */
107 public long[] toArray(final long[] array) {
108 final long[] a = array.length >= length() ?
109 array : new long[length()];
110
111 for (int i = length(); --i >= 0;) {
112 a[i] = longValue(i);
113 }
114
115 return a;
116 }
117
118 /**
119 * Returns an long array containing all of the elements in this chromosome
120 * in proper sequence.
121 *
122 * @since 3.0
123 *
124 * @return an array containing the elements of this chromosome
125 */
126 public long[] toArray() {
127 return toArray(new long[length()]);
128 }
129
130 /**
131 * Create a new {@code LongChromosome} with the given genes.
132 *
133 * @param genes the genes of the chromosome.
134 * @return a new chromosome with the given genes.
135 * @throws IllegalArgumentException if the length of the genes array is
136 * empty.
137 * @throws NullPointerException if the given {@code genes} are {@code null}
138 */
139 public static LongChromosome of(final LongGene... genes) {
140 return new LongChromosome(ISeq.of(genes));
141 }
142
143 /**
144 * Create a new random {@code LongChromosome}.
145 *
146 * @param min the min value of the {@link LongGene}s (inclusively).
147 * @param max the max value of the {@link LongGene}s (inclusively).
148 * @param length the length of the chromosome.
149 * @return a new {@code LongChromosome} with the given gene parameters.
150 * @throws IllegalArgumentException if the {@code length} is smaller than
151 * one.
152 */
153 public static LongChromosome of(
154 final long min,
155 final long max,
156 final int length
157 ) {
158 return new LongChromosome(min, max, length);
159 }
160
161 /**
162 * Create a new random {@code LongChromosome}.
163 *
164 * @since 3.2
165 *
166 * @param range the long range of the chromosome.
167 * @param length the length of the chromosome.
168 * @return a new random {@code LongChromosome}
169 * @throws NullPointerException if the given {@code range} is {@code null}
170 * @throws IllegalArgumentException if the {@code length} is smaller than
171 * one.
172 */
173 public static LongChromosome of(final LongRange range, final int length) {
174 return new LongChromosome(range.getMin(), range.getMax(), length);
175 }
176
177 /**
178 * Create a new random {@code LongChromosome} of length one.
179 *
180 * @param min the minimal value of this chromosome (inclusively).
181 * @param max the maximal value of this chromosome (inclusively).
182 * @return a new {@code LongChromosome} with the given gene parameters.
183 */
184 public static LongChromosome of(final long min, final long max) {
185 return new LongChromosome(min, max);
186 }
187
188 /**
189 * Create a new random {@code LongChromosome} of length one.
190 *
191 * @since 3.2
192 *
193 * @param range the long range of the chromosome.
194 * @return a new random {@code LongChromosome} of length one
195 * @throws NullPointerException if the given {@code range} is {@code null}
196 */
197 public static LongChromosome of(final LongRange range) {
198 return new LongChromosome(range.getMin(), range.getMax());
199 }
200
201 @Override
202 public LongChromosome newInstance(final ISeq<LongGene> genes) {
203 return new LongChromosome(genes);
204 }
205
206 @Override
207 public LongChromosome newInstance() {
208 return new LongChromosome(_min, _max, length());
209 }
210
211 @Override
212 public int hashCode() {
213 return Hash.of(getClass()).and(super.hashCode()).value();
214 }
215
216 @Override
217 public boolean equals(final Object obj) {
218 return Equality.of(this, obj).test(super::equals);
219 }
220
221 /* *************************************************************************
222 * Java object serialization
223 * ************************************************************************/
224
225 private void writeObject(final ObjectOutputStream out)
226 throws IOException
227 {
228 out.defaultWriteObject();
229
230 out.writeInt(length());
231 out.writeLong(_min);
232 out.writeLong(_max);
233
234 for (LongGene gene : _genes) {
235 out.writeLong(gene.getAllele());
236 }
237 }
238
239 private void readObject(final ObjectInputStream in)
240 throws IOException, ClassNotFoundException
241 {
242 in.defaultReadObject();
243
244 final MSeq<LongGene> genes = MSeq.ofLength(in.readInt());
245 _min = in.readLong();
246 _max = in.readLong();
247
248 for (int i = 0; i < genes.length(); ++i) {
249 genes.set(i, new LongGene(in.readLong(), _min, _max));
250 }
251
252 _genes = genes.toISeq();
253 }
254
255 /* *************************************************************************
256 * JAXB object serialization
257 * ************************************************************************/
258
259 @XmlRootElement(name = "long-chromosome")
260 @XmlType(name = "org.jenetics.LongChromosome")
261 @XmlAccessorType(XmlAccessType.FIELD)
262 final static class Model {
263
264 @XmlAttribute(name = "length", required = true)
265 public int length;
266
267 @XmlAttribute(name = "min", required = true)
268 public long min;
269
270 @XmlAttribute(name = "max", required = true)
271 public long max;
272
273 @XmlElement(name = "allele", required = true, nillable = false)
274 public List<Long> values;
275
276 public final static class Adapter
277 extends XmlAdapter<Model, LongChromosome>
278 {
279 @Override
280 public Model marshal(final LongChromosome c) {
281 final Model m = new Model();
282 m.length = c.length();
283 m.min = c._min;
284 m.max = c._max;
285 m.values = c.toSeq().map(LongGene::getAllele).asList();
286 return m;
287 }
288
289 @Override
290 public LongChromosome unmarshal(final Model model) {
291 final Long min = model.min;
292 final Long max = model.max;
293 return new LongChromosome(
294 model.values.stream()
295 .map(value -> new LongGene(value, min, max))
296 .collect(toISeq())
297 );
298 }
299 }
300 }
301 }
|