pub struct EagerRuntime { /* private fields */ }Expand description
Shared eager execution context for tensors on a backend.
Reusing one context lets eager tensors share backend state, extension runtime caches, and gradient storage across a computation.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime, EagerTensor, Tensor};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
let x = EagerTensor::from_tensor_in(Tensor::from_vec_col_major(vec![1], vec![1.0_f64]).unwrap(), ctx.clone()).unwrap();
let y = EagerTensor::from_tensor_in(Tensor::from_vec_col_major(vec![1], vec![2.0_f64]).unwrap(), ctx).unwrap();
let z = x.add(&y).unwrap();
assert_eq!(z.materialized().unwrap().as_slice::<f64>().unwrap(), &[3.0]);Implementations§
Source§impl EagerRuntime
impl EagerRuntime
Sourcepub fn new() -> Arc<Self>
pub fn new() -> Arc<Self>
Create a shared CPU eager execution context.
§Examples
use tenferro_ad::EagerRuntime;
let ctx = EagerRuntime::new();
assert_eq!(std::sync::Arc::strong_count(&ctx), 1);Sourcepub fn with_cpu_backend(backend: CpuBackend) -> Arc<Self>
pub fn with_cpu_backend(backend: CpuBackend) -> Arc<Self>
Create a shared eager execution context from a configured CPU backend.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::with_threads(1).unwrap());
assert_eq!(std::sync::Arc::strong_count(&ctx), 1);Sourcepub fn with_cpu_backend_and_ad_context(
backend: CpuBackend,
ad: &AdContext,
) -> Arc<Self>
pub fn with_cpu_backend_and_ad_context( backend: CpuBackend, ad: &AdContext, ) -> Arc<Self>
Create a shared CPU eager context with explicit AD extension rules.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{AdContext, EagerRuntime};
let ad = AdContext::builder().build().unwrap();
let ctx = EagerRuntime::with_cpu_backend_and_ad_context(CpuBackend::new(), &ad);
assert_eq!(std::sync::Arc::strong_count(&ctx), 1);Sourcepub fn id(&self) -> ContextId
pub fn id(&self) -> ContextId
Return an opaque identifier for this context.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
assert_ne!(ctx.id(), EagerRuntime::with_cpu_backend(CpuBackend::new()).id());Sourcepub fn register_extension(
&self,
register: impl FnOnce(&mut ExtensionExecutor<EagerBackend>) -> Result<(), ExtensionRuntimeRegistryError>,
) -> Result<(), ExtensionRuntimeRegistryError>
pub fn register_extension( &self, register: impl FnOnce(&mut ExtensionExecutor<EagerBackend>) -> Result<(), ExtensionRuntimeRegistryError>, ) -> Result<(), ExtensionRuntimeRegistryError>
Register one extension runtime on this eager context.
Sourcepub fn clear_extension_caches(&self) -> Result<()>
pub fn clear_extension_caches(&self) -> Result<()>
Clear generic extension runtime cache entries.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
ctx.clear_extension_caches()?;
assert_eq!(ctx.cache_stats()?.extensions.entries, 0);Sourcepub fn clear_caches(&self) -> Result<()>
pub fn clear_caches(&self) -> Result<()>
Clear every cache owned by this eager context.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
ctx.clear_caches()?;
assert_eq!(ctx.cache_stats()?.extensions.entries, 0);Sourcepub fn cache_stats(&self) -> Result<EagerRuntimeCacheStats>
pub fn cache_stats(&self) -> Result<EagerRuntimeCacheStats>
Return eager runtime cache-entry and retained-byte stats.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
let stats = ctx.cache_stats()?;
assert_eq!(stats.extensions.entries, 0);Sourcepub fn extension_cache_limits(&self) -> Result<ExtensionCacheLimits>
pub fn extension_cache_limits(&self) -> Result<ExtensionCacheLimits>
Return the extension cache retention limits.
Sourcepub fn set_extension_cache_limits(
&self,
limits: ExtensionCacheLimits,
) -> Result<()>
pub fn set_extension_cache_limits( &self, limits: ExtensionCacheLimits, ) -> Result<()>
Replace extension cache retention limits.
Sourcepub fn with_extension_caches_mut<R>(
&self,
f: impl FnOnce(&mut ExtensionCacheStore) -> R,
) -> Result<R>
pub fn with_extension_caches_mut<R>( &self, f: impl FnOnce(&mut ExtensionCacheStore) -> R, ) -> Result<R>
Mutably borrow generic extension runtime cache storage.
This hook is for standard extension crates that need cache entries owned by an eager runtime while preserving eager value semantics outside a registered extension execution boundary.
§Examples
use tenferro_ad::EagerRuntime;
use tenferro_cpu::CpuBackend;
use tenferro_runtime::ExtensionCacheKey;
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
let key = ExtensionCacheKey::new("example.cache.v1", "plans", 1);
ctx.with_extension_caches_mut(|caches| {
caches.put(key, 7_usize, std::mem::size_of::<usize>());
});
assert_eq!(ctx.cache_stats().unwrap().extensions.entries, 1);Sourcepub fn with_backend_mut<R>(
&self,
f: impl FnOnce(&mut EagerBackend) -> R,
) -> Result<R>
pub fn with_backend_mut<R>( &self, f: impl FnOnce(&mut EagerBackend) -> R, ) -> Result<R>
Mutably borrow this runtime’s backend.
This hook lets standard extension crates run a whole contraction program in a single backend session (instead of one eager op per step) while preserving eager value semantics for untracked tensors.
§Examples
use tenferro_ad::EagerRuntime;
use tenferro_cpu::CpuBackend;
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
// The closure receives `&mut EagerBackend`; standard extension crates
// use it to open one backend session for a whole contraction program.
let answer = ctx.with_backend_mut(|_backend| 42).unwrap();
assert_eq!(answer, 42);Sourcepub fn synchronize(&self) -> Result<()>
pub fn synchronize(&self) -> Result<()>
Block the current thread until backend work submitted by this eager runtime completes.
CPU runtimes return immediately. CUDA and WebGPU runtimes synchronize their current backend work queue.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::EagerRuntime;
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
ctx.synchronize().unwrap();Sourcepub fn clear_grads(&self) -> Result<()>
pub fn clear_grads(&self) -> Result<()>
Clear all live gradient slots tracked by this context.
This resets the stored gradients to None without unregistering the
tensors, so future backward() calls can accumulate again.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime, EagerTensor, Tensor};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
let x = EagerTensor::requires_grad_in(Tensor::from_vec_col_major(vec![3], vec![1.0_f64, 2.0, 3.0]).unwrap(), ctx.clone()).unwrap();
let y = EagerTensor::requires_grad_in(Tensor::from_vec_col_major(vec![3], vec![4.0_f64, 5.0, 6.0]).unwrap(), ctx.clone()).unwrap();
let loss = x.mul(&y).unwrap().reduce_sum(&[0]).unwrap();
let _ = loss.backward().unwrap();
ctx.clear_grads()?;
assert!(x.grad()?.is_none());
assert!(y.grad()?.is_none());Sourcepub fn constant_from(self: &Arc<Self>, tensor: Tensor) -> Result<EagerTensor>
pub fn constant_from(self: &Arc<Self>, tensor: Tensor) -> Result<EagerTensor>
Import a concrete tensor into this context as an untracked constant.
The returned tensor does not participate in gradient tracking. Use this for fixed masks, quadrature weights, physical constants, and other data that should not receive gradients.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime, EagerTensor, Tensor};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
let c = ctx.constant_from(Tensor::from_vec_col_major(vec![2], vec![1.0_f64, 2.0]).unwrap())?;
let x = EagerTensor::requires_grad_in(Tensor::from_vec_col_major(vec![2], vec![3.0_f64, 4.0]).unwrap(), ctx)?;
let z = x.add(&c).unwrap();
assert_eq!(z.materialized()?.as_slice::<f64>().unwrap(), &[4.0, 6.0]);Sourcepub fn variable_from(self: &Arc<Self>, tensor: Tensor) -> Result<EagerTensor>
pub fn variable_from(self: &Arc<Self>, tensor: Tensor) -> Result<EagerTensor>
Import a concrete tensor into this context as a trainable variable.
The returned tensor participates in gradient tracking; its gradient slot is registered in this context.
§Examples
use tenferro_cpu::CpuBackend;
use tenferro_ad::{EagerRuntime, EagerTensor, Tensor};
let ctx = EagerRuntime::with_cpu_backend(CpuBackend::new());
let p = ctx.variable_from(Tensor::from_vec_col_major(vec![2], vec![1.0_f64, 2.0]).unwrap())?;
let loss = p.exp().unwrap().reduce_sum(&[0]).unwrap();
let _ = loss.backward().unwrap();
let grad = p.grad().unwrap().unwrap();
assert_eq!(grad.shape(), &[2]);Trait Implementations§
Auto Trait Implementations§
impl !Freeze for EagerRuntime
impl !RefUnwindSafe for EagerRuntime
impl Send for EagerRuntime
impl Sync for EagerRuntime
impl Unpin for EagerRuntime
impl UnsafeUnpin for EagerRuntime
impl !UnwindSafe for EagerRuntime
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
§impl<T> DistributionExt for Twhere
T: ?Sized,
impl<T> DistributionExt for Twhere
T: ?Sized,
fn rand<T>(&self, rng: &mut (impl Rng + ?Sized)) -> Twhere
Self: Distribution<T>,
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more