@classmethod
def list(cls, page_size: int=None, next_token: str=None, sort: str=None,
    archive_reason: str=None, folder_id: str=None, modified_at: str=None,
    name: str=None, project_id: str=None, schema_id: str=None, registry_id:
    str=None, **kwargs):
    """List :class:`DNASequence` models.

        :param page_size: Number of results to return. Defaults to 50, maximum of 100.
        :param next_token: Token for pagination
        :param sort: Method by which to order search results. Valid sorts are
                    modifiedAt (modified time, most recent first) and name
                    (entity name, alphabetical). Optionally add :asc or
                    :desc to specify ascending or descending order.
                    Default is modifiedAt.
        :param archive_reason: Archive reason. Restricts DNA Sequences to those with
                the specified archive reason. Use “NOT_ARCHIVED” to filter for
                unarchived DNA Sequences.
        :param folder_id: ID of a folder. Restricts results to those in the folder.
        :param modified_at: Datetime, in RFC 3339 format. Supports the > and <
                    operators. Time zone defaults to UTC. Restricts results to those
                    modified in the specified range. e.g. > 2017-04-30.
        :param name: Name of a DNA Sequence. Restricts results to those with the
                    specified name.
        :param project_id: ID of a project. Restricts results to those in the project.
        :param schema_id: ID of a schema. Restricts results to those of the specified
                schema.
        :param registry_id: ID of a registry. Restricts results to those registered in
                this registry.
        :return:
        """
    return super().list(page_size=page_size, next_token=next_token, sort=
        sort, modified_at=modified_at, name=name, folder_id=folder_id,
        project_id=project_id, schema_id=schema_id, archive_reason=
        archive_reason, registry_id=registry_id, **kwargs)


def _xml(tag, xml):
    """(INTERNAL) Get a <tag>value</tag> from XML.
    """
    i = xml.find('<%s>' % (tag,))
    if i > 0:
        i += len(tag) + 2
        j = xml.find('</%s>' % (tag,), i)
        if j > i:
            return xml[i:j].strip()
    return 'no XML tag <%s>' % (tag,)


def exception():
    """Handle an exception that occurred during the transaction commit.

        Returns a sequence of IMessage objects (error messages) to be passed to
        AMQP. Note: The original message will also be acked -- if that's not
        desired, implementers should raise an exception instead.

        """


@classmethod
def rate_limited(cls, val):
    """
        Create an instance of this class set to the ``rate_limited`` tag with
        value ``val``.

        :param str val:
        :rtype: ResendSecondaryEmailResult
        """
    return cls('rate_limited', val)


def compare(first_point, ref_point, compare_point):
    """
    I don't know exaclty what does this formula... anybody can explain ?
    """
    x2, y2 = first_point
    x1, y1 = ref_point
    x3, y3 = compare_point
    m = (y2 - y1 * 1.00001) / (x2 - x1 * 1.00001)
    return y3 - y1 - m * (x3 - x1)


def extractFlags(item, report=1):
    """Extract the flags from an item as a tuple"""
    return (item.negative, item.optional, item.repeating, item.errorOnFail,
        item.lookahead, item.report and report)


def clamp(value, mn=0, mx=255):
    """Clamp the value to the the given minimum and maximum."""
    return max(min(value, mx), mn)


def convert_grid_units(array, grid_arc_seconds, units, kpc_per_arcsec):
    """Convert the grid from its input units (arc-seconds) to the input unit (e.g. retain arc-seconds) or convert to     another set of units (pixels or kilo parsecs).

    Parameters
    -----------
    array : ndarray or hyper.array.scaled_array.ScaledArray
        The 2D array of hyper which is plotted, the shape of which is used for converting the grid to units of pixels.
    grid_arc_seconds : ndarray or hyper.array.grid_stacks.RegularGrid
        The (y,x) coordinates of the grid in arc-seconds, in an array of shape (total_coordinates, 2).
    units : str
        The units of the y / x axis of the plots, in arc-seconds ('arcsec') or kiloparsecs ('kpc').
    kpc_per_arcsec : float
        The conversion factor between arc-seconds and kiloparsecs, required to plot the units in kpc.
    """
    if units is 'pixels':
        return array.grid_arc_seconds_to_grid_pixels(grid_arc_seconds=
            grid_arc_seconds)
    elif units is 'arcsec' or kpc_per_arcsec is None:
        return grid_arc_seconds
    elif units is 'kpc':
        return grid_arc_seconds * kpc_per_arcsec


def hexstr_to_bytes(input_str: str) ->bytes:
    """
    Converts a hex string into bytes, removing the 0x if it's present.
    """
    if input_str.startswith('0x') or input_str.startswith('0X'):
        return bytes.fromhex(input_str[2:])
    return bytes.fromhex(input_str)


def first_true(it, default=None):
    """
    Return the first truthy element from `it`.
    """
    for elem in it:
        if elem:
            return elem
    return default


@classmethod
def __find_mp3_start__(cls, mp3file):
    """places mp3file at the position of the MP3 file's start"""
    from audiotools.id3 import skip_id3v2_comment
    skip_id3v2_comment(mp3file)
    from audiotools.bitstream import BitstreamReader
    reader = BitstreamReader(mp3file, False)
    pos = reader.getpos()
    frame_sync, mpeg_id, layer = reader.parse('11u 2u 2u 1p')
    while not (frame_sync == 2047 and mpeg_id in (0, 2, 3) and layer in (1,
        2, 3)):
        reader.setpos(pos)
        reader.skip(8)
        pos = reader.getpos()
    reader.setpos(pos)


def expand_tweet_urls(tweet):
    """ Replace shortened URLs with long URLs in the twitter status, and add the "RT" flag.
        Should be used before urlize_tweet
    """
    if 'retweeted_status' in tweet:
        text = 'RT @{user}: {text}'.format(user=tweet['retweeted_status'][
            'user']['screen_name'], text=tweet['retweeted_status']['text'])
        urls = tweet['retweeted_status']['entities']['urls']
    else:
        text = tweet['text']
        urls = tweet['entities']['urls']
    for url in urls:
        text = text.replace(url['url'], '%s' % (url[
            'expanded_url'], url['display_url']))
    tweet['html'] = text
    return tweet


@classmethod
def group_id(cls, val):
    """
        Create an instance of this class set to the ``group_id`` tag with value
        ``val``.

        :param str val:
        :rtype: GroupSelector
        """
    return cls('group_id', val)


def invalidate(key=None):
    """Invalidate child with key or all children of this node.
        """


def plus_or_dot(pieces):
    """Return a + if we don't already have one, else return a ."""
    if '+' in pieces.get('closest-tag', ''):
        return '.'
    return '+'


def delete(notification):
    """ Deletes the given notification for the current user
        """


@classmethod
def userAgentsManager(cls):
    """
        Class method to get a reference to the user agents manager.

        @return reference to the user agents manager (UserAgentManager)
        """
    if cls._userAgentsManager is None:
        from .UserAgent.UserAgentManager import UserAgentManager
        cls._userAgentsManager = UserAgentManager()
    return cls._userAgentsManager


def no_dec(num: float) ->str:
    """Format a floating point number with no decimal places."""
    return '{}'.format(round(num))


def prefetch_data_for_score_calculation(reviews_qs):
    """
    Format of displayed score can depend on other models.
    Modify a default queryset of `Review.objects` by pre-fetching data
    so that the function `display_score` won't need any additional database queries.
    """
    return reviews_qs


def trimPath(path):
    """
    Removes the trailing / from the path given
    >>> trimPath('/content/dam/sample/')
    /content/dam/sample
    """
    if path.endswith('/'):
        return path[:-1]
    return path


def printtree():
    """Debugging helper.
        """


def check_user_permission(permissions, user_info):
    """ Returns the first permission the user validates to.

    Looks up every permission in the given list of permissions, and when one
    validates, it returns that perm as a result

    Args:
        permissions: List containing permissions in string format
        user_info: the result from handle_session_data() to check against

    Returns:
        perm: the string permission we first positively validated against
    """
    for permission in permissions:
        try:
            perm = user_info.permissions[permission]
        except KeyError:
            perm = False
        if perm:
            break
    return perm


def printable_command(cmd):
    """Rebuild a command line from system arguments."""
    parts = []
    for part in cmd:
        if ' ' in part:
            has_double_quotes = '"' in part
            has_single_quotes = "'" in part
            if has_double_quotes and not has_single_quotes:
                part = f"'{part}'"
            elif has_single_quotes and has_double_quotes:
                part = part.replace('"', '\\"')
                part = f'"{part}"'
            else:
                part = f'"{part}"'
        parts.append(part)
    return ' '.join(parts)


@staticmethod
def metadata_updated_on(item):
    """Extracts the update time from a FINOS meeting CSV row.

        The timestamp is calculated before and stored into the 'timestamp'
        field extracted from 'published' field.

        :param item: item generated by the backend

        :returns: the timestamp field, UNIX format
        """
    return item['timestamp']


def _filter_args(args):
    """
    filter the arguments

    :param args: arguments
    """
    args.number = int(args.number) if args.number is not None else None
    args.server = str(args.server) if args.server is not None else None
    args.interval = int(args.interval) if args.interval is not None else 30
    args.freeze_period = int(args.freeze_period
        ) if args.freeze_period is not None else 300
    args.lock_time = int(args.lock_time
        ) if args.lock_time is not None else None
    args.debug = True if args.debug is not None and int(args.debug
        ) > 0 else False


def laplaciandeform_bind(modifier: str=''):
    """Bind mesh to system in laplacian deform modifier

    :param modifier: Modifier, Name of the modifier to edit
    :type modifier: str
    """
    pass


@staticmethod
def is_fold_trigger(block):
    """
        Checks if the block is a fold trigger.

        :param block: block to check
        :return: True if the block is a fold trigger (represented as a node in
            the fold panel)
        """
    if block is None:
        return False
    state = block.userState()
    if state == -1:
        state = 0
    return bool(state & 67108864)


def render(**kwargs):
    """Renders template to a unicode string, passing optional
        keyword-arguments."""


@classmethod
def untranslate_store(cls, store, language, fuzzy=False):
    """Remove translations from Translate Toolkit store."""
    super().untranslate_store(store, language, fuzzy)
    plural = language.plural
    store.updateheader(last_translator='Automatically generated',
        plural_forms=plural.plural_form, language_team='none')


def id_maker(type_name, id_number):
    """Generate a consistent ID that is unique within a document,
    assuming `id_number` is unique within the tag type.
    """
    return '%s_%s' % (type_name.upper(), str(id_number))


def trace():
    """Enables and disables request tracing."""

    def fget(self):
        return self._options.get('trace', None)

    def fset(self, value):
        self._options['trace'] = value
    return locals()


def __ne__(A, other):
    """Returns true if both objects are not equal"""
    return not A == other


def dictdel(dct, key):
    """Provides `delattr` semantics for modifiyng dictionaries."""
    del dct[key]


def fail(message=''):
    """Mark the test as failure and stop

    Parameters:
    message (optional, '') : value
    """
    raise AssertionError(message)


@classmethod
def unmount_action(cls, drive: 'Drive', daemon_controller: 'Controller'
    ) ->None:
    """Perform the unmount/remove action."""
    raise NotImplementedError


def full_name(class_type):
    """
    Gets the fully qualified name of a class type.

    From https://stackoverflow.com/questions/2020014/get-fully-qualified-class-name-of-an-object-in-python

    Args:
        class_type (type): the type of the class.

    Returns:
        the fully qualified name of the class type.
    """
    module = class_type.__class__.__module__
    if module is None or module == str.__class__.__module__:
        return class_type.__class__.__name__
    return f'{module}.{class_type.__class__.__name__}'


def reformat_record(record):
    """Repack a record into a cleaner structure for consumption."""
    return {'key': record['dynamodb'].get('Keys', None), 'new': record[
        'dynamodb'].get('NewImage', None), 'old': record['dynamodb'].get(
        'OldImage', None), 'meta': {'created_at': record['dynamodb'][
        'ApproximateCreationDateTime'], 'event': {'id': record['eventID'],
        'type': record['eventName'].lower(), 'version': record[
        'eventVersion']}, 'sequence_number': record['dynamodb'][
        'SequenceNumber']}}


@classmethod
def weekdays_from_value(cls, val, truncate=False):
    """Get list of weekday names that are valid for particular run value.

        args:
          - VALUE (int) 0-127
          - TRUNCATE (bool|default=False) limit names to only first two chars

        returns:
            a list
        """
    if val < 0 or val > 127:
        raise ValueError('Value must be from 0 to 127')
    results = []
    for n in sorted(cls.DAYS.keys(), reverse=True):
        if val & n:
            dow = cls.DAYS[n]
            if truncate:
                results.append(''.join(list(dow)[0:2]))
            else:
                results.append(dow)
    return results


def append_arg(args, key, value):
    """Update a single list-type argument by appending a value."""
    if key in args and args[key]:
        if value:
            args[key] += u',' + value
    else:
        args[key] = value


def false_if_all_false_filter(*value):
    """
    Returns false if all values have a non-'true-ish' value.

    Args:
        *value: list of values

    Returns: 'false' if all values have a non-'true-ish' value
    """
    for v in value:
        if v:
            return True
    return False


def __call__(node):
    """Check wether scope applies on node.

        @param node: ``agx.core.interfaces.INode`` implementation.
        @return: bool
        """


def write_words_txt(orig_lines, highest_numbered_symbol, nonterminals, filename
    ):
    """Writes updated words.txt to 'filename'.  'orig_lines' is the original lines
       in the words.txt file as a list of strings (without the newlines);
       highest_numbered_symbol is the highest numbered symbol in the original
       words.txt; nonterminals is a list of strings like '#nonterm:foo'."""
    with open(filename, 'w', encoding='latin-1') as f:
        for l in orig_lines:
            print(l, file=f)
        cur_symbol = highest_numbered_symbol + 1
        for n in (['#nonterm_begin', '#nonterm_end'] + nonterminals):
            print('{0} {1}'.format(n, cur_symbol), file=f)
            cur_symbol = cur_symbol + 1


def data_view():
    """
    Panel factory for the data tab in the GUI.

    If your model has an adequate show() function this should not be
    necessary.
    """
    from .gui.data_view import DataView
    return DataView


@staticmethod
def json_conversion_message(key, err_msg, line_num, column_num, json_doc):
    """Return a message describing a JSON conversion error at a numbered
        line and column within the JSON document retrieved from the named
        environment variable."""
    json_lines = json_doc.splitlines()
    if len(json_lines) >= line_num:
        error_line = json_lines[line_num - 1]
        truncated_line = error_line[0:column_num - 1]
        detabbed_line = truncated_line.expandtabs()
        char_count = len(detabbed_line)
        pointer_line = char_count * ' ' + '^'
        context_lines = '\n'.join(json_lines[:line_num][-3:]).expandtabs()
        error_location = 'line {:d}:\n{}\n{}'.format(line_num,
            context_lines, pointer_line)
    else:
        error_location = 'line {:d} column {:d}'.format(line_num, column_num)
    return 'In JSON environment variable {}: {} at {}'.format(key, err_msg,
        error_location)


def invalidate_all(oids):
    """
        Remove all cached data for each of the oid integers in *oids*.
        """


def is_fourfront_env(envname):
    """
    Returns True of the given string looks like a Fourfront elasticbeanstalk environment name.
    Otherwise returns False.
    """
    return ('fourfront' in envname and 'cgap' not in envname if envname else
        False)


def xauth(auth):
    """Expand authentication token

    >>> xauth(None)
    >>> xauth(('user', 'pass'))
    ('user', 'pass')
    >>> xauth('user:pass')
    ('user', 'pass')
    >>> xauth('apikey')
    ('apikey', '')

    """
    if auth is None or isinstance(auth, tuple):
        return auth
    else:
        u, _, p = auth.partition(':')
        return u, p


def state(sender, process, data):
    """The process state that Supervisor reports

    - ``process:{name}:state``
    """
    sender.riemann.event(service='process:{name}:state'.format(**data),
        state=data['statename'].lower())


def _attr_rem(attr):
    """Create a 'remove' dictionary for update_workspace_attributes()"""
    return {'op': 'RemoveAttribute', 'attributeName': attr}


def _check_pixel(tup):
    """Check if a pixel is black, supports RGBA"""
    return tup[0] == 0 and tup[1] == 0 and tup[2] == 0


def is_any(iterable, func):
    """
    查找是否存在任何一个为True的结果，否则返回False
    :param iterable:
    :param func:
    :return:
    """
    for x in iterable:
        if func(x):
            return True
    else:
        return False


def write_file(pth, content):
    """Write the content of a file on a local path and
    register associated hash for further modification
    tests.

    Args:
        pth (str): path to the new created file
        content (str): content to write on disk

    Returns:
        None
    """
    with open(pth, 'wb') as f:
        f.write(content.encode('utf-8'))


def t_CDI(t):
    """CDI/2336|CDI/2352"""
    return t


@staticmethod
def read_testcase(testCase):
    """
        Read a testcase file, return the content and indicate if it is binary or not.

        @type testCase: string
        @param testCase: Filename of the file to open

        @rtype: tuple(string, bool)
        @return: Tuple containing the file contents and a boolean indicating if the content is binary

        """
    with open(testCase, 'rb') as f:
        testCaseData = f.read()
    noopBytes = bytearray(range(256))
    textBytes = bytearray([7, 8, 9, 10, 12, 13, 27]) + bytearray(range(32, 256)
        )
    isBinary = bool(testCaseData.translate(noopBytes, textBytes))
    return testCaseData, isBinary


def exit(code='0'):
    """twill command: exit [<code>]

    Exit twill, with the given exit code (defaults to 0, "no error").
    """
    raise SystemExit(int(code))


def demo():
    """demo is used to demonstrate typical examples about this class."""
    demostr = """
import clubear as cb
#clubear.csv is generated by cb.manager.demo()
pm=cb.pump('clubear.csv')
pm.qlist=['height','logsales','price','weight']
pt=cb.plot(pm)
pt.hist('logsales')
pt.size('region')
pt.corr()
pt.mu(y='logsales',x='region')
pt.std(y='logsales',x='gender')
pt.box(y='logsales',x='gender')
pt.gbox(y='logsales',x='price')
"""
    print(demostr)


@staticmethod
def model_version():
    """Return current version of this model, counting up from 0.

        Models may not be backwards-compatible with older versions.
        Version 1 split from version 0 on Aug 29, 2018.
        To use version 0, use --model legacy:seq2seq:0
        (legacy agent code is located in parlai/agents/legacy_agents).
        """
    return 1


def ptr_byref(args, offset=-1):
    """Returns the pointer argument passed in by-reference."""
    return args[offset]._obj


def str_split(strng, sep, pos):
    """https://stackoverflow.com/a/52008134/3521099"""
    strng = strng.split(sep)
    return sep.join(strng[:pos]), sep.join(strng[pos:])


@staticmethod
def positional_to_model(value):
    """Converts a positional argument to a model value"""
    return value


def _allInt(values):
    """true if all values are int"""
    for v in values:
        try:
            if int(v) != v:
                return 0
        except:
            return 0
    return 1


def admin_set_user_settings(UserPoolId=None, Username=None, MFAOptions=None):
    """
    Sets all the user settings for a specified user name. Works on any user.
    Requires developer credentials.
    See also: AWS API Documentation

    :example: response = client.admin_set_user_settings(
        UserPoolId='string',
        Username='string',
        MFAOptions=[
            {
                'DeliveryMedium': 'SMS'|'EMAIL',
                'AttributeName': 'string'
            },
        ]
    )

    :type UserPoolId: string
    :param UserPoolId: [REQUIRED]
            The user pool ID for the user pool where you want to set the user's settings, such as MFA options.

    :type Username: string
    :param Username: [REQUIRED]
            The user name of the user for whom you wish to set user settings.

    :type MFAOptions: list
    :param MFAOptions: [REQUIRED]
            Specifies the options for MFA (e.g., email or phone number).
            (dict) --Specifies the different settings for multi-factor authentication (MFA).
            DeliveryMedium (string) --The delivery medium (email message or SMS message) to send the MFA code.
            AttributeName (string) --The attribute name of the MFA option type.

    :rtype: dict
    :return: {}

    """
    pass


def isp_run(boovsolver, budget, orc, **kwargs):
    """
    Solve multiple sample paths of a problem using the same algorithm.

    Parameters
    ----------
    boovsolver : chnbase.MOSOSolver class
    budget : int
    orc : chnbase.Oracle object
    kwargs : dict

    Returns
    -------
    mydat : dict
        Output of a 'chnbase.MOSOSolver.solve' call
    """
    exists_solvprn = kwargs.get('solvprn', False)
    if exists_solvprn:
        solvprn = kwargs.get('solvprn', None)
        kwargs['sprn'] = solvprn
        del kwargs['solvprn']
    solver = boovsolver(orc, **kwargs)
    mydat = solver.solve(budget)
    return mydat


def register_cp65001():
    """Register cp65001 so that PY2 knowns about it."""
    import codecs
    try:
        codecs.lookup('cp65001')
        return False
    except LookupError:
        codecs.register(lambda name: codecs.lookup('utf-8') if name ==
            'cp65001' else None)
        return True


def add_simple_jar(parser):
    """ Add --simple_jar option to parser. """
    parser.add_argument('-s', '--simple_jar', action='store_true', help=
        'Instead of creating an Uber-JAR for the topology, which contains all of its JVM dependencies, create a simple JAR with just the code for the project.  This is useful when your project is pure Python and has no JVM dependencies.'
        )


def select_set():
    """Set the console selection

    """
    pass


def generate_presigned_url(ClientMethod=None, Params=None, ExpiresIn=None,
    HttpMethod=None):
    """
    Generate a presigned url given a client, its method, and arguments

    :type ClientMethod: string
    :param ClientMethod: The client method to presign for

    :type Params: dict
    :param Params: The parameters normally passed to
            ClientMethod.

    :type ExpiresIn: int
    :param ExpiresIn: The number of seconds the presigned url is valid
            for. By default it expires in an hour (3600 seconds)

    :type HttpMethod: string
    :param HttpMethod: The http method to use on the generated url. By
            default, the http method is whatever is used in the method's model.

    """
    pass


@classmethod
def from_row(cls, row):
    """Initialize from a database row.

        Parameters
        ----------
        row : list
            The database row containing the information.

        Returns
        -------
        :class:`.LunarFeature`
        """
    return cls(*row[1:])


def combinaison(n, k):
    """**combinaison**\\ (*n*\\ , *k*)

    Retourne k parmi n

    :param n: Nombre d'éléments
    :type n: integer
    :param k: éléments pris k à k
    :type k: integer

    >>> from pyromaths.outils import Arithmetique
    >>> Arithmetique.combinaison(6,3)
    20

    :rtype: integer
    """
    if k > n // 2:
        k = n - k
    x = 1
    y = 1
    i = n - k + 1
    while i <= n:
        x = x * i // y
        y += 1
        i += 1
    return x


def handle_wikidata_errors(data, query):
    """
    Raises LookupError if wikidata error found
    """
    entities = data.get('entities')
    if not entities:
        raise LookupError(query)
    elif '-1' in entities:
        raise LookupError(query)
    else:
        item = list(entities.values())[0]
        if 'missing' in item:
            errmsg = 'wikidata item %s has been deleted' % item['id']
            raise LookupError(errmsg)


def update_conf(conf, d):
    """
    Updates conf.py based on the values in dict `d`.
    """
    orig = open(conf).read()
    add = 'globals().update(%s)\n' % str(d)
    imports = d.pop('imports', None)
    with open(conf, 'w') as fout:
        if imports is not None:
            if not isinstance(imports, list):
                imports = [imports]
            for imp in imports:
                fout.write(imp + '\n')
        fout.write(orig)
        fout.write(add)


@classmethod
def get_instance(cls, *args, **kwargs):
    """
        Factory Method for object creation

        Use this instead of directly initializing the class in order to make unit
        testing much easier.
        """
    return cls(*args, **kwargs)


@classmethod
def download_twitter_data(cls, request, ppm_id):
    """
        Downloads the Twitter dataset for the passed user
        :param request: The original Django request object
        :param ppm_id: The PPM ID of the requesting user
        :return: The requested dataset
        """
    response = cls.get(request, f'/sources/api/twitter/{ppm_id}/download',
        raw=True)
    if response:
        return response.content
    return None


def MDL(N, rho, k):
    """Minimum Description Length

    .. math:: MDL(k) = N log \\rho_k + p \\log N

    :validation: results
    """
    from numpy import log
    mdl = N * log(rho) + k * log(N)
    return mdl


def _frange(start, stop=None, step=None):
    """
    _frange range like function for float inputs
    :param start:
    :type start:
    :param stop:
    :type stop:
    :param step:
    :type step:
    :return:
    :rtype:
    """
    if stop is None:
        stop = start
        start = 0.0
    if step is None:
        step = 1.0
    r = start
    while r < stop:
        yield r
        r += step


def label_from_file(filename):
    """Return the label from the file name.

    Suppose you have the label name as a suffix of a
    filename. 'location_vegetation.las' will return 'vegetation'.
    """
    label_suffix_separator = '_'
    seq = filename.split('.')[0].split(label_suffix_separator)
    return seq[-1]


@staticmethod
def bitSizeOf():
    """
        Returns length of Zserio float64 type stored in the bit stream in bits.

        :returns: Length of Zserio float64 type in bits.
        """
    return 64


@classmethod
def hideHighlight(cls):
    """Hides any highlight.
        """
    return cls.build_send_payload('hideHighlight', {}), None


def quote_spaces(arg):
    """Generic function for putting double quotes around any string that
    has white space in it."""
    if ' ' in arg or '\t' in arg:
        return '"%s"' % arg
    else:
        return str(arg)


def render_pep440_pre(pieces):
    """TAG[.post.devDISTANCE] -- No -dirty.

    Exceptions:
    1: no tags. 0.post.devDISTANCE
    """
    if pieces['closest-tag']:
        rendered = pieces['closest-tag']
        if pieces['distance']:
            rendered += '.post.dev%d' % pieces['distance']
    else:
        rendered = '0.post.dev%d' % pieces['distance']
    return rendered


def _isfullcopytraceable(repo, c1, base):
    """ Checks that if base, source and destination are all no-public branches,
    if yes let's use the full copytrace algorithm for increased capabilities
    since it will be fast enough.

    `experimental.copytrace.sourcecommitlimit` can be used to set a limit for
    number of changesets from c1 to base such that if number of changesets are
    more than the limit, full copytracing algorithm won't be used.
    """
    if c1.rev() is None:
        c1 = c1.p1()
    if c1.mutable() and base.mutable():
        sourcecommitlimit = repo.ui.configint(b'experimental',
            b'copytrace.sourcecommitlimit')
        commits = len(repo.revs(b'%d::%d', base.rev(), c1.rev()))
        return commits < sourcecommitlimit
    return False


@classmethod
def are_geoms_connected(cls, geom1, geom2):
    """Return whether ``geom1``'s body is connected to ``geom2``'s body.

		The *connection* is checked as whether geoms bodies are connected
		through a joint or not.

		:param geom1:
		:type geom1: type of :attr:`Geom.inner_object`
		:param geom2:
		:type geom2: type of :attr:`Geom.inner_object`
		:return: True if geoms' bodies are connected; False otherwise
		:rtype: bool

		"""
    raise NotImplementedError()


def _aslist(obj):
    """
    Turn object into a list; lists and tuples are left as-is, None
    becomes [], and everything else turns into a one-element list.
    """
    if obj is None:
        return []
    elif isinstance(obj, (list, tuple)):
        return obj
    else:
        return [obj]


@classmethod
def recognize(cls, location):
    """
        Return a Package object or None given a file location pointing to a
        package archive, manifest or similar.

        Sub-classes should override to implement their own package recognition.
        """
    raise NotImplementedError


@classmethod
def gist(cls, gistid):
    """gistid must be in a username/id form"""
    url = 'https://gist.github.com/{}.js'.format(gistid)
    script = '<script src="{}"></script>'.format(url)
    return script


def leap(year):
    """Is a given year a leap year in the Persian calendar ?"""
    if year > 0:
        y = 474
    else:
        y = 473
    return (year - y % 2820 + 474 + 38) * 682 % 2816 < 682


def dkimport(name):
    """Import and return the item specified by name:

       Usage::

           >>> item = dkimport('dk.core.dkimport.dkimport')
           >>> item.__name__
           'dkimport'

    """
    name = str(name)
    if name.startswith('/'):
        raise ValueError('Cannot import from implicit root.')
    if '.' in name:
        package, item = name.rsplit('.', 1)
        tmp = __import__(package, {}, {}, [item], -1)
        return getattr(tmp, item)
    else:
        return __import__(name, {}, {}, [], -1)


def heuristic_overall_heat_transfer_coefficient(ci, hi, co, ho):
    """
    Return a heuristic estimate of the overall heat transfer coefficient
    [U; in kW/m^2/K]. Assume `U` is 0.5 kW/m^2/K if heat exchange is sensible
    and 1.0 kW/m^2/K otherwise.

    Parameters
    ----------
    ci : Stream
        Cold inlet stream.
    hi : Stream
        Hot inlet stream.
    co : Stream
        Cold outlet stream.
    ho : Stream
        Hot outlet stream.

    Returns
    -------
    U : float
        overall heat transfer coefficient [kW/m^2/K].

    """
    cip, hip, cop, hop = ci.phase, hi.phase, co.phase, ho.phase
    phases = cip + hip + cop + hop
    if 'g' in phases:
        if ('g' in hip and 'l' in hop) and ('l' in cip and 'g' in cop):
            return 1.0
        else:
            return 0.5
    else:
        return 0.5


def age_frequencies():
    """Call to periodically adjust the frequencies of items."""


def get_sstl(l, f, sketch):
    """space-separated token list"""
    token_list = []
    for node in l:
        if token_list:
            token_list.append(' ')
        token = f(node, sketch=sketch)
        token_list.extend(token)
    return token_list


def fmt(obj):
    """fmt(obj)(form) = form % obj

    With this ordering, this is useful for formatting a fixed object
    in many different ways, for example:

    >>> list(map(fmt(10), ["0x%x", "%d"]))
    ['0xa', '10']

    If you want to format lots of objects according to the same spec,
    use format_as.
    """
    return lambda format_string: format_string % obj


def get_hit(HITId=None):
    """
    The GetHIT operation retrieves the details of the specified HIT.
    See also: AWS API Documentation

    :example: response = client.get_hit(
        HITId='string'
    )

    :type HITId: string
    :param HITId: [REQUIRED]
            The ID of the HIT to be retrieved.

    :rtype: dict
    :return: {
        'HIT': {
            'HITId': 'string',
            'HITTypeId': 'string',
            'HITGroupId': 'string',
            'HITLayoutId': 'string',
            'CreationTime': datetime(2015, 1, 1),
            'Title': 'string',
            'Description': 'string',
            'Question': 'string',
            'Keywords': 'string',
            'HITStatus': 'Assignable'|'Unassignable'|'Reviewable'|'Reviewing'|'Disposed',
            'MaxAssignments': 123,
            'Reward': 'string',
            'AutoApprovalDelayInSeconds': 123,
            'Expiration': datetime(2015, 1, 1),
            'AssignmentDurationInSeconds': 123,
            'RequesterAnnotation': 'string',
            'QualificationRequirements': [
                {
                    'QualificationTypeId': 'string',
                    'Comparator': 'LessThan'|'LessThanOrEqualTo'|'GreaterThan'|'GreaterThanOrEqualTo'|'EqualTo'|'NotEqualTo'|'Exists'|'DoesNotExist'|'In'|'NotIn',
                    'IntegerValues': [
                        123,
                    ],
                    'LocaleValues': [
                        {
                            'Country': 'string',
                            'Subdivision': 'string'
                        },
                    ],
                    'RequiredToPreview': True|False
                },
            ],
            'HITReviewStatus': 'NotReviewed'|'MarkedForReview'|'ReviewedAppropriate'|'ReviewedInappropriate',
            'NumberOfAssignmentsPending': 123,
            'NumberOfAssignmentsAvailable': 123,
            'NumberOfAssignmentsCompleted': 123
        }
    }

    """
    pass


def perm_declare_suspicious_file_replicas(issuer, kwargs):
    """
    Checks if an account can declare suspicious file replicas.

    :param issuer: Account identifier which issues the command.
    :param kwargs: List of arguments for the action.
    :returns: True if account is allowed, otherwise False
    """
    return True


def is_parent(t, s):
    """Whether t is s's parent."""
    return t is s.parent


def remove(username, purge=False):
    """
        Remove a user from the workspace, and also unassign from all
        mappings in contained groups (self.groups).

        This does not remove the user from the site, unless all of the
        following conditions are met:

            1. The purge argument is true.
            2. The adaptation context is a top-level project workspace,
            3. The user is not a member of other projects.

            If #1 is true, but either #2 or #3 is False, raises a
            RuntimeError with a message indicating which assertion
            caused a failure.

        Raises ValueError if username specified is not a project member.

        Removal of member from contained workspaces is not in the scope
        of this method, and must be managed by callers.
        """


def UnitToValue(unit):
    """Return the value of an unit."""
    if not unit or unit.upper() in frozenset(['ECU', 'GCEU', 'HRZ']):
        return 1
    unit = unit[0].upper()
    if unit == 'K':
        return 1024
    if unit == 'M':
        return 1024 * 1024
    if unit == 'G':
        return 1024 * 1024 * 1024
    raise Exception("Not valid unit: '%s'" % unit)


def pretty_docs(wrapped, extradocs=None, name=None):
    """
    Modify wrapped, so that it 'looks' like what it's wrapping.

    This is primarily useful for introspection reasons- doc generators, direct
    user interaction with an object in the interpretter, etc.

    :param wrapped: functor to modify
    :param extradocs: ``__doc__`` override for wrapped; else it pulls from
        wrapped's target functor
    :param name: ``__name__`` override for wrapped; else it pulls from
        wrapped's target functor for the name.
    """
    wrapped.__module__ = wrapped.func.__module__
    doc = wrapped.func.__doc__
    if extradocs is None:
        wrapped.__doc__ = doc
    else:
        wrapped.__doc__ = extradocs
    if name:
        wrapped.__name__ = name
    return wrapped


def render(animation: bool=False, write_still: bool=False, use_viewport:
    bool=False, layer: str='', scene: str=''):
    """Render active scene

    :param animation: Animation, Render files from the animation range of this scene
    :type animation: bool
    :param write_still: Write Image, Save rendered the image to the output path (used only when animation is disabled)
    :type write_still: bool
    :param use_viewport: Use 3D Viewport, When inside a 3D viewport, use layers and camera of the viewport
    :type use_viewport: bool
    :param layer: Render Layer, Single render layer to re-render (used only when animation is disabled)
    :type layer: str
    :param scene: Scene, Scene to render, current scene if not specified
    :type scene: str
    """
    pass


def is_html(response):
    """ Check if Flask response if of HTML type.

    Parameters
    ----------
        response: Flask response

    Returns
    -------
        True if valid False if not.
    """
    content_type = getattr(response, 'content_type', '')
    return 'text/html' in content_type.lower()


@classmethod
def get_actions_hotkeys(cls):
    """
        Return or yield a list of hotkeys to be linked to named actions.

        [{'key': key, 'ctrl': Bool, 'shift': Bool, 'ba': action_name}]

        """


@classmethod
def getxy(cls):
    """
        Get the x and y position of the cursor.

        :return: (x, y)
        """
    y, x = cls.WINDOW.getyx()
    if cls.BORDERED:
        x -= 1
        y -= 1
    if cls.MENU:
        y -= 1
    return x, y


def get_n_header(f, header_char='"'):
    """Get the nummber of header rows in a Little Leonardo data file

    Args
    ----
    f : file stream
        File handle for the file from which header rows will be read
    header_char: str
        Character array at beginning of each header line

    Returns
    -------
    n_header: int
        Number of header rows in Little Leonardo data file
    """
    n_header = 0
    reading_headers = True
    while reading_headers:
        line = f.readline()
        if line.startswith(header_char):
            n_header += 1
        else:
            reading_headers = False
    return n_header


def swap_rows(arr, frm, to):
    """swap rows of a 2D np.array"""
    if arr.ndim > 1:
        arr[([frm, to]), :] = arr[([to, frm]), :]
    else:
        arr[frm], arr[to] = arr[to], arr[frm]


def image_statistics(image, calibration, result=None):
    """
    Adds some numeric image parameters (i.e. size) to the results.

    :param image:
    :param calibration:
    :param result:
    :return:

    >>> sorted(image_statistics(np.array([[0, 0, 0],
    ...                                   [0, 0, 0],
    ...                                   [0, 0, 0]]), calibration=15.0).items())
    [('area', 2025.0), ('area_pixel', 9), ('input_height', 45.0), ('input_height_pixel', 3), ('input_width', 45.0), ('input_width_pixel', 3)]
    """
    return {'input_width': image.shape[1] * calibration, 'input_height':
        image.shape[0] * calibration, 'input_width_pixel': image.shape[1],
        'input_height_pixel': image.shape[0], 'area': image.shape[1] *
        calibration * image.shape[0] * calibration, 'area_pixel': image.
        shape[1] * image.shape[0]}


def pystr(s):
    """
    Convert a string of characters to Python str object
    """
    if isinstance(s, bytes):
        return s.decode('utf-8')
    else:
        return s


def field_in_fields(entity, attribute, value):
    """
    Return ``True`` if the entity has the named field.
    """
    return value in entity.fields


@classmethod
def factory(cls, global_config, **local_config):
    """Used for paste app factories in paste.deploy config files.
        Any local configuration (that is, values under the [app:APPNAME]
        section of the paste config) will be passed into the `__init__` method
        as kwargs.
        A hypothetical configuration would look like:
            [app:wadl]
            latest_version = 1.3
            paste.app_factory = nova.api.fancy_api:Wadl.factory
        which would result in a call to the `Wadl` class as
            import nova.api.fancy_api
            fancy_api.Wadl(latest_version='1.3')
        You could of course re-implement the `factory` method in subclasses,
        but using the kwarg passing it shouldn't be necessary.
        """
    return cls(**local_config)


def start():
    """Start for read-write requests placeholder

    Typically performed at the start of a request cycle, say for POST or PUT
    requests.
    """
    pass


def _yes_no(question):
    """
    Continuously asks a yes/no question until user input is in [yYnN].
    Returns True or False respectively.
    """
    yesno_map = {'y': True, 'n': False}
    choice = ''
    while choice not in ['y', 'n']:
        choice = input(question).lower()
    return yesno_map[choice]


def first_neighbours_last(batches, currentBatchIdx, nb_left, nb_right):
    """Build a sublist from a large batch list.

    This is used to display batch links for a large table.

    arguments:
     * batches: a large sequence (may be a batches as well)
     * currentBatchIdx: index of the current batch or item
     * nb_left: number of neighbours before the current batch
     * nb_right: number of neighbours after the current batch

    The returned list gives:
     * the first batch
     * a None separator if necessary
     * left neighbours of the current batch
     * the current batch
     * right neighbours of the current batch
     * a None separator if necessary
     * the last batch

    Example:

      >>> from z3c.batching.batch import first_neighbours_last as f_n_l
      >>> batches = range(100) # it works with real batches as well

    We try to get subsets at different levels:

      >>> for i in range(0,6):
      ...    f_n_l(batches, i, 2, 2)
      [0, 1, 2, None, 99]
      [0, 1, 2, 3, None, 99]
      [0, 1, 2, 3, 4, None, 99]
      [0, 1, 2, 3, 4, 5, None, 99]
      [0, None, 2, 3, 4, 5, 6, None, 99]
      [0, None, 3, 4, 5, 6, 7, None, 99]

      >>> for i in range(93, 99):
      ...    f_n_l(batches, i, 2, 2)
      [0, None, 91, 92, 93, 94, 95, None, 99]
      [0, None, 92, 93, 94, 95, 96, None, 99]
      [0, None, 93, 94, 95, 96, 97, None, 99]
      [0, None, 94, 95, 96, 97, 98, 99]
      [0, None, 95, 96, 97, 98, 99]
      [0, None, 96, 97, 98, 99]

    Try with no previous and no next batch:

      >>> f_n_l(batches, 0, 0, 0)
      [0, None, 99]
      >>> f_n_l(batches, 1, 0, 0)
      [0, 1, None, 99]
      >>> f_n_l(batches, 2, 0, 0)
      [0, None, 2, None, 99]

    Try with only 1 previous and 1 next batch:

      >>> f_n_l(batches, 0, 1, 1)
      [0, 1, None, 99]
      >>> f_n_l(batches, 1, 1, 1)
      [0, 1, 2, None, 99]
      >>> f_n_l(batches, 2, 1, 1)
      [0, 1, 2, 3, None, 99]
      >>> f_n_l(batches, 3, 1, 1)
      [0, None, 2, 3, 4, None, 99]

    Try with incoherent values:

      >>> f_n_l(batches, 0, -4, -10)
      Traceback (most recent call last):
      ...
      AssertionError
      >>> f_n_l(batches, 2000, 3, 3)
      Traceback (most recent call last):
      ...
      AssertionError
    """
    sublist = []
    firstIdx = 0
    lastIdx = len(batches) - 1
    assert currentBatchIdx >= 0 and currentBatchIdx <= lastIdx
    assert nb_left >= 0 and nb_right >= 0
    prevIdx = currentBatchIdx - nb_left
    nextIdx = currentBatchIdx + 1
    firstBatch = batches[0]
    lastBatch = batches[lastIdx]
    if firstIdx < currentBatchIdx:
        sublist.append(firstBatch)
    if firstIdx + 1 < prevIdx:
        sublist.append(None)
    for i in range(prevIdx, prevIdx + nb_left):
        if firstIdx < i:
            sublist.append(batches[i])
    sublist.append(batches[currentBatchIdx])
    for i in range(nextIdx, nextIdx + nb_right):
        if i < lastIdx:
            sublist.append(batches[i])
    if nextIdx + nb_right < lastIdx:
        sublist.append(None)
    if currentBatchIdx < lastIdx:
        sublist.append(lastBatch)
    return sublist


@classmethod
def get_destinations(cls, domain, source):
    """Retrieve forward information."""
    forwards = cls.list(domain, {'items_per_page': 500})
    for fwd in forwards:
        if fwd['source'] == source:
            return fwd['destinations']
    return []


def encodeVarint(fint):
    """ backward-encoded Mobipocket variable-width integer. """
    vint = 0
    bitpos = 0
    while bitpos < 32:
        vint |= (fint & 127) << bitpos
        if fint < 127:
            vint |= 128 << bitpos
            break
        fint >>= 7
        bitpos += 8
    return vint


def render_pep440_old(pieces):
    """TAG[.postDISTANCE[.dev0]] .

    The ".dev0" means dirty.

    Eexceptions:
    1: no tags. 0.postDISTANCE[.dev0]
    """
    if pieces['closest-tag']:
        rendered = pieces['closest-tag']
        if pieces['distance'] or pieces['dirty']:
            rendered += '.post%d' % pieces['distance']
            if pieces['dirty']:
                rendered += '.dev0'
    else:
        rendered = '0.post%d' % pieces['distance']
        if pieces['dirty']:
            rendered += '.dev0'
    return rendered


def uninstall(context):
    """Uninstall script"""


@staticmethod
def calc_range(network, broadcast):
    """
        Calculate the range of addresses in the subnet.
        :param network: network address
        :param broadcast: broadcast address
        :return: range of addresses in subnet
        """
    return network + ' - ' + broadcast


def add_true_negatives(err, cnt_gt):
    """Update errors statistics of a specific method with missing detections"""
    matched = len(err['all'])
    missed = cnt_gt - matched
    zeros = [0] * missed
    err['<0.5m'].extend(zeros)
    err['<1m'].extend(zeros)
    err['<2m'].extend(zeros)
    err['matched'] = 100 * matched / cnt_gt


def parse_date(daystr):
    """ parse a timestring into a timestamp. """
    sec = 0
    min = 0
    hour = 0
    day = 0
    w = 0
    diff = 0
    prev = ''
    val = 0
    total = 0
    for c in daystr:
        if c not in ['s', 'm', 'h', 'd', 'w', 'y']:
            val += c
            continue
        if c == 'y':
            total += val * 3600 * 24 * 365
        if c == 'w':
            total += val * 3600 * 24 * 7
        elif c == 'd':
            total += val * 3600 * 24
        elif c == 'h':
            total += val * 3600
        elif c == 'm':
            total += val * 60
        else:
            total += val
        val = 0
    return total


def lambd_H3PO4_Na_HFM89(T, P):
    """n-c: phosphoric-acid sodium [HFM89]."""
    lambd = 0.075
    valid = T == 298.15
    return lambd, valid


@staticmethod
def _return_list_if_str(event):
    """
        If variable is a string returns a list containing variable.
        Else returns variable itself.
        """
    if isinstance(event, str):
        return [event]
    else:
        return event


def infer_default_values(parameters, code):
    """Very brittle attempt at inferring parameters default values for matlab functions.
    At the moment we assume they are set by a "if nargin < blah" idiom.

    Parameters
    ----------
    parameters: string list
        A list of the parameters of the function,

    code: string
        The code of the function.

    Returns
    -------
    A string list with the default value inferred for each parameter (empty strings for unknown).
    """
    default_values = []
    for i, param in enumerate(parameters):
        val = code.partition('if nargin < %d' % (i + 2))[2].partition(
            '%s = ' % param)[2].partition(';')[0]
        default_values.append(val.strip())
    return default_values


def _format_value(stream, type, value):
    """
    Color format a value as {type}( {value} ).

    :param AnsiStream stream: ANSI stream
    :param str type: type string
    :param any value: value to format
    """
    tmpl = '{blue}{type}({reset} {value} {blue}){reset}'
    if stream:
        return stream.ansi_format(tmpl, type=type, value=value)
    return '{type}( {value} )'.format(type=type, value=value)


def jacobi(n, m):
    """Compute the Jacobi symbol.

    The special case of this when m is prime is the Legendre symbol,
    which is 0 if n is congruent to 0 mod m; 1 if n is congruent to a
    non-zero square number mod m; -1 if n is not congruent to any
    square mod m.

    """
    assert m & 1
    acc = 1
    while True:
        n %= m
        if n == 0:
            return 0
        while not n & 1:
            n >>= 1
            if m & 7 not in {1, 7}:
                acc *= -1
        if n == 1:
            return acc
        if n & 3 == 3 and m & 3 == 3:
            acc *= -1
        n, m = m, n


def create_elasticsearch_domain(DomainName=None, ElasticsearchVersion=None,
    ElasticsearchClusterConfig=None, EBSOptions=None, AccessPolicies=None,
    SnapshotOptions=None, AdvancedOptions=None):
    """
    Creates a new Elasticsearch domain. For more information, see Creating Elasticsearch Domains in the Amazon Elasticsearch Service Developer Guide .
    See also: AWS API Documentation

    :example: response = client.create_elasticsearch_domain(
        DomainName='string',
        ElasticsearchVersion='string',
        ElasticsearchClusterConfig={
            'InstanceType': 'm3.medium.elasticsearch'|'m3.large.elasticsearch'|'m3.xlarge.elasticsearch'|'m3.2xlarge.elasticsearch'|'m4.large.elasticsearch'|'m4.xlarge.elasticsearch'|'m4.2xlarge.elasticsearch'|'m4.4xlarge.elasticsearch'|'m4.10xlarge.elasticsearch'|'t2.micro.elasticsearch'|'t2.small.elasticsearch'|'t2.medium.elasticsearch'|'r3.large.elasticsearch'|'r3.xlarge.elasticsearch'|'r3.2xlarge.elasticsearch'|'r3.4xlarge.elasticsearch'|'r3.8xlarge.elasticsearch'|'i2.xlarge.elasticsearch'|'i2.2xlarge.elasticsearch'|'d2.xlarge.elasticsearch'|'d2.2xlarge.elasticsearch'|'d2.4xlarge.elasticsearch'|'d2.8xlarge.elasticsearch'|'c4.large.elasticsearch'|'c4.xlarge.elasticsearch'|'c4.2xlarge.elasticsearch'|'c4.4xlarge.elasticsearch'|'c4.8xlarge.elasticsearch'|'r4.large.elasticsearch'|'r4.xlarge.elasticsearch'|'r4.2xlarge.elasticsearch'|'r4.4xlarge.elasticsearch'|'r4.8xlarge.elasticsearch'|'r4.16xlarge.elasticsearch',
            'InstanceCount': 123,
            'DedicatedMasterEnabled': True|False,
            'ZoneAwarenessEnabled': True|False,
            'DedicatedMasterType': 'm3.medium.elasticsearch'|'m3.large.elasticsearch'|'m3.xlarge.elasticsearch'|'m3.2xlarge.elasticsearch'|'m4.large.elasticsearch'|'m4.xlarge.elasticsearch'|'m4.2xlarge.elasticsearch'|'m4.4xlarge.elasticsearch'|'m4.10xlarge.elasticsearch'|'t2.micro.elasticsearch'|'t2.small.elasticsearch'|'t2.medium.elasticsearch'|'r3.large.elasticsearch'|'r3.xlarge.elasticsearch'|'r3.2xlarge.elasticsearch'|'r3.4xlarge.elasticsearch'|'r3.8xlarge.elasticsearch'|'i2.xlarge.elasticsearch'|'i2.2xlarge.elasticsearch'|'d2.xlarge.elasticsearch'|'d2.2xlarge.elasticsearch'|'d2.4xlarge.elasticsearch'|'d2.8xlarge.elasticsearch'|'c4.large.elasticsearch'|'c4.xlarge.elasticsearch'|'c4.2xlarge.elasticsearch'|'c4.4xlarge.elasticsearch'|'c4.8xlarge.elasticsearch'|'r4.large.elasticsearch'|'r4.xlarge.elasticsearch'|'r4.2xlarge.elasticsearch'|'r4.4xlarge.elasticsearch'|'r4.8xlarge.elasticsearch'|'r4.16xlarge.elasticsearch',
            'DedicatedMasterCount': 123
        },
        EBSOptions={
            'EBSEnabled': True|False,
            'VolumeType': 'standard'|'gp2'|'io1',
            'VolumeSize': 123,
            'Iops': 123
        },
        AccessPolicies='string',
        SnapshotOptions={
            'AutomatedSnapshotStartHour': 123
        },
        AdvancedOptions={
            'string': 'string'
        }
    )

    :type DomainName: string
    :param DomainName: [REQUIRED]
            The name of the Elasticsearch domain that you are creating. Domain names are unique across the domains owned by an account within an AWS region. Domain names must start with a letter or number and can contain the following characters: a-z (lowercase), 0-9, and - (hyphen).

    :type ElasticsearchVersion: string
    :param ElasticsearchVersion: String of format X.Y to specify version for the Elasticsearch domain eg. '1.5' or '2.3'. For more information, see Creating Elasticsearch Domains in the Amazon Elasticsearch Service Developer Guide .

    :type ElasticsearchClusterConfig: dict
    :param ElasticsearchClusterConfig: Configuration options for an Elasticsearch domain. Specifies the instance type and number of instances in the domain cluster.
            InstanceType (string) --The instance type for an Elasticsearch cluster.
            InstanceCount (integer) --The number of instances in the specified domain cluster.
            DedicatedMasterEnabled (boolean) --A boolean value to indicate whether a dedicated master node is enabled. See About Dedicated Master Nodes for more information.
            ZoneAwarenessEnabled (boolean) --A boolean value to indicate whether zone awareness is enabled. See About Zone Awareness for more information.
            DedicatedMasterType (string) --The instance type for a dedicated master node.
            DedicatedMasterCount (integer) --Total number of dedicated master nodes, active and on standby, for the cluster.

    :type EBSOptions: dict
    :param EBSOptions: Options to enable, disable and specify the type and size of EBS storage volumes.
            EBSEnabled (boolean) --Specifies whether EBS-based storage is enabled.
            VolumeType (string) --Specifies the volume type for EBS-based storage.
            VolumeSize (integer) --Integer to specify the size of an EBS volume.
            Iops (integer) --Specifies the IOPD for a Provisioned IOPS EBS volume (SSD).

    :type AccessPolicies: string
    :param AccessPolicies: IAM access policy as a JSON-formatted string.

    :type SnapshotOptions: dict
    :param SnapshotOptions: Option to set time, in UTC format, of the daily automated snapshot. Default value is 0 hours.
            AutomatedSnapshotStartHour (integer) --Specifies the time, in UTC format, when the service takes a daily automated snapshot of the specified Elasticsearch domain. Default value is 0 hours.

    :type AdvancedOptions: dict
    :param AdvancedOptions: Option to allow references to indices in an HTTP request body. Must be false when configuring access to individual sub-resources. By default, the value is true . See Configuration Advanced Options for more information.
            (string) --
            (string) --

    :rtype: dict
    :return: {
        'DomainStatus': {
            'DomainId': 'string',
            'DomainName': 'string',
            'ARN': 'string',
            'Created': True|False,
            'Deleted': True|False,
            'Endpoint': 'string',
            'Processing': True|False,
            'ElasticsearchVersion': 'string',
            'ElasticsearchClusterConfig': {
                'InstanceType': 'm3.medium.elasticsearch'|'m3.large.elasticsearch'|'m3.xlarge.elasticsearch'|'m3.2xlarge.elasticsearch'|'m4.large.elasticsearch'|'m4.xlarge.elasticsearch'|'m4.2xlarge.elasticsearch'|'m4.4xlarge.elasticsearch'|'m4.10xlarge.elasticsearch'|'t2.micro.elasticsearch'|'t2.small.elasticsearch'|'t2.medium.elasticsearch'|'r3.large.elasticsearch'|'r3.xlarge.elasticsearch'|'r3.2xlarge.elasticsearch'|'r3.4xlarge.elasticsearch'|'r3.8xlarge.elasticsearch'|'i2.xlarge.elasticsearch'|'i2.2xlarge.elasticsearch'|'d2.xlarge.elasticsearch'|'d2.2xlarge.elasticsearch'|'d2.4xlarge.elasticsearch'|'d2.8xlarge.elasticsearch'|'c4.large.elasticsearch'|'c4.xlarge.elasticsearch'|'c4.2xlarge.elasticsearch'|'c4.4xlarge.elasticsearch'|'c4.8xlarge.elasticsearch'|'r4.large.elasticsearch'|'r4.xlarge.elasticsearch'|'r4.2xlarge.elasticsearch'|'r4.4xlarge.elasticsearch'|'r4.8xlarge.elasticsearch'|'r4.16xlarge.elasticsearch',
                'InstanceCount': 123,
                'DedicatedMasterEnabled': True|False,
                'ZoneAwarenessEnabled': True|False,
                'DedicatedMasterType': 'm3.medium.elasticsearch'|'m3.large.elasticsearch'|'m3.xlarge.elasticsearch'|'m3.2xlarge.elasticsearch'|'m4.large.elasticsearch'|'m4.xlarge.elasticsearch'|'m4.2xlarge.elasticsearch'|'m4.4xlarge.elasticsearch'|'m4.10xlarge.elasticsearch'|'t2.micro.elasticsearch'|'t2.small.elasticsearch'|'t2.medium.elasticsearch'|'r3.large.elasticsearch'|'r3.xlarge.elasticsearch'|'r3.2xlarge.elasticsearch'|'r3.4xlarge.elasticsearch'|'r3.8xlarge.elasticsearch'|'i2.xlarge.elasticsearch'|'i2.2xlarge.elasticsearch'|'d2.xlarge.elasticsearch'|'d2.2xlarge.elasticsearch'|'d2.4xlarge.elasticsearch'|'d2.8xlarge.elasticsearch'|'c4.large.elasticsearch'|'c4.xlarge.elasticsearch'|'c4.2xlarge.elasticsearch'|'c4.4xlarge.elasticsearch'|'c4.8xlarge.elasticsearch'|'r4.large.elasticsearch'|'r4.xlarge.elasticsearch'|'r4.2xlarge.elasticsearch'|'r4.4xlarge.elasticsearch'|'r4.8xlarge.elasticsearch'|'r4.16xlarge.elasticsearch',
                'DedicatedMasterCount': 123
            },
            'EBSOptions': {
                'EBSEnabled': True|False,
                'VolumeType': 'standard'|'gp2'|'io1',
                'VolumeSize': 123,
                'Iops': 123
            },
            'AccessPolicies': 'string',
            'SnapshotOptions': {
                'AutomatedSnapshotStartHour': 123
            },
            'AdvancedOptions': {
                'string': 'string'
            }
        }
    }

    :returns:
    (string) --
    (string) --

    """
    pass


@staticmethod
def set_list(l, i, v):
    """
        Function sets i-th value in list to v. If i does not exist in l
        it is initialized else value is modified
        """
    try:
        l[i] = v
    except IndexError:
        for _ in range(i - len(l)):
            l.append(None)
        l.append(v)
    return l


def _add_include_paths_to_flags(args):
    """ Add all the include paths to all three compile flags """
    for path in args.include:
        if path is not None:
            if path not in args.CPPFLAGS:
                args.CPPFLAGS += ' -I ' + path
            if path not in args.CFLAGS:
                args.CFLAGS += ' -I ' + path
            if path not in args.CXXFLAGS:
                args.CXXFLAGS += ' -I ' + path
    if args.verbose >= 4 and len(args.include) > 0:
        print('Extra include paths have been appended to the *FLAG variables:')
        print('\tCPPFLAGS=' + args.CPPFLAGS)
        print('\tCFLAGS=' + args.CFLAGS)
        print('\tCXXFLAGS=' + args.CXXFLAGS)


def clean_node_tree(node_tree):
    """Clear all nodes in a shader node tree except the output.

    Returns the output node
    """
    nodes = node_tree.nodes
    for node in list(nodes):
        if not node.type == 'OUTPUT_MATERIAL':
            nodes.remove(node)
    return node_tree.nodes[0]


def suggest_output_filename(meta_data):
    """Generate a recommended filename if `title`, `dataset` and `version` exist in `meta_data`,
    otherwise suggest `abc.sql`"""
    for item in meta_data:
        if 'name' in item and 'value' in item:
            if item['name'].lower() == 'title':
                title = item['value']
            if item['name'].lower() == 'dataset':
                dataset = item['value']
            if item['name'].lower() == 'version':
                version = str(item['value'])
    try:
        return '{title} - {dataset} Dataset - v{version}.sql'.format(title=
            title, dataset=dataset, version=version)
    except UnboundLocalError:
        return 'abc.sql'


def check_boundary_lines_similar(l_1, l_2):
    """Compare two lists to see if their elements are roughly the same.
    @param l_1: (list) of strings.
    @param l_2: (list) of strings.
    @return: (int) 1/0.
    """
    num_matches = 0
    if type(l_1) != list or type(l_2) != list or len(l_1) != len(l_2):
        return 0
    num_elements = len(l_1)
    for i in range(0, num_elements):
        if l_1[i].isdigit() and l_2[i].isdigit():
            num_matches += 1
        else:
            l1_str = l_1[i].lower()
            l2_str = l_2[i].lower()
            if l1_str[0] == l2_str[0] and l1_str[len(l1_str) - 1] == l2_str[
                len(l2_str) - 1]:
                num_matches = num_matches + 1
    if len(l_1) == 0 or float(num_matches) / float(len(l_1)) < 0.9:
        return 0
    else:
        return 1


def p_dynamic_class_name_variable_properties(p):
    """dynamic_class_name_variable_properties : dynamic_class_name_variable_properties dynamic_class_name_variable_property
                                              | empty"""
    if len(p) == 3:
        p[0] = p[1] + [p[2]]
    else:
        p[0] = []


def _applySpecial_MeshOpts_vertexData(args, overlayList, displayCtx, target):
    """Applies the :attr:`.MeshOpts.vertexData` option. """
    import fsleyes.actions.loadvertexdata as loadvertexdata
    vertexData = list(args.vertexData)
    last = len(args.vertexData) - 1
    for i, vd in enumerate(vertexData):
        vertexData[i] = loadvertexdata.loadVertexData(target.overlay,
            displayCtx, vd, select=i == last)
    target.vertexData = vertexData[0]


def read_file(path):
    """Read contents of file at given path as bytes."""
    with open(path, 'rb') as f:
        return f.read()


@classmethod
def list(cls, domain, options):
    """List mailboxes for a given domain name."""
    return cls.call('domain.mailbox.list', domain, options)


def _lrp_meanPcrEff(tarGroup, vecTarget, pcrEff, vecSkipSample,
    vecNoPlateau, vecShortLogLin):
    """A function which calculates the mean efficiency of the selected target group excluding bad ones.

    Args:
        tarGroup: The target number
        vecTarget: The vector with the targets numbers
        pcrEff: The array with the PCR efficiencies
        vecSkipSample: Skip the sample
        vecNoPlateau: True if there is no plateau
        vecShortLogLin: True indicates a short log lin phase

    Returns:
        An array with [meanPcrEff, pcrEffVar].
    """
    cnt = 0
    sumEff = 0.0
    sumEff2 = 0.0
    for j in range(0, len(pcrEff)):
        if tarGroup is None or tarGroup == vecTarget[j]:
            if not (vecSkipSample[j] or vecNoPlateau[j] or vecShortLogLin[j]
                ) and pcrEff[j] > 1.0:
                cnt += 1
                sumEff += pcrEff[j]
                sumEff2 += pcrEff[j] * pcrEff[j]
    if cnt > 1:
        meanPcrEff = sumEff / cnt
        pcrEffVar = (sumEff2 - sumEff * sumEff / cnt) / (cnt - 1)
    else:
        meanPcrEff = 1.0
        pcrEffVar = 100
    return [meanPcrEff, pcrEffVar]


@classmethod
def get_for_site(cls, site):
    """Return the 'main menu' instance for the provided site"""
    instance, created = cls.objects.get_or_create(site=site)
    return instance


def agency_api_authentication_default():
    """Default value for the ``agency_api_authentication`` field.

    Other keys are specific to each type:
    - token: "header" and "token"
    - oauth2: "client_id" and "client_secret"
    """
    return {'type': 'none'}


def recalc_orig(dic, data, fn, axis=-1):
    """
    Recalculate the origin for given axis
    """
    s = float(data.shape[axis])
    if dic[fn + 'QUADFLAG'] == 0 and axis != -1:
        s = int(s / 2.0)
    if dic['FD2DPHASE'] == 1 and fn != 'FDF2' and dic[fn + 'FTFLAG'] != 1:
        s = int(s / 2.0)
    sw = dic[fn + 'SW']
    car = dic[fn + 'CAR']
    obs = dic[fn + 'OBS']
    s2 = float(dic[fn + 'CENTER'])
    dic[fn + 'ORIG'] = car * obs - sw * ((s - s2) / s)
    return dic


@staticmethod
def extension():
    """Return most common file extension for format."""
    return 'rc'


def completions_sorting_key(word):
    """key for sorting completions

    This does several things:

    - Demote any completions starting with underscores to the end
    - Insert any %magic and %%cellmagic completions in the alphabetical order
      by their name
    """
    prio1, prio2 = 0, 0
    if word.startswith('__'):
        prio1 = 2
    elif word.startswith('_'):
        prio1 = 1
    if word.endswith('='):
        prio1 = -1
    if word.startswith('%%'):
        if not '%' in word[2:]:
            word = word[2:]
            prio2 = 2
    elif word.startswith('%'):
        if not '%' in word[1:]:
            word = word[1:]
            prio2 = 1
    return prio1, word, prio2


@staticmethod
def _get_cov_thresh_dict(cov_thresh, protected_attribute_names):
    """Return dict with covariance thresh for each attribute and error type

        The dict has the form:

            {"sensitive_attribute_name_1":{ 0:{0:cov_thresh, 1:cov_thresh},
                                            1:{0:cov_thresh, 1:cov_thresh},
                                            2:{0:cov_thresh, 1:cov_thresh}},
            "sensitive_attribute_name_2":{  0:{0:cov_thresh, 1:cov_thresh},
                                            1:{0:cov_thresh, 1:cov_thresh},
                                            2:{0:cov_thresh, 1:cov_thresh}},
                ...
            }

        Args:
            cov_thresh (float): covariance threshold (same for each attribute)
            protected_attribute_names (list): list of protected attributes

        Returns:
            sensitive_attrs_to_cov_thresh (dict):
        """
    sensitive_attrs_to_cov_thresh = {}
    for sens_attr_name in protected_attribute_names:
        sensitive_attrs_to_cov_thresh[sens_attr_name] = {(0): {(0):
            cov_thresh, (1): cov_thresh}, (1): {(0): cov_thresh, (1):
            cov_thresh}, (2): {(0): cov_thresh, (1): cov_thresh}}
    return sensitive_attrs_to_cov_thresh


def vector_multiply(a, b):
    """ multiply two vectors, vectorized """
    a1, a2 = a
    b1, b2 = b
    return a1 * b1 + a2 * b2


def psi_K_Mg_Cl_HMW84(T, P):
    """c-c'-a: potassium magnesium chloride [HMW84]."""
    psi = -0.022
    valid = T == 298.15
    return psi, valid


def __new__(cls, name='Default', defaults=None):
    """
        Class constructor.
        :param name: instance name id.
        :param defaults: dafault values dict or None.
        :return: an instance of the config object.
        """
    if name not in cls.__registry__:
        cls.__registry__[name] = dict.__new__(cls)
    return cls.__registry__[name]


@classmethod
def from_content(cls, version, type, format_file=None):
    """
        Write a format file from I{type} and I{format} at
        I{format_file}

        @param version: the source package format version
        @param type: the format type
        @param format_file: the format file to create with
            the above parameters
        """
    format_file = format_file or cls.format_file
    with open(cls.format_file, 'w') as f:
        f.write('%s (%s)' % (version, type))
    return cls.parse_file(cls.format_file)


def SetupRuntimeAcls(acl, context):
    """
    Can be used during object initialisation to process acls.
    Acls can have a additional callback parameter called with the context
    to find out whetther to apply the single acl or not. The callback should return
    true or false. e.g. ::

        (Allow, "group:reader", "read", lambda context: context.meta.pool_state),

    or ::

        def check(context):
            return context.meta.pool_state

        (Allow, "group:reader", "read", check),

    :param acl:
    :param context:
    :return: tuple of acls to be stored as __acl__
    """
    processed = []
    for a in acl:
        if len(a) == 4:
            if a[3](*(context,)):
                processed.append(tuple(list(a[:3])))
            continue
        processed.append(tuple(a))
    return tuple(processed)


def warn(msg, category=UserWarning, stacklevel=2):
    """Generate a a warning with stacktrace.

    Parameters
    ----------
    msg : str
        The message of the warning.

    category : class
        The class of the warning to produce.

    stacklevel : int, optional
        How many steps above this function to "jump" in the stacktrace for
        the displayed file and line number of the error message.
        Usually 2.

    """
    import warnings
    warnings.warn(msg, category=category, stacklevel=stacklevel)


def floor_log2(x):
    """ floor of log2 of abs(`x`)

    Embarrassingly, from https://en.wikipedia.org/wiki/Binary_logarithm

    Parameters
    ----------
    x : int

    Returns
    -------
    L : None or int
        floor of base 2 log of `x`.  None if `x` == 0.

    Examples
    --------
    >>> floor_log2(2**9+1)
    9
    >>> floor_log2(-2**9+1)
    8
    >>> floor_log2(0.5)
    -1
    >>> floor_log2(0) is None
    True
    """
    ip = 0
    rem = abs(x)
    if rem > 1:
        while rem >= 2:
            ip += 1
            rem //= 2
        return ip
    elif rem == 0:
        return None
    while rem < 1:
        ip -= 1
        rem *= 2
    return ip


def feed(consumer, iterable):
    """feed(consumer, iterable) -> yield items

    Helper function to send elements from an iterable into a coroutine.

    >>> def counter():              # Count the items sent in.
    ...     c = 0
    ...     _ = (yield None)        # Start the coroutine.
    ...     while True:
    ...             c += 1
    ...             _ = (yield c)   # Accept a value sent into the coroutine.
    ...
    >>> cr = counter()
    >>> cr.send(None)  # Prime the coroutine.
    >>> list(feed(cr, ["spam", "ham", "eggs"]))  # Send many values.
    [1, 2, 3]
    >>> cr.send("spam and eggs")  # Manually sending works too.
    4

    """
    for obj in iterable:
        yield consumer.send(obj)


def convert_kwargs_to_cmd_line_args(kwargs):
    """Helper function to build command line arguments out of dict."""
    args = []
    for k in sorted(kwargs.keys()):
        v = kwargs[k]
        args.append('-{}'.format(k))
        if v is not None:
            args.append('{}'.format(v))
    return args


def etime_to_secs(etime):
    """Parsing etimes is rougher than it should be."""
    seconds = 0
    etime = etime.split('-')
    if len(etime) == 2:
        seconds += int(etime[0]) * 24 * 60 * 60
        etime = etime[1]
    else:
        etime = etime[0]
    etime = etime.split(':')
    if len(etime) == 3:
        seconds += int(etime[0]) * 60 * 60
        mins, secs = etime[1:]
    else:
        mins, secs = etime
    seconds += 60 * int(mins) + int(secs)
    return seconds


def has_required_spacing(string, required_spacing):
    """
    Checks if a string has the required amount of spaces
    on each side.

    :param string:           The string which is to be checked.
    :param required_spacing: The number of spaces expected on both
                             sides of the string.
    :return:                 True if the string has the required
                             number of spaces on both sides, False
                             otherwise.

    >>> has_required_spacing("  foo  ", 2)
    True
    >>> has_required_spacing(" foo", 1)
    False
    """
    leading_spaces = len(string) - len(string.lstrip(' '))
    trailing_spaces = len(string) - len(string.rstrip(' '))
    return (leading_spaces == required_spacing and trailing_spaces ==
        required_spacing)


@classmethod
def for_driver_task(cls):
    """Create a FunctionDescriptor instance for a driver task."""
    return cls('', '', '', b'')


def prepare_lookup_value(key, value):
    """
    Return a lookup value prepared to be used in queryset filtering.
    """
    if key.endswith('__in'):
        value = value.split(',')
    elif key.endswith('__isnull'):
        value = value.lower() not in ('', 'false', '0')
    return value


def _restrict_to_spherical_volume(source, position, BoxSize):
    """
    Slice the input source such that it only includes a spherical volume
    instead the simulation box.

    This returns a CatalogSource only containing objects within a radius
    of 1/2 the minimum box side length of the box center.
    """
    origin = 0.5 * source.attrs['BoxSize']
    pos = position - origin
    r = (pos ** 2).sum(axis=-1) ** 0.5
    keep = r < 0.5 * source.attrs['BoxSize'].min()
    return source[keep]


@classmethod
def service_start(cls, options=None):
    """Build foreman-maintain service start"""
    cls.command_sub = 'start'
    if options is None:
        options = {}
    result = cls._construct_command(options)
    return result


def allowed_roles():
    """Private method which return a list of roles that that the
        group can have.
        """


def __cmp__(other):
    """if other is equivalent reference, return 0; else raise ValueError.

        Equivalent in this case means that oid and database_name are the same.

        If either is a weak reference, we only support `is` equivalence, and
        otherwise raise a ValueError even if the datbase_names and oids are
        the same, rather than guess at the correct semantics.

        It is impossible to sort reliably, since the actual persistent
        class may have its own comparison, and we have no idea what it is.
        We assert that it is reasonably safe to assume that an object is
        equivalent to itself, but that's as much as we can say.

        We don't compare on 'is other', despite the
        PersistentReferenceFactory.data cache, because it is possible to
        have two references to the same object that are spelled with different
        data (for instance, one with a class and one without)."""


def css_class_data_callback(data, **kwargs):
    """
    Check if TagAttributes
    """
    if 'attrs' in data and 'css_class' in data:
        data['attrs']['class'] = data['css_class']


def _denominate(total):
    """
    Coverts bucket size to human readable bytes.
    """
    total = float(total)
    denomination = ['KB', 'MB', 'GB', 'TB']
    for x in denomination:
        if total > 1024:
            total = total / 1024
        if total < 1024:
            total = round(total, 2)
            total = str(total) + ' ' + x
            break
    return total


@staticmethod
def _build_list_params(param_name, key, values):
    """Builds a list of POST parameters from a list or single value."""
    params = {}
    if hasattr(values, '__iter__'):
        index = 0
        for value in values:
            params[str(param_name) + '[' + str(index) + '].' + str(key)] = str(
                value)
            index += 1
    else:
        params[str(param_name) + '[0].' + str(key)] = str(values)
    return params


def reverse_lists(lists):
    """
    >>> reverse_lists([[1,2,3], [4,5,6]])
    [[3, 2, 1], [6, 5, 4]]
    """
    return list(map(list, map(reversed, lists)))


def skewness(a, axis=None):
    """Skewness of input"""
    raise NotImplementedError


def narrow_row(x, start, stop):
    """Narrow down the tensor along the first dimension.

    Parameters
    ----------
    x : Tensor
        The input tensor.
    start : int
        The start index (inclusive).
    stop : int
        The stop index (exclusive).

    Returns
    -------
    Tensor
        The narrowed tensor

    Notes
    -----
    The returned tensor could be a view of the original tensor.
    """
    pass


def inject_init(init_path, readme_path, setup_kwargs):
    """
        a method to add arguments to setup.py from module init file

    :param init_path: string with path to module __init__ file
    :param readme_path: string with path to module README.rst file
    :param setup_kwargs: dictionary with existing setup keyword arguments
    :return: dictionary with injected keyword arguments
    """
    import re
    from os import path
    from copy import deepcopy
    init_text = ''
    if not path.exists(init_path):
        raise ValueError('%s is not a valid path' % init_path)
    init_text = open(init_path).read()
    init_kwargs = {'version': '', 'author': '', 'url': '', 'description':
        '', 'license': ''}
    for key in init_kwargs.keys():
        key_regex = re.compile("__%s__\\s?\\=\\s?'(.*?)'" % key)
        key_search = key_regex.findall(init_text)
        if key_search:
            init_kwargs[key] = key_search[0]
    mod_kwargs = {'module': '', 'email': '', 'entry': '', 'authors': ''}
    for key in mod_kwargs.keys():
        key_regex = re.compile("__%s__\\s?\\=\\s?'(.*?)'" % key)
        key_search = key_regex.findall(init_text)
        if key_search:
            mod_kwargs[key] = key_search[0]
    if mod_kwargs['module']:
        init_kwargs['name'] = mod_kwargs['module']
    if mod_kwargs['entry']:
        init_kwargs['entry_points'] = {'console_scripts': [mod_kwargs['entry']]
            }
    if mod_kwargs['email']:
        init_kwargs['author_email'] = mod_kwargs['email']
        init_kwargs['maintainer_email'] = mod_kwargs['email']
    if mod_kwargs['authors']:
        del init_kwargs['author']
        init_kwargs['author_list'] = mod_kwargs['authors'].split(' ')
    if not path.exists(readme_path):
        raise ValueError('%s is not a valid path' % readme_path)
    try:
        readme_text = open(readme_path).read()
        init_kwargs['long_description'] = str(readme_text)
    except:
        raise ValueError('%s is not a valid text file.' % readme_path)
    setup_kwargs.update(**init_kwargs)
    updated_kwargs = deepcopy(setup_kwargs)
    for key, value in updated_kwargs.items():
        if not value:
            del setup_kwargs[key]
    return setup_kwargs


def collection_indirect_only_set():
    """Set collection to only contribute indirectly (through shadows and reflections) in the view layer

    """
    pass


def net_book_value(assets, liabilities, intangibles):
    """Computes net book value.

    @params
    -------
    assets: total assets
    liabilities: total liabilities
    intangibles: intangible assets

    returns
    -------
    Net [Adjusted (intangibles)] book value of an enterprice, int or float

    explanation
    -----------
    Generally the value of intangibles on the balance sheet is arbitrary and should be deducted from assets when
    calculating book value. (It is also referred to as the "net tangible assets" or "net book value" of the company)
    """
    return assets - intangibles - liabilities


def timepoints(df, second='first'):
    """Extract timepoints from a dataframe.

    Parameters
    ----------
    df : pd.DataFrame
        This dataframe will be used as a base.

    second : {'first' or 'last'}, default 'first'
        'last' to have the latest, 'first' to have the earliest values
        for timepoint 2.

    """
    index = ['Subject ID', 'Image ID']
    df.reset_index(inplace=True)
    df.set_index(index, inplace=True)
    df.sort_index(inplace=True)
    if 'index' in df.columns:
        df = df.drop(columns='index')
    if 'Description' in df.columns:
        raise ValueError(
            "Make sure that 'Description' is not in columns and only one image per timepoint is in the pd.DataFrame."
            )
    df_subjects = df.index.get_level_values(0)
    df_images = df.index.get_level_values(1)
    timepoints = {}
    if second == 'first':
        total_timepoints = max(df_subjects.value_counts())
        for i in range(total_timepoints):
            timepoint = i + 1
            timepoint_df = df[~df_subjects.duplicated(keep='first')]
            timepoint_str = 'Timepoint ' + str(timepoint)
            timepoints[timepoint_str] = timepoint_df
            df = df[~df_images.isin(timepoint_df.index.get_level_values(1))]
            df_subjects = df.index.get_level_values(0)
            df_images = df.index.get_level_values(1)
    elif second == 'last':
        timepoint_1 = df[~df_subjects.duplicated()]
        timepoints['Timepoint 1'] = timepoint_1
        timepoint_1_images = timepoint_1.index.get_level_values(1)
        after_timepoint_1 = df[~df_images.isin(timepoint_1_images)]
        after_timepoint_1_images = after_timepoint_1.index.get_level_values(0)
        timepoint_2_last = after_timepoint_1[~after_timepoint_1_images.
            duplicated(keep='last')]
        timepoints['Timepoint 2'] = timepoint_2_last
    return timepoints


@classmethod
def has_resuming(cls):
    """Returns whether it supports to resume the fetch process.

        :returns: this backend supports items resuming
        """
    return True


def _parse_userinfo(userinfo):
    """Try to split the URL's userinfo (the part between :// and @) into fields
    separated by :. If anything looks wrong, remind user to percent-encode values."""
    if hasattr(userinfo, 'split'):
        parts = userinfo.split(u':', 1)
        if len(parts) == 2:
            return parts
    raise ValueError(
        'Could not parse user/key in store-URL. Note that values have to be percent-encoded, eg. with urllib.quote_plus().'
        )


def _paginate(seq, page_size):
    """Consume an iterable and return it in chunks.

    Every chunk is at most `page_size`. Never return an empty chunk.
    """
    page = []
    it = iter(seq)
    while True:
        try:
            for i in range(page_size):
                page.append(next(it))
            yield page
            page = []
        except StopIteration:
            if page:
                yield page
            return


def pre_pack(pack_tid, get_references):
    """Decide what to pack.

        pack_tid specifies the most recent transaction to pack.

        get_references is a function that accepts a stored object state
        and returns a set of OIDs that state refers to.
        """


def __material_cf(d):
    """ Fixed length data fields for computer files. """
    return d[0:4], d[4], d[5], d[6:8], d[8], d[9], d[10], d[11:]


def __setitem__(k, value):
    """ Set a key/value pair into the dictionary"""


def get_dict_from_str(string):
    """
    Converts repo_from string into dictionary.
    Expected strings:
    'repo'
    'namespace/repo'
    'fork/username/repo'
    'fork/username/namespace/repo'
    """
    if string:
        words = string.split('/')
        if len(words) == 4:
            fork, username, namespace, repo = words
            return {'username': username, 'namespace': namespace, 'repo': repo}
        elif len(words) == 3:
            fork, username, repo = words
            return {'username': username, 'namespace': None, 'repo': repo}
        elif len(words) == 2:
            namespace, repo = words
            return {'username': None, 'namespace': namespace, 'repo': repo}
        elif len(words) == 1:
            repo, = words
            return {'username': None, 'namespace': None, 'repo': repo}
        else:
            raise Exception('Wrong formatted repo path')


def _true(*args):
    """
    Default rerun filter function that always returns True.
    """
    return True


def get_criteria(label):
    """Returns the RFC 3501 criteria string for the given label"""
    l = 'LARGER %d' % label.min if label.min is not None else ''
    s = 'SMALLER %d' % label.max if label.max is not None else ''
    return '{larger} {smaller}'.format(larger=l, smaller=s).strip()


def show(article):
    """Show one article"""
    print(article)


def convert_identity_rotations(data):
    """ Turns 0 angles axangles to [1,0,0,0] """
    data[:, (0)][data[:, (3)] == 0] = 1
    data[:, (1)][data[:, (3)] == 0] = 0
    data[:, (2)][data[:, (3)] == 0] = 0
    return data


def round_up_to_mult(n, mult):
    """Round an integer up to the next multiple."""
    return (n + mult - 1) // mult * mult


def impersonator_user_role(id, name):
    """
    Canned response for validate token if the token being validated
    is an impersonated token.
    """
    return {'id': id, 'roles': [{'id': '10000001', 'serviceId':
        'test-eabb70a0e702a4626977c331d5c4', 'description':
        'Service admin role for cloud feeds access. Assign only to service users'
        , 'name': 'cloudfeeds:service-admin'}, {'id': '10000002',
        'serviceId': 'test-eabb70a0e702a4626977c331d5c4', 'description':
        'Checkmate Access role', 'name': 'checkmate'}, {'id': '100000003',
        'serviceId': 'test-eabb70a0e702a4626977c331d5c4', 'description':
        'Service admin role for Monitoring access. Assign only to service users'
        , 'name': 'monitoring:service-admin'}, {'id': '100000004',
        'serviceId': 'test-eabb70a0e702a4626977c331d5c4', 'description':
        'Admin Role.', 'name': 'identity:admin'}, {'id': '10000005',
        'serviceId': 'test-d4614b87411e141fe8109099bc4f', 'description':
        'Role to access Customer service as an Admin', 'name':
        'customer:admin'}, {'id': '10000006', 'serviceId':
        'test-eabb70a0e702a4626977c331d5c4', 'description':
        'Service admin role for Cloud Backup access. Assign only to service users'
        , 'name': 'cloudbackup:service-admin'}], 'name': name}


def uint32_from_int32(value):
    """The unsigned 32-bit integer that is stored using bit-by-bit the same
  binary data as the givien signed 32-bit integer"""
    if value < 0:
        value = value + 4294967296
    return value


def exponent(attrs, inputs, proto_obj):
    """Elementwise exponent of input array."""
    return 'exp', attrs, inputs


def dedupe(sequence):
    """Yields a stable de-duplication of an hashable sequence

    Args:
        sequence: hashable sequence to be de-duplicated

    Returns:
        stable de-duplication of the sequence
    """
    seen = set()
    for x in sequence:
        if x not in seen:
            yield x
            seen.add(x)


def find_offset(offset, mapping):
    """Find the offset tuple for a single offset."""
    if isinstance(offset, tuple):
        return offset
    for token_offset, position in mapping:
        if offset <= token_offset:
            break
    return position[0], position[1] + offset - token_offset


def available_dt_filters():
    """
    Iterable of available wavelet filters compatible with the dual-tree complex wavelet transform.

    Returns
    -------
    wavelets : iterable
        List of sorted string names. The wavelet numerical values can be
        retrieved from the :func:`dualtree_wavelet` function.
    """
    return sorted(['qshift1', 'qshift2', 'qshift3', 'qshift4', 'qshift5',
        'qshift6'])


def to_lower_normalizer(name):
    """Utility normalizer that converts a name to lowercase unless it is an
    acronym. To be used as parameter of download_freebase_type().
    """
    words = name.split()
    result = []
    for w in words:
        if not w.isupper():
            w = w.lower()
        result.append(w)
    return ' '.join(result)


def render_pep440_old(pieces):
    """TAG[.postDISTANCE[.dev0]] .

    The ".dev0" means dirty.

    Eexceptions:
    1: no tags. 0.postDISTANCE[.dev0]
    """
    if pieces['closest-tag']:
        rendered = pieces['closest-tag']
        if pieces['distance'] or pieces['dirty']:
            rendered += '.post%d' % pieces['distance']
            if pieces['dirty']:
                rendered += '.dev0'
    else:
        rendered = '0.post%d' % pieces['distance']
        if pieces['dirty']:
            rendered += '.dev0'
    return rendered


def auto_off():
    """turn off all Auto push signals on"""
    from rdf_io.signals import clear_signals
    return clear_signals()


def get_rpgsnapshot(module, array):
    """Return iReplicated Snapshot or None"""
    try:
        snapname = module.params['name'] + '.' + module.params['suffix'
            ] + '.' + module.params['restore']
        for snap in array.list_volumes(snap=True):
            if snap['name'] == snapname:
                return snapname
    except Exception:
        return None


def is_rate_limit_error_message(message):
    """Check if the supplied error message belongs to a rate limit error."""
    return isinstance(message, list) and len(message
        ) > 0 and 'code' in message[0] and message[0]['code'] == 88


def AsyncPendingWrite(file):
    """
    Module function to check for data to be written.

    @param file The file object to be checked
    @type file
    @return Flag indicating if there is data waiting
    @rtype int
    """
    try:
        pending = file.pendingWrite()
    except Exception:
        pending = 0
    return pending


def compose2(f, g):
    """Compose two functions, g(f(x))"""
    return lambda x: g(f(x))


def metadata_isdir(name):
    """Is the named metadata a directory?  (like ``os.path.isdir()``)"""


def list_network_profiles(arn=None, type=None, nextToken=None):
    """
    Returns the list of available network profiles.
    See also: AWS API Documentation

    :example: response = client.list_network_profiles(
        arn='string',
        type='CURATED'|'PRIVATE',
        nextToken='string'
    )

    :type arn: string
    :param arn: [REQUIRED]
            The Amazon Resource Name (ARN) of the project for which you want to list network profiles.

    :type type: string
    :param type: The type of network profile you wish to return information about. Valid values are listed below.

    :type nextToken: string
    :param nextToken: An identifier that was returned from the previous call to this operation, which can be used to return the next set of items in the list.

    :rtype: dict
    :return: {
        'networkProfiles': [
            {
                'arn': 'string',
                'name': 'string',
                'description': 'string',
                'type': 'CURATED'|'PRIVATE',
                'uplinkBandwidthBits': 123,
                'downlinkBandwidthBits': 123,
                'uplinkDelayMs': 123,
                'downlinkDelayMs': 123,
                'uplinkJitterMs': 123,
                'downlinkJitterMs': 123,
                'uplinkLossPercent': 123,
                'downlinkLossPercent': 123
            },
        ],
        'nextToken': 'string'
    }

    """
    pass


def _coef(ctx, J, eps):
    """
    Computes the coefficients  `c_n`  for `0\\le n\\le 2J` with error less than eps

    **Definition**

    The coefficients c_n are defined by

    .. math ::

        \\begin{equation}
        F(z)=\\frac{e^{\\pi i
        \\bigl(\\frac{z^2}{2}+\\frac38\\bigr)}-i\\sqrt{2}\\cos\\frac{\\pi}{2}z}{2\\cos\\pi
        z}=\\sum_{n=0}^\\infty c_{2n} z^{2n}
        \\end{equation}

    they are computed applying the relation

    .. math ::

        \\begin{multline}
        c_{2n}=-\\frac{i}{\\sqrt{2}}\\Bigl(\\frac{\\pi}{2}\\Bigr)^{2n}
        \\sum_{k=0}^n\\frac{(-1)^k}{(2k)!}
        2^{2n-2k}\\frac{(-1)^{n-k}E_{2n-2k}}{(2n-2k)!}+\\\\
        +e^{3\\pi i/8}\\sum_{j=0}^n(-1)^j\\frac{
        E_{2j}}{(2j)!}\\frac{i^{n-j}\\pi^{n+j}}{(n-j)!2^{n-j+1}}.
        \\end{multline}
    """
    newJ = J + 2
    neweps6 = eps / 2.0
    wpvw = max(ctx.mag(10 * (newJ + 3)), 4 * newJ + 5 - ctx.mag(neweps6))
    E = ctx._eulernum(2 * newJ)
    wppi = max(ctx.mag(40 * newJ), ctx.mag(newJ) + 3 + wpvw)
    ctx.prec = wppi
    pipower = {}
    pipower[0] = ctx.one
    pipower[1] = ctx.pi
    for n in range(2, 2 * newJ + 1):
        pipower[n] = pipower[n - 1] * ctx.pi
    ctx.prec = wpvw + 2
    v = {}
    w = {}
    for n in range(0, newJ + 1):
        va = (-1) ** n * ctx._eulernum(2 * n)
        va = ctx.mpf(va) / ctx.fac(2 * n)
        v[n] = va * pipower[2 * n]
    for n in range(0, 2 * newJ + 1):
        wa = ctx.one / ctx.fac(n)
        wa = wa / 2 ** n
        w[n] = wa * pipower[n]
    ctx.prec = 15
    wpp1a = 9 - ctx.mag(neweps6)
    P1 = {}
    for n in range(0, newJ + 1):
        ctx.prec = 15
        wpp1 = max(ctx.mag(10 * (n + 4)), 4 * n + wpp1a)
        ctx.prec = wpp1
        sump = 0
        for k in range(0, n + 1):
            sump += (-1) ** k * v[k] * w[2 * n - 2 * k]
        P1[n] = (-1) ** (n + 1) * ctx.j * sump
    P2 = {}
    for n in range(0, newJ + 1):
        ctx.prec = 15
        wpp2 = max(ctx.mag(10 * (n + 4)), 4 * n + wpp1a)
        ctx.prec = wpp2
        sump = 0
        for k in range(0, n + 1):
            sump += ctx.j ** (n - k) * v[k] * w[n - k]
        P2[n] = sump
    ctx.prec = 15
    wpc0 = 5 - ctx.mag(neweps6)
    wpc = max(6, 4 * newJ + wpc0)
    ctx.prec = wpc
    mu = ctx.sqrt(ctx.mpf('2')) / 2
    nu = ctx.expjpi(3.0 / 8) / 2
    c = {}
    for n in range(0, newJ):
        ctx.prec = 15
        wpc = max(6, 4 * n + wpc0)
        ctx.prec = wpc
        c[2 * n] = mu * P1[n] + nu * P2[n]
    for n in range(1, 2 * newJ, 2):
        c[n] = 0
    return [newJ, neweps6, c, pipower]


@conf
def find_gdc(conf):
    """
	Finds the program gdc and set the variable *D*
	"""
    conf.find_program('gdc', var='D')
    out = conf.cmd_and_log(conf.env.D + ['--version'])
    if out.find('gdc') == -1:
        conf.fatal('detected compiler is not gdc')


def gather(attrs, inputs, proto_obj):
    """Gather elements from an input array along the given axis."""
    return 'take', attrs, inputs


@classmethod
def _csv_filter_class_name(cls, filter_class, lookup_type):
    """
        Generate a suitable class name for a concrete filter class. This is not
        completely reliable, as not all filter class names are of the format
        <Type>Filter.

        ex::

            FilterSet._csv_filter_class_name(DateTimeFilter, 'in')

            returns 'DateTimeInFilter'

        """
    type_name = filter_class.__name__
    if type_name.endswith('Filter'):
        type_name = type_name[:-6]
    lookup_name = lookup_type.capitalize()
    return str('%s%sFilter' % (type_name, lookup_name))


def _v(value):
    """Dereference values (callable)"""
    return value() if callable(value) else value


def apply(x_train, func, output_col: str, x_test=None):
    """
    Wrapper for pandas apply function to be used in this library. Applies `func` to the entire data
    or just the trianing and testing data

    Parameters
    ----------
    x_train : DataFrame
        Dataset

    func : Function pointer
        Function describing the transformation for the new column

    output_col : str
        New column name

    x_test : DataFrame
        Testing dataset, by default None

    Returns
    -------
    Dataframe, *Dataframe
        Transformed dataframe with the new column

    Returns 2 Dataframes if x_test is provided.
    """
    import swifter
    x_train.loc[:, (output_col)] = x_train.swifter.progress_bar().apply(func,
        axis=1)
    if x_test is not None:
        x_test.loc[:, (output_col)] = x_test.swifter.progress_bar().apply(func,
            axis=1)
    return x_train, x_test


def part_of_env(pattern, env_name):
    """Decide if pattern is part of env_name"""
    for part in pattern.split('-'):
        if part.startswith('!'):
            if part[1:] in env_name:
                return False
        elif part not in env_name:
            return False
    return True


def is_rds_db_snapshot_attr_public_access(rds_db_snapshot_attribute):
    """
    Checks whether a RDS snapshot attribute is:

    {
        "AttributeName": "restore",
        "AttributeValues": ["random_aws_account_id", "any"]
    }

    >>> is_rds_db_snapshot_attr_public_access({"AttributeName": "restore", "AttributeValues": ["any"]})
    True
    >>> is_rds_db_snapshot_attr_public_access({"AttributeName": "restore", "AttributeValues": ["aws_account_id"]})
    False
    >>> is_rds_db_snapshot_attr_public_access({"AttributeName": "restore", "AttributeValues": []})
    False
    >>> is_rds_db_snapshot_attr_public_access({"AttributeName": "blorg", "AttributeValues": ["any"]})
    False
    >>> is_rds_db_snapshot_attr_public_access([])
    Traceback (most recent call last):
    ...
    TypeError: list indices must be integers or slices, not str
    >>> is_rds_db_snapshot_attr_public_access(0)
    Traceback (most recent call last):
    ...
    TypeError: 'int' object is not subscriptable
    >>> is_rds_db_snapshot_attr_public_access(None)
    Traceback (most recent call last):
    ...
    TypeError: 'NoneType' object is not subscriptable
    """
    return rds_db_snapshot_attribute['AttributeName'
        ] == 'restore' and 'any' in rds_db_snapshot_attribute['AttributeValues'
        ]


def merge_dicts(*dicts):
    """Given any number of dicts, merges them into a new one."""
    result = {}
    for d in dicts:
        result.update(d)
    return result


def provider_parser(subparser):
    """Configure provider parser for Vultr"""
    subparser.add_argument('--auth-token', help=
        'specify token for authentication')


def num_container_updates(container_replicas, container_quorum,
    object_replicas, object_quorum):
    """
    We need to send container updates via enough object servers such
    that, if the object PUT succeeds, then the container update is
    durable (either it's synchronously updated or written to async
    pendings).

    Define:
      Qc = the quorum size for the container ring
      Qo = the quorum size for the object ring
      Rc = the replica count for the container ring
      Ro = the replica count (or EC N+K) for the object ring

    A durable container update is one that's made it to at least Qc
    nodes. To always be durable, we have to send enough container
    updates so that, if only Qo object PUTs succeed, and all the
    failed object PUTs had container updates, at least Qc updates
    remain. Since (Ro - Qo) object PUTs may fail, we must have at
    least Qc + Ro - Qo container updates to ensure that Qc of them
    remain.

    Also, each container replica is named in at least one object PUT
    request so that, when all requests succeed, no work is generated
    for the container replicator. Thus, at least Rc updates are
    necessary.

    :param container_replicas: replica count for the container ring (Rc)
    :param container_quorum: quorum size for the container ring (Qc)
    :param object_replicas: replica count for the object ring (Ro)
    :param object_quorum: quorum size for the object ring (Qo)

    """
    return max(container_quorum + object_replicas - object_quorum,
        container_replicas)


def water_from_lipid_protein(lipid, protein):
    """Calculate total body water from total lipid and protein

    Args
    ----
    lipid: float or ndarray
        Mass of lipid content in animal
    protein: float or ndarray
        Mass of protein content in animal

    Returns
    -------
    water: float or ndarray
        Mass of water content in animal

    References
    ----------
    Reilly, J.J., Fedak, M.A., 1990. Measurement of the body composition of
    living gray seals by hydrogen isotope dilution. Journal of Applied
    Physiology 69, 885–891.
    """
    return -4.408148e-16 + 2.828348 * protein + 0.1278273 * lipid