{"record":{"id":"90e4c417691ad5c8","repo":"tracel-ai/burn","slug":"other-reduction-is-not-supported-90e4c4","errorCode":null,"errorMessage":"{other:?} reduction is not supported","messagePattern":"(.+?) reduction is not supported","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/burn-nn/src/loss/triplet_margin.rs","lineNumber":91,"sourceCode":"    ///\n    /// # Shapes\n    ///\n    /// - anchor:   `[batch_size, embedding_dim]`\n    /// - positive: `[batch_size, embedding_dim]`\n    /// - negative: `[batch_size, embedding_dim]`\n    /// - output:   `[1]`\n    pub fn forward(\n        &self,\n        anchor: Tensor<2>,\n        positive: Tensor<2>,\n        negative: Tensor<2>,\n        reduction: Reduction,\n    ) -> Tensor<1> {\n        let loss = self.forward_no_reduction(anchor, positive, negative);\n        match reduction {\n            Reduction::Mean | Reduction::Auto => loss.mean(),\n            Reduction::Sum => loss.sum(),\n            other => panic!(\"{other:?} reduction is not supported\"),\n        }\n    }\n\n    /// Compute the loss for each triplet, without reducing.\n    ///\n    /// # Shapes\n    ///\n    /// - anchor:   `[batch_size, embedding_dim]`\n    /// - positive: `[batch_size, embedding_dim]`\n    /// - negative: `[batch_size, embedding_dim]`\n    /// - output:   `[batch_size]`\n    pub fn forward_no_reduction(\n        &self,\n        anchor: Tensor<2>,\n        positive: Tensor<2>,\n        negative: Tensor<2>,\n    ) -> Tensor<1> {\n        // Pairwise distances over the embedding dim: shape [batch_size, 1] -> [batch_size].","sourceCodeStart":73,"sourceCodeEnd":109,"githubUrl":"https://github.com/tracel-ai/burn/blob/d16f7ba2ed0d41408189384044cc886fb4c8f957/crates/burn-nn/src/loss/triplet_margin.rs#L73-L109","documentation":"TripletMarginLoss's reduced `forward` only handles Reduction::Mean/Auto and Reduction::Sum; any other variant panics. Since the reduced call returns a scalar `Tensor<1>`, unsupported reduction modes are rejected by the catch-all match arm.","triggerScenarios":"Calling `TripletMarginLoss::forward(anchor, positive, negative, reduction)` with a Reduction variant other than Mean, Auto, or Sum, typically Reduction::None.","commonSituations":"Porting triplet loss code from PyTorch using reduction='none'; a shared Reduction config value reused across losses with different support; new enum variants from a burn upgrade.","solutions":["Pass Reduction::Mean, Reduction::Auto, or Reduction::Sum.","Call `forward_no_reduction(anchor, positive, negative)` for the per-triplet (unreduced) loss.","Validate the Reduction value before calling forward."],"exampleFix":"// before\nlet loss = triplet_loss.forward(anchor, pos, neg, Reduction::None);\n// after\nlet per_triplet = triplet_loss.forward_no_reduction(anchor, pos, neg);\nlet loss = per_triplet.mean();","handlingStrategy":"validation","validationCode":"fn is_supported_reduction(r: &Reduction) -> bool {\n    matches!(r, Reduction::Mean | Reduction::Auto | Reduction::Sum)\n}\nassert!(is_supported_reduction(&reduction));","typeGuard":"fn is_supported_reduction(r: &Reduction) -> bool {\n    matches!(r, Reduction::Mean | Reduction::Auto | Reduction::Sum)\n}","tryCatchPattern":"let result = std::panic::catch_unwind(|| triplet_loss.forward(a, p, n, reduction));\nmatch result {\n    Ok(loss) => loss,\n    Err(_) => triplet_loss.forward_no_reduction(a, p, n).mean(),\n}","preventionTips":["Use forward_no_reduction for per-triplet losses.","Keep a shared helper that whitelists reductions for all your losses.","Test loss wrappers against the full Reduction enum."],"tags":["rust","panic","loss-function","unsupported-argument"],"backgroundTag":"unsupported-reduction-mode","analyzedSha":"d16f7ba2ed0d41408189384044cc886fb4c8f957","analyzedAt":"2026-09-05T13:19:14.260Z","contentChangedAt":"2026-09-05T13:19:14.260Z","schemaVersion":2},"datasetVersion":"2026-09-12T17:17:11.597Z"}