Skip to content

Commit 51d1163

Browse files
committed
chore: address comments
1 parent 97be7a8 commit 51d1163

File tree

2 files changed

+11
-14
lines changed

2 files changed

+11
-14
lines changed

core/src/main/java/ai/timefold/solver/core/impl/heuristic/selector/move/generic/list/ListChangeMoveSelectorFactory.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ protected MoveSelector<Solution_> buildBaseMoveSelector(HeuristicConfigPolicy<So
6969
}
7070
if (enableEntityValueRangeFilter && entityValueRangeRecorderId == null) {
7171
throw new IllegalStateException(
72-
"When enabling entity value range, the origin value selector ID is required for the destination selector %s."
72+
"Impossible state: when enabling entity value range, the origin value selector ID is required for the destination selector %s."
7373
.formatted(destinationSelectorConfig));
7474
}
7575

core/src/main/java/ai/timefold/solver/core/impl/score/director/ValueRangeManager.java

Lines changed: 10 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
11
package ai.timefold.solver.core.impl.score.director;
22

3+
import java.util.Arrays;
34
import java.util.Collections;
45
import java.util.IdentityHashMap;
56
import java.util.LinkedHashSet;
6-
import java.util.List;
77
import java.util.Map;
88
import java.util.Objects;
99
import java.util.Set;
@@ -26,7 +26,6 @@
2626
import ai.timefold.solver.core.impl.domain.variable.descriptor.ListVariableDescriptor;
2727
import ai.timefold.solver.core.impl.domain.variable.descriptor.VariableDescriptor;
2828
import ai.timefold.solver.core.impl.heuristic.selector.common.ReachableValues;
29-
import ai.timefold.solver.core.impl.util.CollectionUtils;
3029
import ai.timefold.solver.core.impl.util.MathUtils;
3130
import ai.timefold.solver.core.impl.util.MutableInt;
3231
import ai.timefold.solver.core.impl.util.MutableLong;
@@ -58,8 +57,8 @@
5857
public final class ValueRangeManager<Solution_> {
5958

6059
private final SolutionDescriptor<Solution_> solutionDescriptor;
61-
private final List<CountableValueRange<?>> fromSolutionList;
62-
private final Map<Object, List<CountableValueRange<?>>> fromEntityMap =
60+
private final CountableValueRange<?>[] fromSolutionList;
61+
private final Map<Object, CountableValueRange<?>[]> fromEntityMap =
6362
new IdentityHashMap<>();
6463
private @Nullable ReachableValues reachableValues = null;
6564

@@ -82,7 +81,7 @@ public static <Solution_> ValueRangeManager<Solution_> of(SolutionDescriptor<Sol
8281
*/
8382
public ValueRangeManager(SolutionDescriptor<Solution_> solutionDescriptor) {
8483
this.solutionDescriptor = Objects.requireNonNull(solutionDescriptor);
85-
this.fromSolutionList = CollectionUtils.newNullList(solutionDescriptor.getValueRangeDescriptorCount());
84+
this.fromSolutionList = new CountableValueRange[solutionDescriptor.getValueRangeDescriptorCount()];
8685
}
8786

8887
public SolutionInitializationStatistics getInitializationStatistics() {
@@ -357,7 +356,7 @@ public <T> CountableValueRange<T> getFromSolution(ValueRangeDescriptor<Solution_
357356
@SuppressWarnings("unchecked")
358357
public <T> CountableValueRange<T> getFromSolution(ValueRangeDescriptor<Solution_> valueRangeDescriptor,
359358
Solution_ solution) {
360-
var valueRange = fromSolutionList.get(valueRangeDescriptor.getOrdinal());
359+
var valueRange = fromSolutionList[valueRangeDescriptor.getOrdinal()];
361360
if (valueRange == null) { // Avoid computeIfAbsent on the hot path; creates capturing lambda instances.
362361
var extractedValueRange = valueRangeDescriptor.<T> extractAllValues(Objects.requireNonNull(solution));
363362
if (!(extractedValueRange instanceof CountableValueRange<T> countableValueRange)) {
@@ -371,7 +370,7 @@ public <T> CountableValueRange<T> getFromSolution(ValueRangeDescriptor<Solution_
371370
} else {
372371
valueRange = countableValueRange;
373372
}
374-
fromSolutionList.set(valueRangeDescriptor.getOrdinal(), valueRange);
373+
fromSolutionList[valueRangeDescriptor.getOrdinal()] = valueRange;
375374
}
376375
return (CountableValueRange<T>) valueRange;
377376
}
@@ -388,8 +387,8 @@ public <T> CountableValueRange<T> getFromEntity(ValueRangeDescriptor<Solution_>
388387
}
389388
var valueRangeList =
390389
fromEntityMap.computeIfAbsent(entity,
391-
e -> CollectionUtils.newNullList(solutionDescriptor.getValueRangeDescriptorCount()));
392-
var valueRange = valueRangeList.get(valueRangeDescriptor.getOrdinal());
390+
e -> new CountableValueRange[solutionDescriptor.getValueRangeDescriptorCount()]);
391+
var valueRange = valueRangeList[valueRangeDescriptor.getOrdinal()];
393392
if (valueRange == null) { // Avoid computeIfAbsent on the hot path; creates capturing lambda instances.
394393
var extractedValueRange =
395394
valueRangeDescriptor.<T> extractValuesFromEntity(cachedWorkingSolution, Objects.requireNonNull(entity));
@@ -404,7 +403,7 @@ public <T> CountableValueRange<T> getFromEntity(ValueRangeDescriptor<Solution_>
404403
} else {
405404
valueRange = countableValueRange;
406405
}
407-
valueRangeList.set(valueRangeDescriptor.getOrdinal(), valueRange);
406+
valueRangeList[valueRangeDescriptor.getOrdinal()] = valueRange;
408407
}
409408
return (CountableValueRange<T>) valueRange;
410409
}
@@ -483,9 +482,7 @@ private static void updateValueMap(Map<Object, Set<Object>> valueMatrix, Countab
483482
}
484483

485484
public void reset(@Nullable Solution_ workingSolution) {
486-
var size = fromSolutionList.size();
487-
fromSolutionList.clear();
488-
fromSolutionList.addAll(CollectionUtils.newNullList(size));
485+
Arrays.fill(fromSolutionList, null);
489486
fromEntityMap.clear();
490487
reachableValues = null;
491488
// We only update the cached solution if it is not null; null means to only reset the maps.

0 commit comments

Comments
 (0)