Skip to content

Conversation

@ChrisRackauckas-Claude
Copy link

Summary

  • Fixed a bug where eval_unstructured was failing for multi-dimensional BSpline/NURBS interpolation
  • Added regression tests for BSpline and NURBS eval_unstructured
  • Verified interface compatibility with BigFloat, Float32, and standard arrays

Problem

The eval_unstructured function was throwing a BoundsError when used with multi-dimensional BSpline interpolation (e.g., 2D or higher). For example:

t1 = [-3.14, 1.0, 3.0, 7.6, 12.8]
t2 = [-2.71, 1.41, 12.76, 50.2, 120.0]
t1_eval = t1[1:(end - 1)] + diff(t1) / 2
t2_eval = t2[1:(end - 1)] + diff(t2) / 2

u_bspline = fill(2.0, 6, 7)
itp_bspline = NDInterpolation(
    u_bspline,
    (BSplineInterpolationDimension(t1, 2; t_eval = t1_eval, max_derivative_order_eval = 1),
        BSplineInterpolationDimension(t2, 3; t_eval = t2_eval, max_derivative_order_eval = 1))
)

result = eval_unstructured(itp_bspline)  # This was throwing BoundsError

Root Cause

In eval_kernel, when eval_grid=false, @index(Global, NTuple) returns a 1-tuple (e.g., (1,)). This was passed directly to _interpolate! as multi_point_index. However, the BSpline get_basis_function_values method for tuples expects an N_in-tuple and tries to access multi_point_index[dim_in] for all dimensions, causing a bounds error when dim_in > 1.

Fix

Convert the 1-tuple to a scalar using only(k) before passing to _interpolate! when eval_grid=false. This ensures the correct method dispatch:

  • Scalar Number → unstructured evaluation method
  • N_in-tuple → grid evaluation method

Test plan

  • All existing tests pass
  • New tests added for:
    • BSpline 2D eval_unstructured
    • BSpline eval_unstructured with BigFloat
    • NURBS eval_unstructured

Interface Compatibility Check

This PR also checked interface compatibility:

  • ✅ BigFloat works correctly with all interpolation types
  • ✅ Float32 works correctly with type preservation
  • ✅ ArrayInterface compatible (uses similar(), zero(), one() correctly)
  • ⚠️ JLArrays: fails due to missing synchronize for JLBackend in JLArrays (this is a JLArrays issue, not DataInterpolationsND)

cc @ChrisRackauckas

🤖 Generated with Claude Code

The eval_unstructured function was failing for BSpline interpolation
with more than one dimension because the multi_point_index was being
passed as a 1-tuple (e.g., (i,)) instead of a scalar.

The issue was in eval_kernel: when eval_grid=false, @index(Global, NTuple)
returns a 1-tuple, but the get_basis_function_values method for BSpline
expects either:
- A scalar Number for unstructured evaluation
- An N_in-tuple for grid evaluation

The fix converts the 1-tuple to a scalar using only(k) before passing
to _interpolate! when eval_grid=false.

Also adds regression tests for:
- BSpline 2D eval_unstructured
- BSpline eval_unstructured with BigFloat
- NURBS eval_unstructured

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants