Skip to content

Memory efficient KRR - #30

Draft
bmalezieux wants to merge 13 commits into
mainfrom
wip_efficient_krr
Draft

Memory efficient KRR#30
bmalezieux wants to merge 13 commits into
mainfrom
wip_efficient_krr

Conversation

@bmalezieux

Copy link
Copy Markdown
Collaborator

No description provided.

@bmalezieux
bmalezieux requested review from clbonet and Copilot November 7, 2025 21:45

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull Request Overview

This PR introduces a memory-efficient implementation of the Kernel Ridge Regression model for the LCOT pipeline. The new implementation reduces memory complexity from O(n_spheres * n_subjects^2) to O(n_subjects^2) through several optimizations including embedding aggregation, chunked computation, and CPU/GPU memory management.

Key changes:

  • New EfficientKernelRidgeRegression model that aggregates sphere embeddings and uses chunked distance computation to avoid OOM errors
  • Replacement of the original KernelRidgeRegression with the efficient version for "lcot" models
  • DataLoader configuration changes: increased num_workers from 0 to 10 and disabled pin_memory

Reviewed Changes

Copilot reviewed 3 out of 3 changed files in this pull request and generated 20 comments.

File Description
src/diff_benchmark/models/efficient_lcot_model.py New memory-efficient Kernel Ridge Regression implementation with chunked computation and optimized CPU/GPU memory management
src/diff_benchmark/models/model_configurations.py Updated model factory to return EfficientKernelRidgeRegression for "lcot" models instead of the original implementation
src/diff_benchmark/dataloaders/dataloaders.py Modified DataLoader settings to use 10 workers and disable pinned memory
Comments suppressed due to low confidence (1)

src/diff_benchmark/models/efficient_lcot_model.py:3

  • Import of 'tqdm' is not used.
from tqdm import tqdm

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +3 to +5
from tqdm import tqdm


Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The tqdm import on line 3 is unused in this file. Consider removing it to keep imports clean.

Suggested change
from tqdm import tqdm

Copilot uses AI. Check for mistakes.
if name == "lcot":
return KernelRidgeRegression(**config)

# return KernelRidgeRegression(**config)

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[nitpick] The old implementation is commented out rather than removed. Since the new EfficientKernelRidgeRegression is intended to replace KernelRidgeRegression, consider removing the commented-out line to keep the code clean. If there's a need to preserve this for reference or rollback purposes, rely on version control history instead.

Suggested change
# return KernelRidgeRegression(**config)

Copilot uses AI. Check for mistakes.
torch.cuda.empty_cache()

print("Prediction complete!")
return torch.cat(all_predictions, dim=0).cpu()

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Redundant .cpu() call on line 331. The predictions are already moved to CPU on line 321 before being appended to all_predictions, so calling .cpu() again after concatenation has no effect and can be removed.

Suggested change
return torch.cat(all_predictions, dim=0).cpu()
return torch.cat(all_predictions, dim=0)

Copilot uses AI. Check for mistakes.
Comment on lines +191 to +192
if embeddings.dim() == 5:
embeddings = embeddings.squeeze(1)

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Using .squeeze(1) without checking which dimension equals 1 could remove the wrong dimension if the batch size is 1. For example, if embeddings has shape (1, n_subjects, n_spheres, n_bvals, d) with a batch size of 1, .squeeze(1) would remove dimension 1 (n_subjects) instead of dimension 0 (batch). Consider using .squeeze(0) to specifically remove the batch dimension, or use more explicit indexing like embeddings[0] if you expect the batch dimension to always be at position 0.

Copilot uses AI. Check for mistakes.
if embeddings.dim() == 5:
embeddings = embeddings.squeeze(1)
if power.dim() == 4:
power = power.squeeze(1)

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Using .squeeze(1) without checking which dimension equals 1 could remove the wrong dimension if the batch size is 1. Consider using .squeeze(0) to specifically remove the batch dimension, or use more explicit indexing like power[0] if you expect the batch dimension to always be at position 0.

Suggested change
power = power.squeeze(1)
power = power.squeeze(0)

Copilot uses AI. Check for mistakes.
Returns:
aggregated: shape (n_subjects, n_bvals, d) - one embedding per subject per bval
"""
n_subjects, n_spheres, n_bvals, d = embeddings.shape

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Variable n_subjects is not used.

Suggested change
n_subjects, n_spheres, n_bvals, d = embeddings.shape
_, n_spheres, n_bvals, d = embeddings.shape

Copilot uses AI. Check for mistakes.
Returns:
aggregated: shape (n_subjects, n_bvals, d) - one embedding per subject per bval
"""
n_subjects, n_spheres, n_bvals, d = embeddings.shape

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Variable n_spheres is not used.

Suggested change
n_subjects, n_spheres, n_bvals, d = embeddings.shape
n_subjects, _, n_bvals, d = embeddings.shape

Copilot uses AI. Check for mistakes.
Returns:
aggregated: shape (n_subjects, n_bvals, d) - one embedding per subject per bval
"""
n_subjects, n_spheres, n_bvals, d = embeddings.shape

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Variable n_bvals is not used.

Suggested change
n_subjects, n_spheres, n_bvals, d = embeddings.shape
n_subjects, n_spheres, _, d = embeddings.shape

Copilot uses AI. Check for mistakes.
Returns:
aggregated: shape (n_subjects, n_bvals, d) - one embedding per subject per bval
"""
n_subjects, n_spheres, n_bvals, d = embeddings.shape

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Variable d is not used.

Suggested change
n_subjects, n_spheres, n_bvals, d = embeddings.shape
n_subjects, n_spheres, n_bvals, _ = embeddings.shape

Copilot uses AI. Check for mistakes.

n = emb1.shape[0]
m = emb2.shape[0]
n_bvals = emb1.shape[1]

Copilot AI Nov 7, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Variable n_bvals is not used.

Suggested change
n_bvals = emb1.shape[1]

Copilot uses AI. Check for mistakes.
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.

5 participants