#!/usr/bin/env python3
"""
Example usage of the fast-resample package.
"""

import time

import numpy as np

from sgnl_cpu_interp import upsample


def benchmark_example():
    """Run a benchmark comparing different configurations."""

    print("=== Fast Resample Benchmark ===\n")

    # Test parameters
    configs = [
        (1024, 128, 2, 8),  # 128 channels, 2x upsampling
        (1024, 512, 2, 8),  # 512 channels, 2x upsampling
        (1024, 1024, 2, 8),  # 1024 channels, 2x upsampling
        (1024, 128, 4, 8),  # 128 channels, 4x upsampling
    ]

    for n_samples, n_channels, factor, half_length in configs:
        # Create test data
        data = np.random.randn(n_samples, n_channels).astype(np.float32)

        # Warmup
        _ = upsample(data, factor=factor, half_length=half_length)

        # Benchmark
        n_iters = 100
        times = []

        for _ in range(n_iters):
            start = time.perf_counter()
            result = upsample(data, factor=factor, half_length=half_length)
            end = time.perf_counter()
            times.append(end - start)

        times = np.array(times) * 1000  # Convert to ms

        print(f"Config: {n_channels} channels, {factor}x upsampling")
        print(f"  Input:  {data.shape}")
        print(f"  Output: {result.shape}")
        print(f"  Time:   {times.mean():.3f} ± {times.std():.3f} ms")
        print(f"  Min:    {times.min():.3f} ms")
        print(f"  Max:    {times.max():.3f} ms")
        print()


def simple_example():
    """Simple usage example."""

    print("=== Simple Example ===\n")

    # Create a simple sine wave with 4 channels
    n_samples = 100
    n_channels = 4
    t = np.linspace(0, 1, n_samples)

    # Each channel has a different frequency
    data = np.zeros((n_samples, n_channels), dtype=np.float32)
    for ch in range(n_channels):
        freq = (ch + 1) * 2  # 2, 4, 6, 8 Hz
        data[:, ch] = np.sin(2 * np.pi * freq * t)

    print(f"Input shape:  {data.shape}")

    # Upsample by factor of 4
    upsampled = upsample(data, factor=4, half_length=16)

    print(f"Output shape: {upsampled.shape}")
    print(f"\nUpsampled {data.shape[0]} samples to {upsampled.shape[0]} samples")
    print(f"Lost {2 * 16} edge samples due to convolution")

    # Verify shape
    expected_samples = (n_samples - 2 * 16) * 4
    assert upsampled.shape[0] == expected_samples
    print("\n✓ Shape verification passed")


def single_channel_example():
    """Example with single-channel data."""

    print("\n=== Single Channel Example ===\n")

    # Create 1D signal
    t = np.linspace(0, 1, 50)
    signal = np.sin(2 * np.pi * 5 * t).astype(np.float32)

    print(f"Input shape:  {signal.shape}")

    # Upsample - function automatically handles 1D input
    upsampled = upsample(signal, factor=2, half_length=8)

    print(f"Output shape: {upsampled.shape}")
    print("\n✓ Single channel upsampling works!")


if __name__ == "__main__":
    simple_example()
    single_channel_example()
    benchmark_example()
