Source code for reV.losses.utils

# -*- coding: utf-8 -*-
"""reV-losses utilities.

"""
import calendar
import logging

import numpy as np

from reV.utilities.exceptions import reVLossesValueError

logger = logging.getLogger(__name__)

# 1900 is just a representative year, since a year input is required
DAYS_PER_MONTH = [calendar.monthrange(1900, i)[1] for i in range(1, 13)]
FIRST_DAY_INDEX_OF_MONTH = np.cumsum([0] + DAYS_PER_MONTH[:-1])


[docs]def convert_to_full_month_names(month_names): """Format an iterable of month names to match those in :mod:`calendar`. This function will format each input name to match the formatting in :obj:`calendar.month_name` (upper case, no extra whitespace), and it will convert all abbreviations to full month names. No other assumptions are made about the inputs, so an input string " abc " will get formatted and passed though as "Abc". Parameters ---------- month_names : iter An iterable of strings representing the input month names. Month names can be unformatted and contain 3-letter month abbreviations. Returns ------- :obj:`list` A list of month names matching the formatting of :obj:`calendar.month_name` (upper case, no extra whitespace). Abbreviations are also converted to a full month name. Examples -------- >>> input_names = ['March', ' aprIl ', 'Jun', 'jul', ' abc '] >>> convert_to_full_month_names(input_names) ['March', 'April', 'June', 'July', 'Abc'] """ formatted_names = [] for name in month_names: month_name = format_month_name(name) month_name = full_month_name_from_abbr(month_name) or month_name formatted_names.append(month_name) return formatted_names
[docs]def filter_unknown_month_names(month_names): """Split the input into known and unknown month names. Parameters ---------- month_names : iter An iterable of strings representing the input month names. Month names must match the formatting in :obj:`calendar.month_name` (upper case, no extra whitespace), otherwise they will be placed into the ``unknown_months`` return list. Returns ------- known_months : :obj:`list` List of known month names. unknown_months : :obj:`list` List of unknown month names. """ known_months, unknown_months = [], [] for name in month_names: if name in calendar.month_name: known_months.append(name) else: unknown_months.append(name) return known_months, unknown_months
[docs]def hourly_indices_for_months(month_names): """Convert month names into a list of hourly indices. Given a list of month names, this function will return a list of indices such that any index value corresponds to an hour within the input months. Parameters ---------- month_names : iter An iterable of month names for the desired starting indices. The month names must match the formatting in :obj:`calendar.month_name` (upper case, no extra whitespace), otherwise their hourly indices will not be included in the output. Returns ------- :obj:`list` A list of hourly index values such that any index corresponds to an hour within the input months. """ indices = [] for ind in sorted(month_indices(month_names)): start_index = FIRST_DAY_INDEX_OF_MONTH[ind] * 24 hours_in_month = DAYS_PER_MONTH[ind] * 24 indices += list(range(start_index, start_index + hours_in_month)) return indices
[docs]def month_indices(month_names): """Convert input month names to an indices (0-11) of the months. Parameters ---------- month_names : iter An iterable of month names for the desired starting indices. The month names must match the formatting in :obj:`calendar.month_name` (upper case, no extra whitespace), otherwise their index will not be included in the output. Returns ------- :obj:`set` A set of month indices for the input month names. Unknown month indices (-1) are removed. """ return {month_index(name) for name in month_names} - {-1}
[docs]def month_index(month_name): """Convert a month name (as string) to an index (0-11) of the month. Parameters ---------- month_name : str Name of month to corresponding to desired index. This input must match the formatting in :obj:`calendar.month_name` (upper case, no extra whitespace). Returns ------- :obj:`int` The 0-index of the month, or -1 if the month name is not understood. Examples -------- >>> month_index("June") 5 >>> month_index("July") 6 >>> month_index("Jun") -1 >>> month_index("july") -1 """ for month_ind in range(12): if calendar.month_name[month_ind + 1] == month_name: return month_ind return -1
[docs]def format_month_name(month_name): """Format a month name to match the names in the :mod:`calendar` module. In particular, any extra spaces at the beginning or end of the string are stripped, and the name is converted to a title (first letter is uppercase). Parameters ---------- month_name : str Name of month. Returns ------- :obj:`str` Name of month, formatted to match the month names in the :mod:`calendar` module. Examples -------- >>> format_month_name("June") "June" >>> format_month_name("aprIl") "April" >>> format_month_name(" aug ") "Aug" """ return month_name.strip().title()
[docs]def full_month_name_from_abbr(month_name): """Convert a month abbreviation to a full month name. Parameters ---------- month_name : str Abbreviated month name. Must be one of: - "Jan" - "Feb" - "Mar" - "Apr" - "May" - "Jun" - "Jul" - "Aug" - "Sep" - "Oct" - "Nov" - "Dec" If the input does not match one of these, this function returns :obj:`None`. Returns ------- :obj:`str` | :obj:`None` Unabbreviated month name, or :obj:`None` if input abbreviation is not understood. Examples -------- >>> full_month_name_from_abbr("Jun") "June" >>> full_month_name_from_abbr("June") is None True >>> full_month_name_from_abbr('Abcdef') is None True """ for month_index in range(1, 13): if calendar.month_abbr[month_index] == month_name: return calendar.month_name[month_index]
def _validate_arrays_not_empty(obj, array_names=None): """Validate that the input data arrays are not empty. """ array_names = array_names or [] for name in array_names: try: arr = getattr(obj, name) except AttributeError: continue if not arr.size: msg = "Invalid {} input: Array is empty! - {}" msg = msg.format(name.replace('_', ' '), arr) logger.error(msg) raise reVLossesValueError(msg)