@@ -305,23 +305,36 @@ namespace gtsam {
305305 const Vector x =
306306 frontalValues.vector (KeyVector (beginFrontals (), endFrontals ()));
307307
308- // Copy the augmented Jacobian matrix:
309- auto newAb = Ab_;
308+ // Compute updated right-hand side: d - R * x
309+ const auto RR = R ().triangularView <Eigen::Upper>();
310+ const Vector rhs = d () - RR * x;
310311
311- // Restrict view to parent blocks
312- newAb.firstBlock () += nrFrontals_;
312+ // Collect parent dimensions
313+ FastVector<DenseIndex> parentDims;
314+ parentDims.reserve (nrParents ());
315+ for (auto it = beginParents (); it != endParents (); ++it) {
316+ parentDims.push_back (getDim (it));
317+ }
313318
314- // Update right-hand-side (last column)
315- auto last = newAb.matrix ().cols () - 1 ;
316- const auto RR = R ().triangularView <Eigen::Upper>();
317- newAb.matrix ().col (last) -= RR * x;
319+ // Build a VerticalBlockMatrix containing only parent blocks and RHS.
320+ const DenseIndex m = rows ();
321+ VerticalBlockMatrix newAb (parentDims, m, true );
322+
323+ // Copy parent blocks (S matrices).
324+ DenseIndex blockIndex = 0 ;
325+ for (auto it = beginParents (); it != endParents (); ++it, ++blockIndex) {
326+ newAb (blockIndex) = S (it);
327+ }
328+
329+ // Set the RHS block.
330+ const DenseIndex lastBlock = newAb.nBlocks () - 1 ;
331+ newAb (lastBlock).col (0 ) = rhs;
318332
319333 // The keys now do not include the frontal keys:
320334 KeyVector newKeys;
321335 newKeys.reserve (nrParents ());
322336 for (auto && key : parents ()) newKeys.push_back (key);
323337
324- // Hopefully second newAb copy below is optimized out...
325338 return std::make_shared<JacobianFactor>(newKeys, newAb, model_);
326339 }
327340
0 commit comments