Yoda
Yoda

Reputation: 690

How plot a two-dimensional function in three-dimensional space with MATLAB?

I want to plot a two-dimensional function of the polar coordinates r and theta in three-dimensional cartesian coordinates. I have that (sorry about bad maths formatting, LaTeX not compatible, it seems)

f(r,theta) = r/2 * (cos(theta - pi/4) + sqrt(1 + 1/2 * cos(2*theta)))

Converting r and theta to cartesian coordinates

x = r * cos(theta), y = r * sin(theta)

Further, the domain is -1<r<1 and 0<theta<2 * pi, which I define by

r = -1:2/50:1;

and

theta = 0:2*pi/50:2*pi;

giving me two vectors of the same dimensions.

I can define the x and y values used for plotting as row vectors by

x = r. * cos(theta);

and

y = r. * sin(theta);

So now I need to define the z values, which will depend on the values of x and y. I thought I should make a 101x101 where each matrix element contains a data point of the final surface. But how should I do this? I thought about using a double for loop:

for i=1:numel(r)
    for j=1:numel(theta)
        z(i,j) = r(i)/2 .* cos(theta(j) - pi/4) + r(i).*sqrt(1 + 1/2 * cos(2.*theta(j)));
    end
end

Then simply surf(z)

While this definitely gives me a surface, it gives me the incorrect surface! I don't know what is happening here. The incorrect surface is given in Figure 1, while the correct one is given in Figure 2. Can anyone help me out? For reference, the correct surface was plotted with GeoGebra, using

A = Function[<expression 1>, <Expresison 2>, <Expression 3>, <var 1>, <start>, <stop>, <var 2>, <start>, <stop>]

Incorrect surface

Figure 1. Incorrect surface.

Correct surface

Figure 2. Correct surface.

Upvotes: 2

Views: 388

Answers (2)

Jay Brady
Jay Brady

Reputation: 106

As others have said, you can use meshgrid to make this work.

Here's your example using gridded r and theta and an anonymous function to replace the double loop:

r = -1:2/50:1;
theta = 0:2*pi/50:2*pi;

% define anonymous function f(r,theta)
f =  @(r,theta) r/2 .* (cos(theta - pi/4) + sqrt(1 + 1/2 .* cos(2.*theta)));

% generate grids for r and theta
[r, theta] = meshgrid(r,theta); 
% calculate z from gridded r and theta
z = f(r,theta); 

% convert r,theta to x,y and plot with surf
x = r.*cos(theta); 
y = r.*sin(theta);
surf(x,y,z);

Upvotes: 1

Brick
Brick

Reputation: 4262

You need to use meshgrid to get matrix coordinates if you want to use surf. Taking your x and y (lower case), call

[X,Y] = meshgrid(x,y);

Then X and Y (upper case) will have the same values as you gave it, but laid out in the two-dimensional array as expected by surf. Loop over the indices here and compute your Z, which should have all(size(Z) == size(X)).

https://www.mathworks.com/help/matlab/ref/meshgrid.html

Upvotes: 0

Related Questions