FieldCachedTransformProvider.java
- /* Copyright 2022-2025 Thales Alenia Space
- * Licensed to CS GROUP (CS) under one or more
- * contributor license agreements. See the NOTICE file distributed with
- * this work for additional information regarding copyright ownership.
- * CS licenses this file to You under the Apache License, Version 2.0
- * (the "License"); you may not use this file except in compliance with
- * the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
- package org.orekit.frames;
- import org.hipparchus.CalculusFieldElement;
- import org.orekit.time.FieldAbsoluteDate;
- import java.util.LinkedHashMap;
- import java.util.Map;
- import java.util.concurrent.locks.ReentrantLock;
- import java.util.function.Function;
- /** Thread-safe cached provider for frame transforms.
- * <p>
- * This provider is based on a thread-safe Least Recently Used cache
- * using date as it access key, hence saving computation time on
- * transform building.
- * </p>
- * <p>
- * This class is thread-safe.
- * </p>
- * @param <T> type of the field elements
- * @author Luc Maisonobe
- * @since 13.0.3
- */
- public class FieldCachedTransformProvider<T extends CalculusFieldElement<T>> {
- /** Origin frame. */
- private final Frame origin;
- /** Destination frame. */
- private final Frame destination;
- /** Number of transforms kept in the date-based cache. */
- private final int cacheSize;
- /** Generator for full transforms. */
- private final Function<FieldAbsoluteDate<T>, FieldTransform<T>> fullGenerator;
- /** Generator for kinematic transforms. */
- private final Function<FieldAbsoluteDate<T>, FieldKinematicTransform<T>> kinematicGenerator;
- /** Generator for static transforms. */
- private final Function<FieldAbsoluteDate<T>, FieldStaticTransform<T>> staticGenerator;
- /** Lock for concurrent access. */
- private final ReentrantLock lock;
- /** Transforms LRU cache. */
- private final Map<FieldAbsoluteDate<T>, FieldTransform<T>> fullCache;
- /** Transforms LRU cache. */
- private final Map<FieldAbsoluteDate<T>, FieldKinematicTransform<T>> kinematicCache;
- /** Transforms LRU cache. */
- private final Map<FieldAbsoluteDate<T>, FieldStaticTransform<T>> staticCache;
- /**
- * Simple constructor.
- * @param origin origin frame
- * @param destination destination frame
- * @param fullGenerator generator for full transforms
- * @param kinematicGenerator generator for kinematic transforms
- * @param staticGenerator generator for static transforms
- * @param cacheSize number of transforms kept in the date-based cache
- */
- public FieldCachedTransformProvider(final Frame origin, final Frame destination,
- final Function<FieldAbsoluteDate<T>, FieldTransform<T>> fullGenerator,
- final Function<FieldAbsoluteDate<T>, FieldKinematicTransform<T>> kinematicGenerator,
- final Function<FieldAbsoluteDate<T>, FieldStaticTransform<T>> staticGenerator,
- final int cacheSize) {
- this.origin = origin;
- this.destination = destination;
- this.cacheSize = cacheSize;
- this.fullGenerator = fullGenerator;
- this.kinematicGenerator = kinematicGenerator;
- this.staticGenerator = staticGenerator;
- this.lock = new ReentrantLock();
- // cache for full transforms
- this.fullCache = new LinkedHashMap<FieldAbsoluteDate<T>, FieldTransform<T>>(cacheSize, 0.75f, true) {
- /** {@inheritDoc} */
- @Override
- protected boolean removeEldestEntry(final Map.Entry<FieldAbsoluteDate<T>, FieldTransform<T>> eldest) {
- return size() > cacheSize;
- }
- };
- // cache for kinematic transforms
- this.kinematicCache = new LinkedHashMap<FieldAbsoluteDate<T>, FieldKinematicTransform<T>>(cacheSize, 0.75f, true) {
- /** {@inheritDoc} */
- @Override
- protected boolean removeEldestEntry(final Map.Entry<FieldAbsoluteDate<T>, FieldKinematicTransform<T>> eldest) {
- return size() > cacheSize;
- }
- };
- // cache for static transforms
- this.staticCache = new LinkedHashMap<FieldAbsoluteDate<T>, FieldStaticTransform<T>>(cacheSize, 0.75f, true) {
- /** {@inheritDoc} */
- @Override
- protected boolean removeEldestEntry(final Map.Entry<FieldAbsoluteDate<T>, FieldStaticTransform<T>> eldest) {
- return size() > cacheSize;
- }
- };
- }
- /** Get origin frame.
- * @return origin frame
- */
- public Frame getOrigin() {
- return origin;
- }
- /** Get destination frame.
- * @return destination frame
- */
- public Frame getDestination() {
- return destination;
- }
- /** Get the nmber of transforms kept in the date-based cache.
- * @return nmber of transforms kept in the date-based cache
- */
- public int getCacheSize() {
- return cacheSize;
- }
- /** Get the {@link Transform} corresponding to specified date.
- * @param date current date
- * @return transform at specified date
- */
- public FieldTransform<T> getTransform(final FieldAbsoluteDate<T> date) {
- lock.lock();
- try {
- return fullCache.computeIfAbsent(date, fullGenerator);
- } finally {
- lock.unlock();
- }
- }
- /** Get the {@link Transform} corresponding to specified date.
- * @param date current date
- * @return transform at specified date
- */
- public FieldKinematicTransform<T> getKinematicTransform(final FieldAbsoluteDate<T> date) {
- lock.lock();
- try {
- return kinematicCache.computeIfAbsent(date, kinematicGenerator);
- } finally {
- lock.unlock();
- }
- }
- /** Get the {@link Transform} corresponding to specified date.
- * @param date current date
- * @return transform at specified date
- */
- public FieldStaticTransform<T> getStaticTransform(final FieldAbsoluteDate<T> date) {
- lock.lock();
- try {
- return staticCache.computeIfAbsent(date, staticGenerator);
- } finally {
- lock.unlock();
- }
- }
- }