Skip to content

Commit 6b70285

Browse files
committed
da/utils.py: bug fixes, see details
fixed bug where full domain with ghost cells was used in calculating variance for obs noise; fixed bug where I took 0.05 from the std. dev. and not the variance as it is written down.
1 parent d2e59c5 commit 6b70285

File tree

1 file changed

+21
-6
lines changed

1 file changed

+21
-6
lines changed

RKLM_Python/data_assimilation/utils.py

Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -383,7 +383,7 @@ def sparse_obs_selector(obs, elem, node, ud, dap):
383383
return mask_arr
384384

385385

386-
def obs_noiser(obs,dap,rloc):
386+
def obs_noiser(obs,mask,dap,rloc,elem):
387387
if dap.add_obs_noise:
388388
assert isinstance(dap.obs_noise, dict), "obs_noise has to be dict"
389389
assert len(dap.obs_noise) == len(dap.obs_attributes), "obs_noise length has to be equal to obs_attributes len"
@@ -394,27 +394,40 @@ def obs_noiser(obs,dap,rloc):
394394

395395
std_dev = np.zeros((obs.shape[0],len(dap.obs_noise_seeds)))
396396

397+
# define inner domain in 2D VS
398+
i2 = (slice(elem.igx,-elem.igx),slice(elem.igy,-elem.igy))
399+
397400
for tt, obs_t in enumerate(obs):
398401
attr_cnt = 0
399402
for key, value in obs_t.items():
403+
404+
# Get inner 2D domain of sparse obs field
405+
value = value[i2]
406+
mask_at_t = mask[tt][key][i2]
407+
value = np.ma.array(value,mask=mask_at_t)
408+
400409
seed = dap.obs_noise_seeds[attr_cnt]
401410
np.random.seed(seed)
402411

403412
if dap.noise_type == 'AmpCov':
404-
field_var = np.abs(value.max() - value.min())
413+
field_var = (dap.obs_noise[key] * np.abs(value.max() - value.min()))
414+
field_sd = field_var**0.5
405415
elif dap.noise_type == 'VarCov':
406-
field_var = (((value - value.mean())**2).mean())**0.5
416+
field_var = (dap.obs_noise[key] * ((value - value.mean())**2).mean())
417+
field_sd = field_var**0.5
418+
407419
elif dap.noise_type == 'FixCov':
408-
field_var = 1.0
420+
field_sd = 1.0 * dap.obs_noise[key]
409421

410422
# here, we take the fraction defined by obs_noise multiplied by the maximum value of the observation as the standard deviation of the measurement noise.
411-
std_dev[tt,attr_cnt] = (dap.obs_noise[key] * field_var)
423+
424+
std_dev[tt,attr_cnt] = field_sd
412425

413426
attr_cnt += 1
414427

415428
# var = std_dev**2
416429

417-
if dap.noise_type == 'VarCov':
430+
if dap.noise_type == 'VarCov' or dap.noise_type == 'AmpCov':
418431
sd = std_dev.mean(axis=0,keepdims=True)
419432
std_dev[:,...] = sd
420433

@@ -423,6 +436,8 @@ def obs_noiser(obs,dap,rloc):
423436
for key, value in obs_t.items():
424437
shp = value.shape
425438
sd = std_dev[tt,attr_cnt]
439+
440+
# print(tt, key, sd**2, np.abs(value.max()-value.min()))
426441

427442
# generate gaussian noise for observations.
428443
noise = np.random.normal(0.0, sd, size=(shp))

0 commit comments

Comments
 (0)