-
Notifications
You must be signed in to change notification settings - Fork 4
/
rnd2plm.m
206 lines (184 loc) · 5.92 KB
/
rnd2plm.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
function varargout=rnd2plm(lmcosi,meth)
% lmcosip=RND2PLM(lmcosi,meth)
%
% Randomizes a spherical-harmonic coefficient matrix
%
% INPUT:
%
% lmcosi Input matrix listing l, m, Ccos and Csin
% meth 'kevin' a la Kevin (faster for low degrees)
% 'frederik' a la Frederik (faster for high degrees)
%
% OUTPUT:
%
% lmcosip Output matrix listing l, m, Ccos and Csin
%
% SEE ALSO:
%
% PLM2RND, COV2PLM
%
% REQUIRES:
%
% RandOrthMat, from
% http://www.mathworks.com/matlabcentral/fileexchange/11783-randorthmat
%
% EXAMPLE:
%
% rnd2plm('demo1')
% produces realizations of fields with the same
% statistics as lunar topography
%
% Written by Kevin Lewis, 02/21/2010
% Last modified by fjsimons-at-alum.mit.edu, 10/15/2023
if ~isstr(lmcosi)
% Supply the default, i.e. a low-resolution terrestrial gravity field
defval('lmcosi',...
kindeks(rindeks(fralmanac('EGM96','SHM'),1:addmup(255)-3),1:4))
defval('meth','kevin')
switch meth
case 'kevin'
tic
l=lmcosi(:,1);
m=lmcosi(:,2);
co=lmcosi(:,3);
si=lmcosi(:,4);
for i=min(l):max(l)
ind=find(l==i);
lcoeffs=RandOrthMat(2*i+1)*[flipud(si(ind(2:end))) ; co(ind)];
si2(ind(2:end))=flipud(lcoeffs(1:i));
co2(ind)=lcoeffs(i+1:end);
end
lmcosip=[l m co2(:) si2(:)];
toc
case 'frederik'
tic
lmcosip=[lmcosi(:,1:2) zeros(length(lmcosi),2)];
% Loop over the degrees
for l=lmcosi(1,1):lmcosi(end,1)
% Extract the COSINE coefficients and their indices at increasing degree
[Ccos,b,e]=shcos(lmcosi,l);
% Extract the SINE coefficients and return them at decreasing degree
Csin=lmcosi(e:-1:b+1,4);
% Randomize by orthogonal multiplication
lcoeffs=RandOrthMat(2*l+1)*[Csin ; Ccos];
% Assign the SINE coefficients (m>0) to the right spots in the larger matrix
% Note the trick with the sum to convert the empty to a zero if needed
lmcosip(e:-1:b+1,4)=sum(lcoeffs(1:l),2);
% Assign the COSINE (m<=0) coefficients to the right spots
lmcosip(b:e,3)=lcoeffs(l+1:end);
end
toc
end
% Prepare output
varns={lmcosip};
varargout=varns(1:nargout);
elseif strcmp(lmcosi,'demo1')
clf
% Capture the demo string
strin=lmcosi;
% Load lunar topography
lmcosi=fralmanac('GLTM2B','SHM');
L=lmcosi(end,1);
[ah,ha]=krijetem(subnum(3,2));
axes(ah(1))
[topo,b,c]=plotplm(lmcosi,[],[],4,1); delete([b c])
% Color scale
col1=getpos(ah(1));
col1=[col1(1)-col1(3)/10 col1(2) col1(3)/15 col1(4)];
[cb(1),xcb(1)]=addcb(col1,round(minmax(topo)),round(minmax(topo)),'jet');
shrink(cb(1),1,1.55)
% Calculate the global power spectral density
[SWSl,l]=plm2spec(lmcosi);
axes(ah(2))
p(1)=plot(l,decibel(SWSl),'b-o'); axis tight
% Prepare for the localization
TH=20;
Lw=10;
phi0=200;
th0=90;
axes(ha(3))
[G,V,EL,EM,N]=glmalphapto(TH,Lw,phi0,th0,0);
[V,i]=sort(V,'descend'); G=G(:,i);
wot=1;
% Check the normalization of GLM2LMCOSI
lmcosit=glm2lmcosi(G,wot);
[taper,b,c]=plotplm(lmcosit,[],[],4,1); delete([b c])
[st,lt]=plm2spec(lmcosit);
axes(ah(6))
p(2)=plot(lt,decibel(st),'b-o'); axis tight
% No point in generating more global examples as the global power
% spectrum is always identical
for inde=1:2
% Generate random topographies just like the moon
lmcosip=rnd2plm(lmcosi);
topop=plm2xyz(lmcosip,1);
% Plot examples in the space domain
axes(ah(3))
[~,b,c]=plotplm(topop,[],[],4,1); delete([b c])
[lon2,lat2]=caploc([phi0 90-th0],TH,[]);
hold on; d=plot(lon2,lat2,'k'); hold off
col2=getpos(ha(2));
col2=[col2(1)-col2(3)/10 col2(2) col2(3)/15 col2(4)];
[cb(2),xcb(2)]=addcb(col2,round(minmax(topop)),round(minmax(topop)),'jet');
shrink(cb(2),1,1.55)
Sal=0;
% Calculate the LOCAL power spectral density
for onde=1:min(round(3*N),size(G,2))
% To keep with Dahlen & Simons, need the factor
% See RB VIII, p 126
taper=plm2xyz(glm2lmcosi(G,onde),1)*sqrt(4*pi);
% Note that the XYZ2PLM uses 4pi normalized harmonics
lmcosipt=xyz2plm(topop.*taper,L);
lmcosipt(:,3:4)=lmcosipt(:,3:4)/sqrt(4*pi);
Sal=Sal+V(onde)*plm2spec(lmcosipt);
end
SMTl=Sal/sum(V(1:onde));
axes(ah(4))
p(2+inde)=plot(0:L,SMTl,'b-o'); axis tight; set(gca,'yscale','log')
hold on
drawnow
end
% So now the claim is that the AVERAGE of the SMTl is given by the
% convolution of the multitaper coupling kernel with the true global
% spectrum and that the VARIANCE of the SMTl is given by the multitaper
% variance (which is in function of the truth).
% Now calculate the expected value of the multitaper estimates in
% function of the truth. Took 80 because 70 has a file problem
Mllp=mcouplings(Lw,80);
Mllp=Mllp(1:L+1,1:L+1);
ESMTl=Mllp*SWSl;
% Calculate the variance-use the global variance??
varSl=mtvar(SWSl,l,Lw,TH,1);
[pp,ex,ey]=errorxy(l,ESMTl,[],2*sqrt(varSl));
hold on
plot(l,ESMTl,'k-','LineW',2)
% Figure cosmetics
fig2print(gcf,'tall')
tits={sprintf('lunar topography to degree %i',L),...
'power spectrum',...
sprintf('randomized lunar topography %i',L),...
'power spectrum',...
'Slepian taper','power spectrum'};
xes={'longitude','spherical harmonic degree'};
yes={'latitude','spectral density (dB)'};
for in=1:length(ah)
axes(ah(in))
title(tits{in}); xlabel(xes{~mod(in,2)+1}); ylabel(yes{~mod(in,2)+1})
end
longticks(ah)
set(ha(1:3),'yaxisl','r')
set(ha(4:6),'yaxisl','r','xgrid','on','ygrid','on',...
'ylim',[-45 5],'xlim',[-5 L])
shrink(ha(3:4),1,3/2)
movev([ah(1:2) cb(1)],-.1)
moveh([ha(1:2)],0.015)
set(p(1:2),'MarkerS',2,'MarkerF','b')
set(p(3:end),'MarkerS',2,'MarkerF','r')
set(xcb,'string','')
set(get(ha(1),'ylabel'),'rotation',-90)
set(get(ha(2),'ylabel'),'rotation',-90)
movev([ah cb],.15)
figna=figdisp([],sprintf('%s_%i',strin,inde),[],1);
system(sprintf('degs %s.eps',figna));
system(sprintf('epstopdf %s.eps',figna));
end