3 WAVEGUIDES
[POZAR] Chapter 3 does not address the current broad use of commercial electromagnetic simulators because this chapter is an introduction to wave guides as it was done when the book was written.
However, the solutions manual frequently recurs to briefly mentioning different simulators, without specifics, to solve those exercises.
There are different electromagnetic simulators in the market, some with short trial and/or student versions.
In order to simulate Electromagnetic fields with MATLAB, literature references [TL] [TXLP] [ED] are useful.
[TL] has a detailed evolution time line of the FDTD solving industry related problems, as well as a detailed list of strong FDTD points against other simulation algorithms.
Example 3.1.1
Example 3.1.2
Example 3.1.3
Example 3.2
Example 3.3
Example 3.4
Example 3.5
Example 3.6
Example 3.7
Example 3.8
Example 3.9
Exercise 3.1
Exercise 3.2
Exercise 3.3
Exercise 3.4
Exercise 3.5
Exercise 3.6
Exercise 3.7
Exercise 3.8
Exercise 3.9
Exercise 3.10
Exercise 3.11
Exercise 3.12
Exercise 3.13
Exercise 3.14
Exercise 3.15
Exercise 3.16
Exercise 3.17
Exercise 3.18
Exercise 3.19
Exercise 3.20
Exercise 3.21
Exercise 3.22
Exercise 3.23
Exercise 3.24
Exercise 3.25
Exercise 3.26
Exercise 3.27
Exercise 3.28
Exercise 3.29
% create exact function and its derivative
N_exact = 301; % number of sample points for exact function
x_exact = linspace(0,6*pi,N_exact);
f_exact = sin(x_exact).*exp(-0.3*x_exact);
f_derivative_exact = cos(x_exact).*exp(-0.3*x_exact) -0.3*sin(x_exact).*exp(-0.3*x_exact);
% plot exact function
figure(1);
plot(x_exact,f_exact,'k-','linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -1 1]); grid on;
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('$f(x)$','Interpreter','latex','FontSize',16);
%% create exact function for pi/5 sampling period and its finite difference derivatives
N_a = 31; % number of points for pi/5 sampling period
x_a = linspace(0,6*pi,N_a);
f_a = sin(x_a).*exp(-0.3*x_a);
f_derivative_a = cos(x_a).*exp(-0.3*x_a) -0.3*sin(x_a).*exp(-0.3*x_a);
dx_a = pi/5;
f_derivative_forward_a = zeros(1,N_a);
f_derivative_forward_o2_a = zeros(1,N_a);
f_derivative_backward_a = zeros(1,N_a);
f_derivative_backward_o2_a = zeros(1,N_a);
f_derivative_central_a = zeros(1,N_a);
f_derivative_central_o4_a = zeros(1,N_a);
f_derivative_forward_a(1:N_a-1) = (f_a(2:N_a)-f_a(1:N_a-1))/dx_a;
% 1st order
f_derivative_forward_o2_a(1:N_a-2) = (-f_a(3:N_a)+4*f_a(2:N_a-1)-3*f_a(1:N_a-2))/(2*dx_a); % 2nd order
f_derivative_backward_a(2:N_a) = (f_a(2:N_a)-f_a(1:N_a-1))/dx_a;
f_derivative_backward_o2_a(3:N_a) = (f_a(1:N_a-2)-4*f_a(2:N_a-1)+3*f_a(3:N_a))/(2*dx_a);
f_derivative_central_a(2:N_a-1) = (f_a(3:N_a)-f_a(1:N_a-2))/(2*dx_a);
f_derivative_central_o4_a(3:N_a-2) = (-f_a(5:N_a)+8*f_a(4:N_a-1)-8*f_a(2:N_a-3)+f_a(1:N_a-4) )/(12*dx_a);
%% create exact function for pi/10 sampling period and its finite difference derivatives
N_b = 61; % number of points for pi/10 sampling period
x_b = linspace(0,6*pi,N_b);
f_b = sin(x_b).*exp(-0.3*x_b);
f_derivative_b = cos(x_b).*exp(-0.3*x_b) -0.3*sin(x_b).*exp(-0.3*x_b);
dx_b = pi/10;
f_derivative_forward_b = zeros(1,N_b);
f_derivative_backward_b = zeros(1,N_b);
f_derivative_central_b = zeros(1,N_b);
f_derivative_forward_b(1:N_b-1) = (f_b(2:N_b)-f_b(1:N_b-1))/dx_b;
f_derivative_backward_b(2:N_b) = (f_b(2:N_b)-f_b(1:N_b-1))/dx_b;
f_derivative_central_b(2:N_b-1) = (f_b(3:N_b)-f_b(1:N_b-2))/(2*dx_b);
%% plot exact derivative of the function and its finite difference derivatives using pi/5 sampling period
figure(2);
plot(x_exact,f_derivative_exact,'k', ...
x_a(1:N_a-1),f_derivative_forward_a(1:N_a-1),'b--', ...
x_a(2:N_a),f_derivative_backward_a(2:N_a),'r-.', ...
x_a(2:N_a-1),f_derivative_central_a(2:N_a-1),':ms', ...
'MarkerSize',4, 'linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -1 1]);
grid on;
legend('exact', 'forward difference',...
'backward difference','central difference');
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('$f''(x)$','Interpreter','latex','FontSize',16);
text(pi,0.6,'$\Delta x = \pi/5$','Interpreter', ...
'latex','fontsize',16, 'BackgroundColor','w','EdgeColor','k');
title('1st order')
% plot error for finite difference derivatives using pi/5 sampling period
error_forward_a = f_derivative_a - f_derivative_forward_a;
error_backward_a = f_derivative_a - f_derivative_backward_a;
error_central_a = f_derivative_a - f_derivative_central_a;
figure(3);
plot(x_a(1:N_a-1),error_forward_a(1:N_a-1),'b--', ...
x_a(2:N_a),error_backward_a(2:N_a),'r-.', ...
x_a(2:N_a-1),error_central_a(2:N_a-1),':ms', ...
'MarkerSize',4, 'linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -0.2 0.2]);
grid on;
legend('forward difference', 'backward difference', ...
'central difference');
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('error $[f''(x)]$','Interpreter','latex','FontSize',16);
text(pi,0.15,'$\Delta x = \pi/5$','Interpreter', ...
'latex','fontsize',16, 'BackgroundColor','w','EdgeColor','k');
title('1st order')
% plot error for finite difference derivatives using pi/10 sampling period
error_forward_b = f_derivative_b - f_derivative_forward_b;
error_backward_b = f_derivative_b - f_derivative_backward_b;
error_central_b = f_derivative_b - f_derivative_central_b;
figure(4);
plot(x_b(1:N_b-1),error_forward_b(1:N_b-1),'b--', ...
x_b(2:N_b),error_backward_b(2:N_b),'r-.', ...
x_b(2:N_b-1),error_central_b(2:N_b-1),':ms', ...
'MarkerSize',4, 'linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -0.2 0.2]);
grid on;
legend('forward difference','backward difference', ...
'central difference');
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('error $[f''(x)]$','Interpreter','latex','FontSize',16);
text(pi,0.15,'$\Delta x = \pi/10$','Interpreter', ...
'latex','fontsize',16,'BackgroundColor','w','EdgeColor','k');
title('1st order')
%% repeat with 2nd order approximations
figure(5);
plot(x_exact,f_derivative_exact,'k', ...
x_a(1:N_a-1),f_derivative_forward_o2_a(1:N_a-1),'b--', ...
x_a(2:N_a),f_derivative_backward_o2_a(2:N_a),'r-.', ...
x_a(2:N_a-1),f_derivative_central_o4_a(2:N_a-1),':ms', ...
'MarkerSize',4, 'linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -1 1]);
grid on;
legend('exact', 'forward difference',...
'backward difference','central difference');
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('$f''(x)$','Interpreter','latex','FontSize',16);
text(pi,0.6,'$\Delta x = \pi/5$','Interpreter', ...
'latex','fontsize',16, 'BackgroundColor','w','EdgeColor','k');
title('2nd order')
%% plot error for finite difference derivatives using pi/5 sampling period
error_forward_o2_a = f_derivative_a - f_derivative_forward_o2_a;
error_backward_o2_a = f_derivative_a - f_derivative_backward_o2_a;
error_central_o2_a = f_derivative_a - f_derivative_central_o4_a;
figure(6);
plot(x_a(1:N_a-1),error_forward_o2_a(1:N_a-1),'b--', ...
x_a(2:N_a),error_backward_o2_a(2:N_a),'r-.', ...
x_a(2:N_a-1),error_central_o2_a(2:N_a-1),':ms', ...
'MarkerSize',4, 'linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -0.2 0.2]);
grid on;
legend('forward difference', 'backward difference', ...
'central difference');
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('error $[f''(x)]$','Interpreter','latex','FontSize',16);
text(pi,0.15,'$\Delta x = \pi/5$','Interpreter', ...
'latex','fontsize',16, 'BackgroundColor','w','EdgeColor','k');
title('2nd order')
% plot error for finite difference derivatives using pi/10 sampling period
error_forward_b = f_derivative_b - f_derivative_forward_b;
error_backward_b = f_derivative_b - f_derivative_backward_b;
error_central_b = f_derivative_b - f_derivative_central_b;
figure(7);
plot(x_b(1:N_b-1),error_forward_b(1:N_b-1),'b--', ...
x_b(2:N_b),error_backward_b(2:N_b),'r-.', ...
x_b(2:N_b-1),error_central_b(2:N_b-1),':ms', ...
'MarkerSize',4, 'linewidth',1.5);
set (gca,'FontSize',12,'fontweight','demi');
axis([0 6*pi -0.2 0.2]);
grid on;
legend('forward difference','backward difference', ...
'central difference');
xlabel('$x$','Interpreter','latex','FontSize',16);
ylabel('error $[f''(x)]$','Interpreter','latex','FontSize',16);
text(pi,0.15,'$\Delta x = \pi/10$','Interpreter', ...
'latex','fontsize',16,'BackgroundColor','w','EdgeColor','k');
title('2nd order')
The initial odd sample of the central 2nd order, left graph, 1st sample of magenta trace, it is not an error. It’s just that the higher the order, central requires double shortening of the output samples, both head and tail have to be shortened, loosing double amount of input samples compared to same order forward or backward approximations.
For h-step regularly spaced samples around a reference point x0, central approximation of derivative, the coefficients aproximating m-th derivative with accuracy n, as in h(o^n) can be calculated with the following script:
m=4 % order of derivative to approximate with finite differences
n=4 % required derivative accuracy h(o^n)
syms p;p_=double(solve(2*p+1==2*floor((m+1)/2)-1+n,p))
disp(['amount of required coeffs: ' num2str(2*p_+1)])
X=repmat([-p_:1:p_],2*p_+1,1)
X2=zeros(size(X))
for k=1:1:2*p_+1
L=X(k,:);
X2(k,:)=L.^(k-1);
end
X2
a=zeros(1,2*double(p_)+1);
a(m+1)=factorial(m);
coeffs=round((X2\a')',n)
% from table intro to Finite Difference coefficients link expected result
r0=[-1/6 2 -13/2 28/3 -13/2 2 -1/6];
% peak error
max(abs(coeffs-r0))
m = 4
n = 4
p_ = 3
amount of required coeffs: 7
X =
-3 -2 -1 0 1 2 3
-3 -2 -1 0 1 2 3
-3 -2 -1 0 1 2 3
-3 -2 -1 0 1 2 3
-3 -2 -1 0 1 2 3
-3 -2 -1 0 1 2 3
-3 -2 -1 0 1 2 3
X2 =
1 1 1 1 1 1 1
-3 -2 -1 0 1 2 3
9 4 1 0 1 4 9
-27 -8 -1 0 1 8 27
81 16 1 0 1 16 81
-243 -32 -1 0 1 32 243
729 64 1 0 1 64 729
coeffs =
Columns 1 through 3
-0.166700000000000 2.000000000000000 -6.500000000000000
Columns 4 through 6
9.333300000000000 -6.500000000000000 2.000000000000000
Column 7
-0.166700000000000
=
3.333333333443989e-05
Following, script to calculate coefficients, also called stencil points, for an vector of samples of arbitrary lenth N and any spacing, any amount of samples and any derivative order.
Let be for instance
s=[-3 -2 -1 0 1] % 0 is the reference sample
m=4 % order of derivative to approximate with finite differences
N=numel(s) % length of samples including reference sample
X=repmat(s,N,1)
X2=zeros(size(X));
for k=1:1:N
L=X(k,:);
X2(k,:)=L.^(k-1);
end
X2
a=zeros(1,N);
a(m+1)=factorial(m)
coeffs=(X2\a')'
s = -3 -2 -1 0 1
m = 4
N = 5
X =
-3 -2 -1 0 1
-3 -2 -1 0 1
-3 -2 -1 0 1
-3 -2 -1 0 1
-3 -2 -1 0 1
X2 =
1 1 1 1 1
-3 -2 -1 0 1
9 4 1 0 1
-27 -8 -1 0 1
81 16 1 0 1
a = 0 0 0 0 24
coeffs =
Columns 1 through 3
1.000000000000000 -4.000000000000000 5.999999999999998
Columns 4 through 5
-4.000000000000000 1.000000000000000
The single point derivative approximation is the Euler method u'(x)=(u(x+h)-u(x))/h and solve for u(x).
equivalent terms in derivative approximation: forward = explicit, backward = implicit, central time central diffference (Crank-Nicholson)
Additional references:
MIT intro to Finite Difference Methods OpenWare includes self assessment [5].
Generation of Finite Difference Formulas on Arbitrarily Spaced Grids, B.Fornberg [6]
[5] http://web.mit.edu/course/16/16.90/BackUp/www/pdfs/Chapter13.pdf
[6] https://web.njit.edu/~jiang/math712/fornberg.pdf
Formberg supplies the following Finite Difference 1D central coefficients table:
[3] focuses on solving Maxwell equations, and a rudimentary list of procedures is custom implemented to input 3D structures with different material properties.
Since Versatility is important to any simulation, what's the point of having a wonderful FDTD solver script if one has to spend too many hours 'writing' the 3D input structures, there's a MATLAB Simulink toolbox that imports CAD files directly: