A welding arm in a shipyard is a planar two-link arm: the shoulder joint at the origin, a first link of length l1, an elbow, and a second link of length l2 ending at the torch (the hand). The joint angles are in radians and relative: t1 is the first link's angle from the +x axis, and t2 is the second link's angle from the direction of the first link. With x to the right and y up, the hand is at
The Jacobian J is the 2 \times 2 matrix of partial derivatives \begin{pmatrix} \partial x / \partial t_1 & \partial x / \partial t_2 \\ \partial y / \partial t_1 & \partial y / \partial t_2 \end{pmatrix}, and its determinant is \det J = J_{00} J_{11} - J_{01} J_{10}. When \det J = 0 the pose is singular: there is a direction the torch cannot move in, however the joints turn, and the controller must steer clear of it.
A pose counts as singular when |\det J| \le tol. Write singular_poses(l1, l2, configs, tol) that returns one string per configuration (t1, t2) in configs, in order:
"stretched"if the pose is singular and the elbow is nearly straight (\cos t_2 > 0);"folded"if the pose is singular and the second link lies back along the first (\cos t_2 < 0);"regular"otherwise.
Examples
Input: l1 = 1, l2 = 0.5,
configs = [(0.3, 0.0), (1.0, math.pi), (2.0, 1.0), (0.2, 0.0015), (0.0, -2 * math.pi)],
tol = 1e-3
Output: ["stretched", "folded", "regular", "stretched", "stretched"]
Explanation: at (0.2, 0.0015) the determinant is 0.00075, within the tolerance;
t2 = -2 * pi is a whole turn, so the arm is straight.
Input: l1 = 2, l2 = 2, configs = [(0.5, -3.1), (0.5, 3.1416)], tol = 0.1
Output: ["regular", "folded"]
Explanation: |det J| is 0.166 for t2 = -3.1, more than 0.1.
Constraints
tol < l1 * l2 / 2, so a singular pose is always clearly stretched or clearly folded
Goals
- Compute the determinant of a two-link arm's Jacobian
- Recognise a singular pose by a determinant within a tolerance of zero
- Tell the stretched singularity from the folded one