v2.0 (14 Feb 2018)
******************

This document explains the changes made to Iris for this release
(:doc:`View all changes <index>`.)


Features
========

.. _showcase:

.. admonition:: Dask Integration

  The use of `Biggus`_ to provide support for *virtual arrays* and
  *lazy evaluation* within Iris has been replaced with `Dask`_.

  In addition the concept of *lazy data*, already used for the
  :class:`~iris.cube.Cube` data component, has now been extended to the
  data arrays of a :class:`~iris.coords.Coord` and an
  :class:`~iris.aux_factory.AuxCoordFactory`.

  This is a major feature enhancement, allowing Iris to leverage dask's rich
  functionality and community knowledge.

  In particular, Dask's *threaded*, *multiprocessing* or *distributed*
  `schedulers`_ can be used in order to best utilise available compute and
  memory resource. For further details, see :doc:`Real and Lazy Data
  </userguide/real_and_lazy_data>`.

* Changes to the :class:`iris.cube.Cube`:

  * The *new* :meth:`~iris.cube.Cube.core_data` method returns the *real* or
    *lazy* :class:`~iris.cube.Cube` :data:`data`.

  * The *new* in-place arithmetic operators :data:`__iadd__`, :data:`__idiv__`,
    :data:`__imul__`, :data:`__isub__`, and :data:`__itruediv__` have been
    added to support :class:`~iris.cube.Cube` operations :data:`+=`,
    :data:`/=`, :data:`*=`, and :data:`-=`. Note that, for **divison**
    *__future__.division* is always in effect.

* Changes to the :class:`iris.coords.Coord`:

  * The *new* :attr:`~iris.coords.Coord.bounds_dtype` property (read-only)
    provides the :data:`dtype` of the coordinate bounds, if they exist.

  * The *new* :meth:`~iris.coords.Coord.core_points` and
    :meth:`~iris.coords.Coord.core_bounds` methods return the *real* or *lazy*
    :class:`~iris.coords.Coord` :data:`points` and :data:`bounds` data,
    respectively.

  * The *new* :meth:`~iris.coords.Coord.has_lazy_points` and
    :meth:`~iris.coords.Coord.has_lazy_bounds` boolean methods return whether
    the coordinate has *lazy* :data:`points` and *lazy* :data:`bounds` data,
    respectively.

  * The *new* :meth:`~iris.coords.Coord.lazy_points` and
    :meth:`~iris.coords.Coord.lazy_bounds` methods return *lazy*
    representations of the coordinate :data:`points` and :data:`bounds` data,
    respectively.


The :data:`iris.FUTURE` has Arrived!
------------------------------------

Throughout version 1 of Iris a set of toggles in
:attr:`iris.FUTURE` were maintained. These toggles allowed certain "future"
behaviour to be enabled. Since the future has now arrived in Iris 2,
all existing toggles in :attr:`iris.FUTURE` now default to :data:`True`.

 * :attr:`iris.Future.cell_datetime_objects`

   * Use of this FUTURE toggle is now deprecated.
   * :class:`iris.coords.Cell` objects in time coordinates now contain datetime objects by default and not numbers.
     For example::

        >>> cube = iris.load_cube(iris.sample_data_path('air_temp.pp'))
        >>> print(cube.coord('time').cell(0).point)
            1998-12-01 00:00:00

      This change particularly impacts constraining datasets on time. All time constraints
      must now be constructed with datetime objects or :class:`~iris.time.PartialDateTime` objects.
      See userguide section 2.2.1 for more details on producing time constraints.


 * :attr:`iris.Future.netcdf_promote`

   * Use of this FUTURE toggle is now deprecated.
   * Removed deprecated behaviour that does not automatically promote NetCDF variables to cubes.
     This change means that NetCDF variables that define reference surfaces for
     dimensionless vertical coordinates will always be promoted and loaded as
     independent cubes.

 * :attr:`iris.Future.netcdf_no_unlimited`

   * Use of this FUTURE toggle is now deprecated.
   * Removed deprecated behaviour that automatically set the length of the outer
     netCDF variable to 'UNLIMITED' on save. This change means that no cube
     dimension coordinates will be automatically saved as netCDF variables with
     'UNLIMITED' length.
   * You can manually specify cube dimension coordinates to save with 'UNLIMITED'
     length. For example::

       >>> iris.save(my_cube, 'my_result_file.nc', unlimited_dimensions=['latitude'])

 * :attr:`iris.Future.clip_latitudes`

   * Use of this FUTURE toggle is now deprecated.
   * The :meth:`iris.coords.Coord.guess_bounds()` now limits the guessed bounds
     to [-90, 90] for latitudes by default. The ability to turn this behaviour
     off is now deprecated.


Bugs Fixed
==========

* Indexing or slicing an :class:`~iris.coords.AuxCoord` coordinate will return a coordinate with
  :data:`points` and :data:`bounds` data that are new copied arrays, rather than views onto those of
  the original parent coordinate.

* Indexing or slicing a cell measure will return a new cell measure with
  :data:`data` that is a new copied array, rather than a view onto the original parent cell measure.

* Performing an in-place arithmetic :func:`~iris.analysis.maths.add`,
  :func:`~iris.analysis.maths.divide`, :func:`~iris.analysis.maths.multiply`,
  or :func:`~iris.analysis.maths.subtract` operation on a
  :class:`~iris.cube.Cube` with :data:`integer` or :data:`boolean` data with
  a :data:`float` result will raise an :data:`ArithmeticError` exception.

* Lazy data now refers to absolute paths rather than preserving the form that
  was passed to iris.load functions. This means that it is possible to use
  relative paths at load, change working directory, and still expect to be able
  to load any un-loaded/lazy data. (#2325)

* The order in which files are passed to iris.load functions is now the order in
  which they are processed. (#2325)

* Loading from netCDF files with :func:`iris.load` will load a cube for each scalar variable,
  a variable that does not reference a netCDF dimension, unless that scalar variable is identified as
  a CF scalar coordinate, referenced from another data variable via the 'coordinates' attribute.
  Previously such data variables were ignored during load.


Incompatible Changes
====================

* The :meth:`~iris.cube.Cube.lazy_data` method no longer accepts any arguments.
  Setting lazy data should now be done with :attr:`cube.data
  <iris.cube.Cube.data>`.

.. admonition:: Significant Changes in Calculated Results

  Due to the replacement of `Biggus`_ with `Dask`_, as described above, the results
  of certain types of calculation may have significantly different values from
  those obtained in earlier versions.
  This is of a much greater order than the usual small changes in floating
  point results : it applies especially to any data with masked points, or of
  long integer types.

* Due to concerns regarding maintainability and API consistency the
  :attr:`iris.cube.Cube.share_data` flag introduced in v1.13 has been removed.
  Intra-cube data sharing is a oft-requested feature that we will be targeting
  in a future Iris release.

* Using :meth:`~iris.cube.Cube.convert_units` on a cube with unknown units will
  now result in a :data:`UnitConversionError` being raised.

* ``iris.fileformats.pp_rules`` has been renamed to
  :mod:`iris.fileformats.pp_load_rules` for consistency with the new
  :mod:`iris.fileformats.pp_save_rules`.

* Fill values are no longer taken from the cube's `data` attribute when it is
  a masked array.

* When saving a cube or list of cubes in NetCDF format, a fill value or list of
  fill values can be specified via a new `fill_value` argument. If a list is
  supplied, each fill value will be applied to each cube in turn. If a
  `fill_value` argument is not specified, the default fill value for the file
  format and the cube's data type will be used.

* When saving to PP, the "standard" BMDI of -1e30 is now always applied in
  ``PPField`` generation. To save PP data with an alternative BMDI, use
  :func:`iris.fileformats.pp.save_pairs_from_cube` to generate ``PPFields``,
  and modify these before saving them to file.

* A 'fill_value' key can no longer be specified as part of the `packing`
  argument to `iris.save` when saving in netCDF format. Instead, a fill value or
  list of fill values should be specified as a separate `fill_value` argument if
  required.

* If the `packing` argument to `iris.save` is a dictionary, an error is raised
  if it contains any keys other than 'dtype', 'scale_factor' and 'add_offset'.

* The deprecated :mod:`iris.fileformats.grib` was removed. All Iris GRIB
  functionality is now delivered through :mod:`iris-grib`.

* In Iris v1 it was possible to configure Iris to log at import time through
  `iris.config.LOGGING`. This capability has been removed in Iris v2.

* When coordinates have no well defined plot axis, :mod:`iris.plot` and
  :mod:`iris.quickplot` routines now use the order of the cube's dimensions
  to determine the coordinates to plot as the x and y axis of a plot. 

* The cf_units dependency version has been updated to v1.2.0, which prints
  shorter unit strings. For example, the unit ``meter-second^-1`` is now
  printed as ``m.s-1``.


Deprecation
===========

All deprecated functionality that was announced for removal in Iris 2.0 has
been removed. In particular:

* The deprecated keyword arguments ``coord`` and ``name`` have been removed from
  the :class:`iris.cube.Cube` constructor.

* The deprecated methods ``iris.cube.Cube.add_history``,
  ``iris.cube.Cube.assert_valid`` and ``iris.cube.Cube.regridded`` have
  been removed from :class:`iris.cube.Cube`.

* The deprecated module ``iris.fileformats.pp_packing`` has been removed.

* The deprecated module ``iris.proxy`` has been removed.

* The deprecated configuration variable ``SAMPLE_DATA_DIR`` has been removed
  from ``iris.config`` in favour of user installation of
  the ``iris-sample-data`` package.

* The deprecated module ``iris.unit`` has been removed in favour of
  :mod:`cf_units`.

* The ``BitwiseInt`` class has been removed from :mod:`iris.fileformats.pp`.

* Removed deprecated functions ``reset_load_rules``, ``add_save_rules``,
  ``reset_save_rules`` and ``as_pairs`` from :mod:`iris.fileformats.pp`.

* The deprecated module ``iris.analysis.interpolate`` has been removed, along
  with the following deprecated classes and functions:

    * ``iris.analysis.interpolate.linear``
    * ``iris.analysis.interpolate.nearest_neighbour_data_value``
    * ``iris.analysis.interpolate.regrid``
    * ``iris.analysis.interpolate.regrid_to_max_resolution``
    * ``iris.analysis.interpolate.extract_nearest_neighbour``
    * ``iris.analysis.interpolate.nearest_neighbour_indices``
    * ``iris.analysis.interpolate.Linear1dExtrapolator``

* Removed deprecated module ``iris.experimental.fieldsfile``.
  Note that there is no direct replacement for
  ``:meth:iris.experimental.fieldsfile.load``, which specifically performed
  fast loading from _either_ PP or FF files.
  Instead, please use the `:meth:iris.fileformats.um.structured_um_loading`
  context manager, and within that context call `:meth:iris.load`, or the format-specific
  `:meth:iris.fileformats.pp.load_cubes` or
  `:meth:iris.fileformats.um.load_cubes`.

* Removed deprecated module ``iris.fileformats.ff``.
  Please use facilities in :mod:`iris.fileformats.um` instead.

* Removed deprecated and unused kwarg ``ignore`` from the following functions:
    * :func:`iris.analysis.calculus.curl`,
    * :func:`iris.analysis.maths.add`, and
    * :func:`iris.analysis.maths.subtract`.

* Deprecated functions ``iris.util.broadcast_weights``,
  ``iris.util.ensure_array`` and ``iris.util.timers`` have been removed from
  :mod:`iris.util`.

* The following classes and functions have been removed from
  :mod:`iris.fileformats.rules`:

	* ``iris.fileformat.rules.calculate_forecast_period``
	* ``iris.fileformat.rules.log``
	* ``iris.fileformat.rules.CMAttribute``
	* ``iris.fileformat.rules.CMCustomAttribute``
	* ``iris.fileformat.rules.CoordAndDims``
	* ``iris.fileformat.rules.DebugString``
	* ``iris.fileformat.rules.FunctionRule``
	* ``iris.fileformat.rules.ProcedureRule``
	* ``iris.fileformat.rules.Rule``
	* ``iris.fileformat.rules.RulesContainer``
	* ``iris.fileformat.rules.RuleResult``

* In addition the deprecated keyword argument ``legacy_custom_rules`` has been
  removed from the :class:`iris.fileformats.rules.Loader` constructor.


Documentation
=============

* A new UserGuide chapter on :doc:`Real and Lazy Data
  </userguide/real_and_lazy_data>` has been added, and referenced from key
  points in the :doc:`User Guide </userguide/index>` .


.. _Biggus: https://biggus.readthedocs.io/en/latest/
.. _Dask: http://dask.pydata.org/en/latest/
.. _iris_grib: https://github.com/SciTools/iris-grib/
.. _schedulers: http://dask.pydata.org/en/latest/scheduler-overview.html
