It is necessary for me to find the unit outward normal vector for the curve:

$$\gamma=(x(t),y(t)) $$

where $$x(t)=\cos(t)−0.5\cos(3t)$$ and $$y(t)=\sin(t)+\sin(7t)+\sin(3t)$$ I know how to find unit outward normal vector for this: using

$$T=\frac{\gamma' (t)}{||\gamma(t)||} $$ so $$N=\frac{T (t)}{||T(t)|| }$$

but my problem is that I do not have $t$ . I just have $x(t)$ and $y(t)$. How could I find $t$ or $N$ without knowing $t$.

Is there any command in MATLAB or MAPLE to this?


2 Answers 2


All the info you need can be found by reading about the Frenet (or TNB, Tangent-Normal-Binormal) frame.

Using the notation on the Wikipedia page, you can denote your curve as $$ \vec{r}(s) = (x(s),y(s),0) $$ and the tangent and normal vectors are given by $$ \vec{T} = \dfrac{d\vec{r}}{ds} $$ and $$ \vec{N} = \dfrac{d\vec{T}}{ds}\left/\left|\left|\dfrac{d\vec{T}}{ds}\right|\right|\right., $$ where $s$ represents arc length. Since you are restricted to 2D instead of 3D, the binormal vector is just $\pm\bf\hat{k}$.

The normal vector $\vec{N}$ always points to the interior of the curve (the direction of normal acceleration if you're moving along the curve), so the vector you want is actually given by $-\vec{N}$.

I'm not quite sure what you mean by the statement "I do not have $t$. I just have $x(t)$ and $y(t)$." The normal vector will be different at different points along your curve. You can write a general expression for $\vec{N}(t)$ or you can pick a specific value for $t$ and get a unique $\vec{N}$. Also, since your independent variable, $t$, is not arc length you will have to compute $\vec{T}$ using the chain rule as $$ \vec{T} = \dfrac{d\vec{r}}{dt}\left/\dfrac{ds}{dt}\right.. $$

There is an analytical formula for arc length of a parametrically defined curve $$ s = \int_{t_0}^t \sqrt{x'(t^*)^2+y'(t^*)^2} dt^* $$ Or, if you have $x$ and $y$ defined as a set of discrete points along the curve as $x=\{x_1, x_2, x_3, ...\}$, $y=\{y_1, y_2, y_3, ...\}$ you could estimate the tangent and normal vectors using (for example) finite differences.

Your specific case:

An analytical expression for the parameterization you have given will be complicated. A good alternative might be to pick a bunch of (closely spaced) points on your curve to discretize the problem and then use something like this Frenet coordinate routine from the MATLAB File Exchange.


I implemented this real quick using finite differences as suggested by @DougLipinski, and this is what I come up with, at first glance it looks correct. Green vectors are the tangent vectors and red are the normals.

To calculate the differential arc length I used this relationship $$(ds)^2 = (dx)^2 + (dy)^2$$ and applied a simple first order finite difference to $x$ and $y$.

enter image description here

Here's the code, let me know if you see anything wrong

clear all
close all

t = 0:0.01:(2*pi+0.01);
t = t(:);
n = length(t);
x = cos(t) - 0.5*cos(3*t);
y = sin(t) + sin(7*t) + sin(3*t);

e = ones(n,1);
A = 0.5*spdiags([-e e],[-1,1],n,n);%first order FD stencil

dx = A*x; 
dy = A*y;

ds = sqrt(dx.^2 + dy.^2);

T = [dx./ds  dy./ds];
for rr = 1:size(T,1)
   T(rr,:) = T(rr,:)/sqrt(T(rr,1)^2 + T(rr,2)^2); 
dT  = [A*T(:,1) A*T(:,2)];

N   = [dT(:,1)./ds dT(:,2)./ds];
for rr = 1:size(N,1)
   N(rr,:) = N(rr,:)/sqrt(N(rr,1)^2 + N(rr,2)^2); 

    hold on
  • $\begingroup$ Definitely not quite right. Your tangent (green) vectors are not unit vectors so the red vectors are not normal to the curve since they account for the changing length of T as well as the changing direction. $\endgroup$ Commented Dec 10, 2014 at 18:52
  • $\begingroup$ They weren't unit vectors because I was normalizing them wrong, I corrected that, but something still seems off. Anything obvious to you? $\endgroup$
    – user7257
    Commented Dec 10, 2014 at 19:24
  • $\begingroup$ Your code looks ok to me now. I would do the normalization for T (and N) as T = [dx./ds dy./ds]; normT = sqrt(sum(T.^2,2)); T = bsxfun(@rdivide,T,normT); but loops make it more clear what's going on. $\endgroup$ Commented Dec 10, 2014 at 21:20
  • $\begingroup$ @DougLipinski Any idea what the speeds up are using bsxfun over loops? $\endgroup$
    – user7257
    Commented Dec 11, 2014 at 14:37
  • $\begingroup$ It depends on the loop. In some cases (i.e. if the just-in-time compiler does a good job with the loop) there may not be much difference. In this code the loops don't take much time anyway. However, if you use a lot more points you will start to see a difference. Using 10,000x more points on my machine your loop takes a factor of ~40x as long as calling T = bsxfun(@rdivide,T,sqrt(sum(T.^2,2)));. Things are even faster (~70x speedup) using normT = sqrt(T(:,1).^2+T(:,2).^2); T(:,1) = T(:,1)./normT; T(:,2) = T(:,2)./normT;. $\endgroup$ Commented Dec 11, 2014 at 15:30

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.