ReflectPaddingStrategy.java
package com.morphiqlabs.wavelet.padding;
import com.morphiqlabs.wavelet.exception.InvalidArgumentException;
/**
* Reflect padding strategy that mirrors the signal without boundary duplication.
*
* <p>This strategy reflects the signal at its boundaries, excluding the
* boundary points. It avoids discontinuities and is ideal for:</p>
* <ul>
* <li>Smooth signal extensions</li>
* <li>Avoiding boundary point duplication</li>
* <li>Signals where boundary values should not be emphasized</li>
* </ul>
*
* <p>Example: {@code [1, 2, 3, 4]} padded to length 8 becomes {@code [1, 2, 3, 4, 3, 2, 1, 2]}</p>
*/
public record ReflectPaddingStrategy() implements PaddingStrategy {
@Override
public double[] pad(double[] signal, int targetLength) {
if (signal == null) {
throw new InvalidArgumentException("Signal cannot be null");
}
if (signal.length == 0) {
throw new InvalidArgumentException("Signal cannot be empty");
}
if (targetLength < signal.length) {
throw new InvalidArgumentException(
"Target length " + targetLength + " must be >= signal length " + signal.length);
}
if (targetLength == signal.length) {
return signal.clone();
}
// Handle special case of single-element signal
if (signal.length == 1) {
double[] padded = new double[targetLength];
for (int i = 0; i < targetLength; i++) {
padded[i] = signal[0];
}
return padded;
}
double[] padded = new double[targetLength];
System.arraycopy(signal, 0, padded, 0, signal.length);
int padLength = targetLength - signal.length;
int period = 2 * (signal.length - 1); // Period of reflection pattern
for (int i = 0; i < padLength; i++) {
int pos = i % period;
if (pos < signal.length - 1) {
// Forward part: reflect from end (excluding last element)
padded[signal.length + i] = signal[signal.length - 2 - pos];
} else {
// Backward part: reflect from start (excluding first element)
padded[signal.length + i] = signal[pos - signal.length + 2];
}
}
return padded;
}
@Override
public String name() {
return "reflect";
}
@Override
public String description() {
return "Reflect padding - mirrors signal without boundary duplication";
}
}