Skip to content

Commit 04890b8

Browse files
committed
v0.1
1 parent f19f5c2 commit 04890b8

2 files changed

Lines changed: 65 additions & 44 deletions

File tree

Lines changed: 62 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,9 @@
99
# progress bar
1010
from tqdm import tqdm
1111

12+
### Version :
13+
version = '0.1' #05.08.2022 (Major version).(Minor version)
14+
1215
#######################################
1316
#### specify your source path
1417
#######################################
@@ -21,7 +24,7 @@
2124

2225
try:
2326
# load csv :
24-
ismip = pd.read_csv(workdir + '/ismip6_criteria_v0.csv',delimiter=';',decimal=",")
27+
ismip = pd.read_csv(workdir + '/ismip6_criteria.csv',delimiter=';',decimal=",")
2528
except IOError:
2629
print('ERROR: Unable to open the compliance criteria file (.csv required with ; as delimiter and , for decimal.). Is the path to the file correct ? '+ workdir + 'ismip6_criteria_v0.csv')
2730
else:
@@ -68,6 +71,11 @@ def files_and_subdirectories(path):
6871
directories.append(f)
6972
return directories, files
7073

74+
# check motonocity of a list (used to check time serie)
75+
76+
def strictly_increasing(L):
77+
return all(x<y for x, y in zip(L, L[1:]))
78+
7179
###############################################
7280
# create the compliance_checker_log.txt file
7381
###############################################
@@ -84,7 +92,7 @@ def files_and_subdirectories(path):
8492
f.write('************************************************************************************\n')
8593
f.write('************* Ice Sheet Model Simulations - Compliance Checker *************\n')
8694
f.write('************************************************************************************\n')
87-
f.write('version: 0 \n')
95+
f.write(f'version: {version} \n')
8896
f.write('verification criteria: ismip6_criteria_v0.csv \n')
8997
f.write('date: '+ today.strftime("%Y/%m/%d") +'\n')
9098
f.write('source: https://github.com/jbbarre/ISM_SimulationChecker \n')
@@ -128,7 +136,6 @@ def files_and_subdirectories(path):
128136
file_counter = 0
129137
#initialize files checked counter
130138
exp_counter = 0
131-
132139
for xp in experiment_directories:
133140

134141
exp_counter += 1
@@ -166,15 +173,17 @@ def files_and_subdirectories(path):
166173
temp_mandatory_var = mandatory_variables
167174
if variable in mandatory_variables:
168175
temp_mandatory_var.remove(variable)
176+
#split the experiment directory name
177+
experiment_chain = xp.split('_')
169178
#get the experiment name (example: exp05)
170-
experiment_name = xp.split('_')[0]
179+
experiment_name = '_'.join(experiment_chain[:-1])
171180
#get the resolution as integer
172-
grid_resolution = int(xp.split('_')[1])
181+
grid_resolution = int(experiment_chain[-1])
173182

174183
if experiment_name in [dic['experiment'] for dic in experiments]:
175184
f.write('\n ')
176185
f.write('**********************************************************\n')
177-
f.write('** Experiment: ' + experiment_name + ' \n ')
186+
f.write(' ** Experiment: ' + experiment_name + ' \n ')
178187
f.write('**********************************************************\n')
179188
f.write('\n ')
180189
if not temp_mandatory_var:
@@ -342,47 +351,59 @@ def files_and_subdirectories(path):
342351
f.write('TIME Tests \n')
343352
#check if time dimension is not missing
344353
if set(['t']).issubset(dim) or set(['time']).issubset(dim):
354+
iteration = len(ds.coords['time'])
345355
start_exp = pd.to_datetime(min(ds['time']).values.astype("datetime64[ns]"))
346356
end_exp = pd.to_datetime(max(ds['time']).values.astype("datetime64[ns]"))
347357
avgyear = 365.2425 # pedants definition of a year length with leap years
348-
duration_days = (end_exp - start_exp)
349-
duration_years = round(pd.to_numeric(duration_days.days / avgyear))
350-
358+
351359
index_exp=[dic['experiment'] for dic in experiments].index(experiment_name)
352360
#test if start_exp and end_exp are datetime format
353361
if isinstance(start_exp, datetime.datetime) & isinstance(end_exp, datetime.datetime):
354-
# test Starting date
355-
if experiments[index_exp]['startinf'] <= start_exp <= experiments[index_exp]['startsup']:
356-
f.write(' - Experiment starts correctly on ' + start_exp.strftime('%Y-%m-%d') + '.\n')
357-
else:
358-
f.write(' - ERROR: the experiment starts the ' + start_exp.strftime('%Y-%m-%d') + '. The date should be comprised between ' + experiments[index_exp]['startinf'].strftime('%Y-%m-%d') + ' and ' + experiments[index_exp]['startsup'].strftime('%Y-%m-%d')+'\n')
359-
var_time_errors += 1
360-
# test Ending date
361-
if experiments[index_exp]['endinf'] <= end_exp <= experiments[index_exp]['endsup']:
362-
f.write(' - Experiment ends correctly on ' + end_exp.strftime('%Y-%m-%d') + '.\n')
363-
else:
364-
f.write(' - ERROR: the experiment ends on ' + end_exp.strftime('%Y-%m-%d') + '. The date should be comprised between ' + experiments[index_exp]['endinf'].strftime('%Y-%m-%d') + ' and ' + experiments[index_exp]['endsup'].strftime('%Y-%m-%d')+'\n')
365-
var_time_errors += 1
366-
# test Duration
367-
if experiments[index_exp]['duration']-1 <= duration_years <= experiments[index_exp]['duration']:
368-
f.write(" - Experiment lasts " + str(duration_years) + ' years.\n')
369-
else:
370-
f.write(' - ERROR: the experiment lasts ' + str(duration_years) + ' years. The duration should be ' + str(experiments[index_exp]['duration']) + ' years\n')
371-
var_time_errors += 1
372-
# test Time step
373-
if isinstance((ds['time'].values[1]-ds['time'].values[0]),datetime.timedelta):
374-
time_step = (ds['time'].values[1]-ds['time'].values[0]).days
375-
else:
376-
if isinstance((ds['time'].values[1]-ds['time'].values[0]),np.timedelta64):
377-
time_step = np.timedelta64(ds['time'].values[1]-ds['time'].values[0], 'D')/ np.timedelta64(1, 'D')
378-
else:
379-
time_step = ds['time'].values[1]-ds['time'].values[10]
380-
381-
if 360<=time_step<=367:
382-
f.write(' - Time step: ' + str(time_step) + ' days' + '\n')
383-
else:
384-
f.write(' - ERROR: the time step(' + str(time_step) + ') should be comprised between [360,367].\n')
362+
#check Monotonicity of the time serie
363+
if strictly_increasing(ds.coords['time']):
364+
# test Time step : should be 360<timestep<367
365+
if isinstance((ds['time'].values[1]-ds['time'].values[0]),datetime.timedelta):
366+
time_step = (ds['time'].values[1]-ds['time'].values[0]).days
367+
else:
368+
if isinstance((ds['time'].values[1]-ds['time'].values[0]),np.timedelta64):
369+
time_step = np.timedelta64(ds['time'].values[1]-ds['time'].values[0], 'D')/ np.timedelta64(1, 'D')
370+
else:
371+
time_step = ds['time'].values[1]-ds['time'].values[10]
372+
373+
if 360<=time_step<=367:
374+
f.write(' - Time step: ' + str(time_step) + ' days' + '\n')
375+
else:
376+
f.write(' - ERROR: the time step(' + str(time_step) + ') should be comprised between [360,367].\n')
377+
var_time_errors += 1
378+
379+
# test duration (iteration = length of the coords 'time')
380+
duration_days = pd.to_timedelta(time_step * iteration,'D')
381+
duration_years = round(pd.to_numeric(duration_days.days / avgyear))
382+
if duration_years == experiments[index_exp]['duration']:
383+
f.write(" - Experiment lasts " + str(duration_years) + ' years.\n')
384+
# test Starting date
385+
if experiments[index_exp]['startinf'] <= start_exp <= experiments[index_exp]['startsup']:
386+
f.write(' - Experiment starts correctly on ' + start_exp.strftime('%Y-%m-%d') + '.\n')
387+
else:
388+
f.write(' - ERROR: the experiment starts the ' + start_exp.strftime('%Y-%m-%d') + '. The date should be comprised between ' + experiments[index_exp]['startinf'].strftime('%Y-%m-%d') + ' and ' + experiments[index_exp]['startsup'].strftime('%Y-%m-%d')+'\n')
389+
var_time_errors += 1
390+
# test Ending date
391+
if experiments[index_exp]['endinf'] <= end_exp <= experiments[index_exp]['endsup']:
392+
f.write(' - Experiment ends correctly on ' + end_exp.strftime('%Y-%m-%d') + '.\n')
393+
else:
394+
f.write(' - ERROR: the experiment ends on ' + end_exp.strftime('%Y-%m-%d') + '. The date should be comprised between ' + experiments[index_exp]['endinf'].strftime('%Y-%m-%d') + ' and ' + experiments[index_exp]['endsup'].strftime('%Y-%m-%d')+'\n')
395+
var_time_errors += 1
396+
else:
397+
end_date = start_exp + datetime.timedelta(days = experiments[index_exp]['duration']*avgyear)
398+
f.write(' - ERROR: the experiment lasts ' + str(duration_years) + ' years. The duration should be ' + str(experiments[index_exp]['duration']) + ' years\n')
399+
f.write(' - As the experiment started on ' + start_exp.strftime('%Y-%m-%d') + ' , it should end on '+ end_date.strftime('%Y-%m-%d')+'\n')
400+
var_time_errors += 1
401+
402+
403+
else: #time serie not monotonous
404+
f.write(' - ERROR: the time serie is not monotonous. Time segments have probably been concatenate in a wrong order.\n')
385405
var_time_errors += 1
406+
386407
else:
387408
#not a datetime format
388409
f.write(' - ERROR: the time format of the Netcdf file is not recognized.Time Tests have been ignored.\n')
@@ -449,7 +470,7 @@ def files_and_subdirectories(path):
449470
else:
450471
f.write('\n ')
451472
f.write('**********************************************************\n')
452-
f.write('** Experiment: ' + experiment_name + ' \n ')
473+
f.write(' ** Experiment: ' + experiment_name + ' \n ')
453474
f.write('**********************************************************\n')
454475
f.write('\n ')
455476
f.write('ERROR: The compliance check is ignored for experiment ' + experiment_name + ' as it is not in [hist, ctrl, ctrl_proj, exp01, exp02, exp03, exp04, exp05, exp06, exp07, exp08, exp09, exp10, exp11, exp12, exp13]. \n')
Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,9 @@ litempbotgr;x-y-t;ST;Basal temperature beneath grounded ice sheet;temperature_at
1313
litemptop;x-y-t;ST;Surface temperature;temperature_at_top_of_ice_sheet_model;temperature_at_ground_level_in_snow_or_firn;K;0;183;274;183;274
1414
lithk;x-y-t;ST;Ice thickness;land_ice_thickness;;m;1;0;5000;0;5000
1515
orog;x-y-t;ST;Surface elevation;surface_altitude;;m;1;0;4500;0;4500
16-
sftflf;x-y-t;ST;Floating ice sheet area fraction;floating_ice_shelf_area_fraction;floating_ice_sheet_area_fraction;unitless;1;0;1;0;1
17-
sftgif;x-y-t;ST;Land ice area fraction;land_ice_area_fraction;;unitless;1;0;1;0;1
18-
sftgrf;x-y-t;ST;Grounded ice sheet area fraction;grounded_ice_sheet_area_fraction;;unitless;1;0;1;0;1
16+
sftflf;x-y-t;ST;Floating ice sheet area fraction;floating_ice_shelf_area_fraction;floating_ice_sheet_area_fraction;1;1;0;1;0;1
17+
sftgif;x-y-t;ST;Land ice area fraction;land_ice_area_fraction;;1;1;0;1;0;1
18+
sftgrf;x-y-t;ST;Grounded ice sheet area fraction;grounded_ice_sheet_area_fraction;;1;1;0;1;0;1
1919
strbasemag;x-y-t;ST;Basal drag;land_ice_basal_drag;magnitude_of_land_ice_basal_drag;Pa;1;0;200000;0;200000
2020
topg;x-y-t;ST;Bedrock elevation;bedrock_altitude;;m;1;-7000;4000;-3000;4000
2121
xvelbase;x-y-t;ST;Basal velocity in x;land_ice_basal_x_velocity;;m s-1;0;-0,000400;0,000400;-0,000800;0,000800

0 commit comments

Comments
 (0)