We are seeing a similar problem reported here:
although there have been no replies to this thread.
We are attempting to use iris to write-out some cf-compliant netCDF files for a model intercomparison project. In the data specification both _FillValue and missing_value need to be defined.
The data is generated as a masked array which is allowing _FillValue to be defined, however missing_value cannot be manually defined, as it raises the error
ValueError: 'missing_value' is not a permitted attribute
In fact, neither _FillValue or missing_value can be manually defined or edited (and I'm not sure how the masked array is able to create a _FillValue while I am not).
I have a number of questions:
- Is it possible at all to manually set missing_value (and _FillValue)
- Should the masked array be also setting the missing_value attribute, as well as the _FillValue attribute
I have produced a minimal code to highlight this problem which I have tested in Iris 1.7.1 and 1.7.3. To use this to you first need to download
hybrid_height.nc needs to be downloaded from
The example iris script is below, although the missing_value section will need to be commented out to be able to crash at the _FillValue section.
float air_potential_temperature(model_level_number, grid_latitude, grid_longitude) ;
air_potential_temperature:standard_name = "air_potential_temperature" ;
air_potential_temperature:units = "K" ;
air_potential_temperature:ukmo__um_stash_source = "m01s00i004" ;
air_potential_temperature:source = "Data from Met Office Unified Model 7.04" ;
air_potential_temperature:grid_mapping = "rotated_latitude_longitude" ;
air_potential_temperature:coordinates = "forecast_period forecast_reference_time level_height sigma surface_altitude time" ;
and the equivalent metadata from the MaskedArray.nc file (see script) is
float air_potential_temperature(model_level_number, grid_latitude, grid_longitude) ;
air_potential_temperature:_FillValue = 1.e+20f ;
air_potential_temperature:standard_name = "air_potential_temperature" ;
air_potential_temperature:units = "K" ;
air_potential_temperature:um_stash_source = "m01s00i004" ;
air_potential_temperature:grid_mapping = "rotated_latitude_longitude" ;
air_potential_temperature:coordinates = "forecast_period forecast_reference_time level_height sigma surface_altitude time" ;
i.e. _FillValue has been added.
Output from the script is:
{'source': 'Data from Met Office Unified Model 7.04', 'STASH': STASH(model=1, section=0, item=4), 'Conventions': 'CF-1.5'}
------------------------------
{'source': 'Data from Met Office Unified Model 7.04', 'STASH': STASH(model=1, section=0, item=4), 'Conventions': 'CF-1.5'}
Traceback (most recent call last):
File "<string>", line 1, in <module>
File "iris_min.py", line 26, in <module>
cube.attributes['missing_value'] = 1e+20
File "/usr/local/shared/ubuntu-12.04/x86_64/python2.7-iris/1.7.1/local/lib/python2.7/site-packages/Iris-1.7.1-py2.7.egg/iris/_cube_coord_common.py", line 61, in __setitem__
raise ValueError('%r is not a permitted attribute' % key)
ValueError: 'missing_value' is not a permitted attribute
and if the section trying to add-in missing_value is commented out then the output is
{'source': 'Data from Met Office Unified Model 7.04', 'STASH': STASH(model=1, section=0, item=4), 'Conventions': 'CF-1.5'}
------------------------------
{'source': 'Data from Met Office Unified Model 7.04', 'STASH': STASH(model=1, section=0, item=4), 'Conventions': 'CF-1.5'}
Traceback (most recent call last):
File "<string>", line 1, in <module>
File "iris_min.py", line 32, in <module>
cube.attributes['_FillValue'] = 1e+20
File "/usr/local/shared/ubuntu-12.04/x86_64/python2.7-iris/1.7.1/local/lib/python2.7/site-packages/Iris-1.7.1-py2.7.egg/iris/_cube_coord_common.py", line 61, in __setitem__
raise ValueError('%r is not a permitted attribute' % key)
ValueError: '_FillValue' is not a permitted attribute
Many thanks for your help.
Luke
import iris
import numpy.ma as ma
filename = 'hybrid_height.nc'
file = iris.sample_data_path(filename)
# Obtainable from:
# https://github.com/SciTools/iris-sample-data/tree/master/sample_data
# Stick in pwd.
try:
cube = iris.load_cube(file)
except IOError:
cube = iris.load_cube(filename)
# now mask of a certain part of the cube data
cube.data = ma.masked_greater(cube.data,288.0)
print cube.attributes
# masked array should be able to set _FillValue...
iris.fileformats.netcdf.save(cube,'MaskedArray.nc',netcdf_format='NETCDF4_CLASSIC')
print '------------------------------'
print cube.attributes
# ...but it is impossible to add-in the missing_value attribute...
cube.attributes['missing_value'] = 1e+20
iris.fileformats.netcdf.save(cube,'missing_value.nc',netcdf_format='NETCDF4_CLASSIC')
print '------------------------------'
print cube.attributes
# ...or indeed try to add/edit _FillValue.
cube.attributes['_FillValue'] = 1e+20
iris.fileformats.netcdf.save(cube,'FillValue.nc',netcdf_format='NETCDF4_CLASSIC')