Hi, I’m starting playing with the C++ Front-end and I wanted to know what would be the most correct way of using auto-differentiation to compute the derivatives or arbitrary functions with respect to different parameters.
I wrote the following minimal toy-example where I just wanted to see how to compute the derivative of pointsInFrame1 with respect a change on pointsInFrame0 (in particular just the first dimension of the pointsInFrame1 vector). In order to do that I used pointsInFrame1ActiveDerivatives to indicate that I wanted the derivative with respect to the first dimension, however I wonder if there is a cleaner way of doing this?
#include <torch/torch.h>
#include <iostream>

int main ()
{
    // One tensor containing one homogeneous 3D point in frame0 coordinates
    torch::Tensor pointsInFrame0 = torch::empty(4);
    pointsInFrame0[0] = -12.0;
    pointsInFrame0[1] = 13.0;
    pointsInFrame0[2] = -14.0;
    pointsInFrame0[3] = 1.0;
    pointsInFrame0.set_requires_grad(true);
    std::cout << "pointsInFrame0:\n" << pointsInFrame0 << "\n";
    
    // One tensor containing a 4x4 isometry transformation matrix, transforming
    // world coordinates to frame0 coordinates
    torch::Tensor frame0FromWorld = torch::zeros({4,4});
    frame0FromWorld[0][0] = std::sqrt(3.0)/2.0;
    frame0FromWorld[0][1] = -1.0/2.0;
    frame0FromWorld[1][0] = 1.0/2.0;
    frame0FromWorld[1][1] = std::sqrt(3.0)/2.0;
    frame0FromWorld[2][2] = 1.0;
    frame0FromWorld[3][3] = 1.0;
    frame0FromWorld.set_requires_grad(true);
    std::cout << "frame0FromWorld:\n" << frame0FromWorld << "\n";
    
    // One tensor containing a 4x4 isometry transformation matrix, transforming
    // world coordinates to frame1 coordinates
    torch::Tensor frame1FromWorld = torch::zeros({4,4});
    frame1FromWorld[0][0] = 1.0;
    frame1FromWorld[0][3] = -2.0;
    frame1FromWorld[1][1] = 1.0;
    frame1FromWorld[1][3] = 3.0;
    frame1FromWorld[2][2] = 1.0;
    frame1FromWorld[2][3] = -4.0;
    frame1FromWorld[3][3] = 1.0;
    frame1FromWorld.set_requires_grad(true);
    std::cout << "frame1FromWorld:\n" << frame1FromWorld << "\n";
    
    // One tensor containing the transformed 3D points in frame1 coordinates
    torch::Tensor pointsInFrame1 = at::matmul(frame1FromWorld, at::matmul(torch::inverse(frame0FromWorld), pointsInFrame0));
    std::cout << "pointsInFrame1:\n" << pointsInFrame1 << "\n";
    
    // One tensor computing the partial derivatives dpointsInFrame1/dpointsInFrame0
    torch::Tensor pointsInFrame1ActiveDerivatives = torch::zeros({4});
    pointsInFrame1ActiveDerivatives[0] = 1; // <-- NOTE: my intention is to compute dpointsInFrame1.x/dpointsInFrame0
    pointsInFrame1.backward(pointsInFrame1ActiveDerivatives);
    std::cout << "dpointsInFrame1/dpointsInFrame0:\n" << pointsInFrame0.grad() << "\n";
    
    // Check expected output
    torch::Tensor expectedPointsInFrame1Derivatives = torch::empty({4});
    expectedPointsInFrame1Derivatives[0] = 0.86604;
    expectedPointsInFrame1Derivatives[1] = 0.50002;
    expectedPointsInFrame1Derivatives[2] = 0.00000;
    expectedPointsInFrame1Derivatives[3] = -2.00000;
    assert((pointsInFrame0.grad()-expectedPointsInFrame1Derivatives).norm().item<float>() < 5e-5);
}

Thanks a lot in advance!