cf.Field.match

Field.match(description=None, items=None, rank=None, ndim=None, exact=False, match_and=True, inverse=False)[source]

Test whether or not the field satisfies the given conditions.

Different types of conditions may be set with the parameters:

Parameter What gets tested
description Field properties and attributes
items Field items
rank The number of domain axes
ndim The number of field data array axes

By default, when multiple criteria are given the field matches if it satisfies the conditions given by each one.

See also

items, select

Quick start examples

There is great flexibility in the types of test which can be specified, and as a result the documentation is very detailed in places. These preliminary, simple examples show that the usage need not always be complicated and may help with understanding the keyword descriptions.

  1. Test if a field contains air temperature data, as given determined by its identity method:

    >>> f.match('air_temperature')
    
  2. Test if a field contains air temperature data, as given determined by its identity method, or has a long name which contains the string “temp”:

    >>> f.match(['air_temperature', {'long_name': cf.eq('.*temp.*', regex=true)}])
    
  3. Test if a field has at least one longitude grid cell point on the Greenwich meridian:

    >>> f.match(items={'longitude': 0})
    
  4. Test if a field has latitude grid cells which all have a resolution of less than 1 degree:

    >>> f.match(items={'latitude': cf.cellsize(cf.lt(1, 'degree'))})
    
  5. Test if a field has exactly 4 domain axes:

    >>> f.match(rank=4)
    
  6. Examples 1 to 4 may be combined to test if a field has exactly 4 domain axes, contains air temperature data, has at least one longitude grid cell point on the Greenwich meridian and all latitude grid cells have a resolution of less than 1 degree:

    >>> f.match('air_temperature',
    ...         items={'longitude': 0,
    ...                'latitude': cf.cellsize(cf.lt(1, 'degree'))},
    ...         rank=4)
    
  7. Test if a field contains Gregorian calendar monthly mean data array values:

    >>> f.match({'cell_methods': cf.CellMethods('time: mean')},
    ...         items={'time': cf.cellsize(cf.wi(28, 31, 'days'))})
    

Further examples are given within and after the description of the arguments.

Parameters:
description: optional

Set conditions on the field’s CF property and attribute values. description may be one, or a sequence of:

  • None or an empty dictionary. Always matches the field. This is the default.
  • A string which identifies string-valued metadata of the field and a value to compare it against. The value may take one of the following forms:

    description Interpretation
    Contains : Selects on the CF property specified before the first :
    Contains % Selects on the attribute specified before the first %
    Anything else Selects on identity as returned by the identity method

    By default the part of the string to be compared with the item is treated as a regular expression understood by the re module and the field matches if its appropriate value matches the regular expression using the re.match method (i.e. if zero or more characters at the beginning of field’s value match the regular expression pattern). See the exact parameter for details.

    Example:

    To match a field with identity beginning with “lat”: match='lat'.

    Example:

    To match a field with long name beginning with “air”: match='long_name:air'.

    Example:

    To match a field with netCDF variable name of exactly “tas”: match='ncvar%tas$'.

    Example:

    To match a field with identity which ends with the letter “z”: match='.*z$'.

    Example:

    To match a field with long name which starts with the string “.*a”: match='long_name%\.\*a'.

  • A cf.Query object to be compared with field’s identity, as returned by its identity method.

    Example:

    To match a field with identity of exactly “air_temperature” you could set match=cf.eq('air_temperature') (see cf.eq).

    Example:

    To match a field with identity ending with “temperature” you could set match=cf.eq('.*temperature$', exact=False) (see cf.eq).

  • A dictionary which identifies properties of the field with corresponding tests on their values. The field matches if all of the tests in the dictionary are passed.

    In general, each dictionary key is a CF property name with a corresponding value to be compared against the field’s CF property value.

    If the dictionary value is a string then by default it is treated as a regular expression understood by the re module and the field matches if its appropriate value matches the regular expression using the re.match method (i.e. if zero or more characters at the beginning of field’s value match the regular expression pattern). See the exact parameter for details.

    Example:

    To match a field with standard name of exactly “air_temperature” and long name beginning with the letter “a”: match={'standard_name': cf.eq('air_temperature'), 'long_name': 'a'} (see cf.eq).

    Some key/value pairs have a special interpretation:

    Special key Value
    'units' The value must be a string and by default is evaluated for equivalence, rather than equality, with the field’s units property, for example a value of 'Pa' will match units of Pascals or hectopascals, etc. See the exact parameter.
    'calendar' The value must be a string and by default is evaluated for equivalence, rather than equality, with the field’s calendar property, for example a value of 'noleap' will match a calendar of noleap or 365_day. See the exact parameter.
    'cell_methods' The value must be a cf.CellMethods object containing N cell methods and by default is evaluated for equivalence with the last N cell methods contained within the field’s cell_methods property. See the exact parameter.
    None The value is interpreted as for a string value of the description parameter. For example, description={None: 'air'} is equivalent to match='air' and description={None: 'ncvar%pressure'} is equivalent to description='ncvar%pressure'.
    Example:

    To match a field with standard name starting with “air”, units of temperature and a netCDF variable name beginning with “tas” you could set match={'standard_name': 'air', 'units': 'K', None: 'ncvar%tas'}.

    Example:

    To match a field whose last two cell methods are equivalent to “time: minimum area: mean”: match={'cell_methods': cf.Cellmethods('time: minimum area: mean'). This would match a field which has, for example, cell methods of “height: mean time: minimum area: mean”.

If description is a sequence of any combination of the above then the field matches if it matches at least one element of the sequence:

Example:

>>> f.match('air_temperature')
True
>>> f.match('air_pressure')
False
>>> f.match({'units': 'hPa', 'long_name': 'foo'})
False
>>> f.match(['air_temperature',
...          'air_pressure',
...          {'units': 'hPa', 'long_name': 'foo'}])
True

If the sequence is empty then the field always matches.

items: dict, optional

A dictionary which identifies items of the field (dimension coordinate, auxiliary coordinate, cell measure or coordinate reference objects) with corresponding tests on their elements. The field matches if all of the specified items exist and their tests are passed.

Each dictionary key specifies an item to test as the one that would be returned by this call of the field’s item method: f.item(key, exact=exact) (see cf.Field.item).

The corresponding value is, in general, any object for which the item may be compared with for equality (==). The test is passed if the result evaluates to True, or if the result is an array of values then the test is passed if at least one element evaluates to true.

If the value is None then the test is always passed, i.e. this case tests for item existence.

Example:

To match a field which has a latitude coordinate value of exactly 30: items={'latitude': 30}.

Example:

To match a field whose longitude axis spans the Greenwich meridien: items={'longitude': cf.contain(0)} (see cf.contain).

Example:

To match a field which has a time coordinate value of 2004-06-01: items={'time': cf.dt('2004-06-01')} (see cf.dt).

Example:

To match a field which has a height axis: items={'Z': None}.

Example:

To match a field which has a time axis and depth coordinates greater then 1000 metres: items={'T': None, 'depth': cf.gt(1000, 'm')} (see cf.gt).

Example:

To match a field with time coordinates after than 1989 and cell sizes of between 28 and 31 days: items={'time': cf.dtge(1990) & cf.cellsize(cf.wi(28, 31, 'days'))} (see cf.dtge, cf.cellsize and cf.wi).

rank: optional

Specify a condition on the number of axes in the field. The field matches if its number of domain axes equals rank. A range of values may be selected if rank is a cf.Query object. Not to be confused with the ndim parameter (the number of data array axes may be fewer than the number of domain axes).

Example:

rank=2 matches a field with exactly two domain axes and rank=cf.wi(3, 4) matches a field with three or four domain axes (see cf.wi).

ndim: optional

Specify a condition on the number of axes in the field’s data array. The field matches if its number of data array axes equals ndim. A range of values may be selected if ndim is a cf.Query object. Not to be confused with the rank parameter (the number of domain axes may be greater than the number of data array axes).

Example:

ndim=2 matches a field with exactly two data array axes and ndim=cf.le(2) matches a field with fewer than three data array axes (see cf.le).

exact: bool, optional

The exact parameter applies to the interpretation of string values of the description parameter and of keys of the items parameter. By default exact is False, which means that:

  • A string value is treated as a regular expression understood by the re module.
  • Units and calendar values in a description dictionary are evaluated for equivalence rather then equality (e.g. “metre” is equivalent to “m” and to “km”).
  • A cell methods value containing N cell methods in a description dictionary is evaluated for equivalence with the last *N cell methods contained within the field’s *cell_methods property.
Example:

To match a field with a standard name which begins with “air” and any units of pressure: f.match({'standard_name': 'air', 'units': 'hPa'}).

Example:

f.match({'cell_methods': cf.CellMethods('time: mean (interval 1 hour)')}) would match a field with cell methods of “area: mean time: mean (interval 60 minutes)”.

If exact is True then:

  • A string value is not treated as a regular expression.
  • Units and calendar values in a description dictionary are evaluated for exact equality rather than equivalence (e.g. “metre” is equal to “m”, but not to “km”).
  • A cell methods value in a description dictionary is evaluated for exact equality to the field’s cell methods.
Example:

To match a field with a standard name of exactly “air_pressure” and units of exactly hectopascals: f.match({'standard_name': 'air_pressure', 'units': 'hPa'}, exact=True).

Example:

To match a field with a cell methods of exactly “time: mean (interval 1 hour)”: f.match({'cell_methods': cf.CellMethods('time: mean (interval 1 hour)').

Note that cf.Query objects provide a mechanism for overriding the exact parameter for individual values.

Example:

f.match({'standard_name': cf.eq('air', exact=False), 'units': 'hPa'}, exact=True) will match a field with a standard name which begins “air” but has units of exactly hectopascals (see cf.eq).

Example:

f.match({'standard_name': cf.eq('air_pressure'), 'units': 'hPa'}) will match a field with a standard name of exactly “air_pressure” but with units which equivalent to hectopascals (see cf.eq).

match_and: bool, optional

By default match_and is True and the field matches if it satisfies the conditions specified by each test parameter (description, items, rank and ndim).

If match_and is False then the field will match if it satisfies at least one test parameter’s condition.

Example:

To match a field with a standard name of “air_temperature” and 3 data array axes: f.match('air_temperature', ndim=3). To match a field with a standard name of “air_temperature” or 3 data array axes: f.match('air_temperature", ndim=3, match_and=False).

inverse: bool, optional

If True then return the field matches if it does not satisfy the given conditions.

Example:

>>> f.match('air', ndim=4, inverse=True) == not f.match('air', ndim=4)
True
Returns:
out: bool

True if the field satisfies the given criteria, False otherwise.

Examples:

Field identity starts with “air”:

>>> f.match('air')

Field identity ends contains the string “temperature”:

>>> f.match('.*temperature')

Field identity is exactly “air_temperature”:

>>> f.match('^air_temperature$')
>>> f.match('air_temperature', exact=True)

Field has units of temperature:

>>> f.match({'units': 'K'}):

Field has units of exactly Kelvin:

>>> f.match({'units': 'K'}, exact=True)

Field identity which starts with “air” and has units of temperature:

>>> f.match({None: 'air', 'units': 'K'})

Field identity starts with “air” and/or has units of temperature:

>>> f.match(['air', {'units': 'K'}])

Field standard name starts with “air” and/or has units of exactly Kelvin:

>>> f.match([{'standard_name': cf.eq('air', exact=False), {'units': 'K'}],
...         exact=True)

Field has height coordinate values greater than 63km:

>>> f.match(items={'height': cf.gt(63, 'km')})

Field has a height coordinate object with some values greater than 63km and a north polar point on its horizontal grid:

>>> f.match(items={'height': cf.gt(63, 'km'),
...                'latitude': cf.eq(90, 'degrees')})

Field has some longitude cell sizes of 3.75:

>>> f.match(items={'longitude': cf.cellsize(3.75)})

Field latitude cell sizes within a tropical region are all no greater than 1 degree:

>>> f.match(items={'latitude': (cf.wi(-30, 30, 'degrees') &
...                             cf.cellsize(cf.le(1, 'degrees')))})

Field contains monthly mean air pressure data and all vertical levels within the bottom 100 metres of the atmosphere have a thickness of 20 metres or less:

>>> f.match({None: '^air_pressure$', 'cell_methods': cf.CellMethods('time: mean')},
...         items={'height': cf.le(100, 'm') & cf.cellsize(cf.le(20, 'm')),
...                'time': cf.cellsize(cf.wi(28, 31, 'days'))})