Skip to content

Commit

Permalink
Hotfix: some unsupported MatJax
Browse files Browse the repository at this point in the history
  • Loading branch information
francisrstokes committed May 10, 2024
1 parent bcd870a commit 8511e14
Showing 1 changed file with 3 additions and 5 deletions.
8 changes: 3 additions & 5 deletions 2024/5/10/cordic.md
Expand Up @@ -77,9 +77,7 @@ It's sort of like a binary search: You move towards the target angle by some la
If you've worked with these kinds of operations before, you'll know that rotating a vector involves multiplying it with a matrix consisting of sines and cosines of the angle to be rotated to. That seems counter productive, since those are the functions we're trying to compute!
$$
\newcommand\colvec[1]{\begin{bmatrix}#1\end{bmatrix}}
\colvec{x'\\y'} = \begin{bmatrix}\cos(\theta) & -\sin(\theta)\\\sin(\theta) & \cos(\theta)\end{bmatrix} \colvec{x\\y}
\begin{bmatrix}x' \\ y'\end{bmatrix} = \begin{bmatrix}\cos(\theta) & -\sin(\theta) \\ \sin(\theta) & \cos(\theta)\end{bmatrix} \begin{bmatrix}x \\ y\end{bmatrix}
$$
We'll put that aside for a second, and get a big picture overview before solving this problem. Now, it's fairly obvious that rotating by say `22.75˚` is the same as rotating by `45˚` and then `-22.5˚` - i.e. we can break up a rotation into smaller parts, with both positive and negative components.
Expand All @@ -104,13 +102,13 @@ $$
\\ \\
\sin(\theta) = \frac{\tan(\theta)}{\sqrt{1 + tan^2(\theta)}}
\\ \\
\colvec{x'\\y'} = \cos(\theta)\begin{bmatrix}1 & -\tan(\theta)\\\tan(\theta) & 1\end{bmatrix} \colvec{x\\y}
\begin{bmatrix}x' \\ y'\end{bmatrix} = \cos(\theta)\begin{bmatrix}1 & -\tan(\theta) \\ \tan(\theta) & 1\end{bmatrix} \begin{bmatrix}x \\ y\end{bmatrix}
$$
We have a few constants ones now, but we still have the `tan(a)`, plus the `cos(a)` out front. Let's ignore the `cos(a)` and focus on getting rid of `tan(a)`. As you saw when we ran through the algorithm, we're always rotating by a total of `~90˚`: First by `45˚`, then `22.5˚`, then `11.25˚`, and so on. Since we're doing this a fixed number of times, we can just precompute those values, and put them in a table. You might be thinking: *"You said there wouldn't be any tables!"*. Well, no. I said there wouldn't be any *expensive* tables. This table, in our case, will only contain 16 `uint32_t`s - a whopping 64 bytes! Even the most stripped down embedded projects can *usually* afford that. (In contrast, an *unoptimised* table for `sin(x)` that contains 4096 entries covering values from -1 to 1 would need 16KiB - and that's pretty poor precision!)
$$
\colvec{x'\\y'} = \cos(\theta)\begin{bmatrix}1 & -table[i]\\table[i] & 1\end{bmatrix} \colvec{x\\y}
\begin{bmatrix}x' \\ y'\end{bmatrix} = \cos(\theta)\begin{bmatrix}1 & -table[i] \\ table[i] & 1\end{bmatrix} \begin{bmatrix}x \\ y\end{bmatrix}
$$
That means our rotation matrix now only contains constants! We do however still have that `cos(a)` term. In fact, every iteration brings it's own new `cos(a)` term. But because of algebra, we can simply multiply all those terms together and apply them at the end.
Expand Down

0 comments on commit 8511e14

Please sign in to comment.