Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Take advantage of separable basis functions #1530

Open
unalmis opened this issue Jan 20, 2025 · 2 comments · May be fixed by #1405
Open

Take advantage of separable basis functions #1530

unalmis opened this issue Jan 20, 2025 · 2 comments · May be fixed by #1405
Labels
performance New feature or request to make the code faster transforms Related to the spectral-real space transformations

Comments

@unalmis
Copy link
Collaborator

unalmis commented Jan 20, 2025

Right now, anytime we compute a series expansion, for all of the basis classes in DESC, the resulting Vandermonde matrix is computed by first forming an outer product of the mode numbers then evaluating the basis functions.

For each point $x$, this generates a large mode matrix $A(x)$ of size $L M N$. If there are $P$ points then the matrix $A$ has size $P L M N$. From this matrix all the basis functions $f \colon A \mapsto f(A)$ are evaluated. In the performance analysis for this type of stuff, the dominant expense is by far evaluating $f$. Hence, this is an inefficient approach to computing the Vandermonde matrix because $f$ must be evaluated at $P L M N$ times.

Now, because the basis function associated with any given spectral coefficient $a_{l,m,n}$ are separable in the spatial dimensions, more efficient methods can be used to generate the Vandermonde matrix. In particular for any basis the $K$ dimensional Vandermonde matrix should be computed by

  1. first forming $K$ one-dimensional Vandermonde matrices ${V_i | i \in (1,...,K)}$ in each spatial coordinate
  2. Computing the basis functions on these matrices ${f(V_i) | i \in (1,...,K)} $
  3. Generate the desired $K$ dimensional Vandermonde by taking the outer product $f(V_1) \otimes f(V_2) \otimes, \dots, \otimes f(V_K)$

This reduces the computational cost from $\mathcal{O}(P L M N)$ to $\mathcal{O}(P [L + M + N])$ and can be done without making any assumptions on the grid or computing auxiliary data. I have already updated the DoubleFourierSeries basis in #1440 with this change and it should be simple to extend it to the other basis.

This can be done in complement to the partial summation techniques discussed in #1154 and #1243 .

@unalmis unalmis added the performance New feature or request to make the code faster label Jan 20, 2025
@f0uriest
Copy link
Member

I think the unique option of Basis.evaluate already sort of does this, and is improved in #1405 to not need repeated calls to np.unique

@unalmis
Copy link
Collaborator Author

unalmis commented Jan 21, 2025

  1. That option is not JIT compilable or differentiable.
  2. Calling np.unique and then indexing the unique modes and expanding them with gather operations are unnecessary and somewhat expensive. It also involves storing more things in memory.

@YigitElma YigitElma added the transforms Related to the spectral-real space transformations label Jan 22, 2025
@unalmis unalmis linked a pull request Jan 23, 2025 that will close this issue
unalmis added a commit that referenced this issue Jan 23, 2025
so that the local singular integration region can be
modeled as a circle in theta, zeta space or ideally as
a circle in real space by some clever choice from the user.

Apply the strategy of #1530 to bounce integral interpolation.
This is a crutch to hold out until the nuffts are added to DESC.

Move Fourier conversion utilities to vmec_utils as mentioned in #1531
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
performance New feature or request to make the code faster transforms Related to the spectral-real space transformations
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants