@classmethod
def Zaxis(cls):
    """Construct a unit vector along the Z axis.

        Returns
        -------
        :class:`compas.geometry.Vector`
            A vector with components ``x = 0.0, y = 0.0, z = 1.0``.

        Examples
        --------
        >>> Vector.Zaxis()
        Vector(0.000, 0.000, 1.000)
        """
    return cls(0.0, 0.0, 1.0)


def process_shared_options(context_obj, kwargs):
    """
    Update context with values for shared options.
    """
    context_obj['config'] = kwargs['config']
    context_obj['no_color'] = kwargs['no_color']
    context_obj['log_level'] = kwargs['log_level']
    context_obj['download_url'] = kwargs['download_url']
    context_obj['target_dir'] = kwargs['target_dir']
    context_obj['arch'] = kwargs['arch']
    context_obj['profile'] = kwargs['profile']
    context_obj['image_name'] = kwargs['image_name']


@staticmethod
def spawn(val):
    """Use the new value to spawn an new adapter of this adapter.
        """
    raise NotImplementedError()


def double_check_attribute(object, setter, backup_attribute,
    custom_error_text=None):
    """Check if a parameter to be used is None, if it is, then check the specified backup attribute and throw
    an error if it is also None.

    Args:
        object: The original object
        setter: Any input object
        backup_attribute (str): Attribute in <object> to be double checked
        custom_error_text (str): If a custom string for the error should be raised

    Raises:
         ValueError: If both setter and backup_attribute are None

    """
    if not setter:
        next_checker = getattr(object, backup_attribute)
        if not next_checker:
            if custom_error_text:
                raise ValueError(custom_error_text)
            else:
                raise ValueError('Attribute replacing "{}" must be specified'
                    .format(backup_attribute))


def finalize_client(client):
    """Stops and closes a client, even if it wasn't started."""
    client.stop()
    client.close()


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

        :param AccountCaptureChangePolicyDetails val:
        :rtype: EventDetails
        """
    return cls('account_capture_change_policy_details', val)


def set_default_image(session, cloud_name, image_id, return_type=None, **kwargs
    ):
    """
    Set default Image

    :type session: zadarapy.session.Session
    :param session: A valid zadarapy.session.Session object.  Required.

    :type cloud_name: str
    :param cloud_name: Cloud Name: i.e: zadaraqa9

    :type image_id: str
    :param image_id: Image ID

    :type return_type: str
    :param return_type: If this is set to the string 'json', this function
        will return a JSON string.  Otherwise, it will return a Python
        dictionary.  Optional (will return a Python dictionary by default).

    :rtype: dict, str
    :returns: A dictionary or JSON data set as a string depending on
        return_type parameter.
    """
    path = '/api/clouds/{0}/images/{1}/set_default.json'.format(cloud_name,
        image_id)
    return session.post_api(path=path, return_type=return_type, **kwargs)


def trim1(l, proportiontocut, tail='right'):
    """
Slices off the passed proportion of items from ONE end of the passed
list (i.e., if proportiontocut=0.1, slices off 'leftmost' or 'rightmost'
10% of scores).  Slices off LESS if proportion results in a non-integer
slice index (i.e., conservatively slices off proportiontocut).

Usage:   ltrim1 (l,proportiontocut,tail='right')  or set tail='left'
Returns: trimmed version of list l
"""
    if tail == 'right':
        lowercut = 0
        uppercut = len(l) - int(proportiontocut * len(l))
    elif tail == 'left':
        lowercut = int(proportiontocut * len(l))
        uppercut = len(l)
    return l[lowercut:uppercut]


def __new__(cls, positionals=None, keywords=None):
    """Overwrite class creation to provide proper default arguments."""
    if positionals is None:
        positionals = []
    if keywords is None:
        keywords = {}
    return super().__new__(cls, positionals, keywords)


def _set_ids(ctx):
    """Sets document id.

    """
    for grid in (ctx.doc.esm_model_grids + ctx.doc.esm_exchange_grids):
        if not grid.id:
            grid.id = grid.short_name


def paste_splines():
    """Paste splines from clipboard

    """
    pass


def package_name(artifact):
    """
    Retrieves python package (app) name if denoted with 'PACKAGE' in a project file
    """
    try:
        with open(artifact) as f1:
            f2 = f1.readlines()
        for line in f2:
            if line.startswith('PACKAGE'):
                return line.split(':')[1].strip()
    except Exception:
        return None


def format_size(size):
    """
    Return a human-readable value for the `size` int or float.

    For example:
    >>> assert format_size(0) == '0 Byte'
    >>> assert format_size(1) == '1 Byte'
    >>> assert format_size(0.123) == '0.1 Byte'
    >>> assert format_size(123) == '123 Bytes'
    >>> assert format_size(1023) == '1023 Bytes'
    >>> assert format_size(1024) == '1 KB'
    >>> assert format_size(2567) == '2.51 KB'
    >>> assert format_size(2567000) == '2.45 MB'
    >>> assert format_size(1024*1024) == '1 MB'
    >>> assert format_size(1024*1024*1024) == '1 GB'
    >>> assert format_size(1024*1024*1024*12.3) == '12.30 GB'
    """
    if not size:
        return '0 Byte'
    if size < 1:
        return '%(size).1f Byte' % locals()
    if size == 1:
        return '%(size)d Byte' % locals()
    size = float(size)
    for symbol in ('Bytes', 'KB', 'MB', 'GB', 'TB'):
        if size < 1024:
            if int(size) == float(size):
                return '%(size)d %(symbol)s' % locals()
            return '%(size).2f %(symbol)s' % locals()
        size = size / 1024.0
    return '%(size).2f %(symbol)s' % locals()


@classmethod
def toBool(cls, value):
    """ converts to bool

        :param value: variable to convert
        :type value: any
        :returns: result in bool type
        :rtype: :obj:`bool`
        """
    if type(value).__name__ == 'str' or type(value).__name__ == 'unicode':
        lvalue = value.strip().lower()
        if lvalue == 'false' or lvalue == '0':
            return False
        else:
            return True
    elif value:
        return True
    return False


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 get_plural_string(word: str, amount: int) ->str:
    """Returns singular or plural of the word depending on the amount.
	Example:
		word = 'piece', amount = 0 -> '0 pieces'
		word = 'piece', amount = 1 -> '1 piece'
		word = 'piece', amount = 5 -> '5 pieces'"""
    if amount == 1:
        return f'1 {word}'
    else:
        return f'{amount} {word}s'


def is_classifier(estimator):
    """Return True if the given estimator is (probably) a classifier.

    Parameters
    ----------
    estimator : object
        Estimator object to test.

    Returns
    -------
    out : bool
        True if estimator is a classifier and False otherwise.
    """
    return getattr(estimator, '_estimator_type', None) == 'classifier'


def pull_reference(integrate_mtz):
    """Generate reference data set from integrate.hkl, check out the calculated
    x, y and z centroids as well as the Miller indices as coordinates in some
    high dimensional space. Only consider measurements with meaningful
    centroids..."""
    from iotbx import mtz
    m = mtz.object(integrate_mtz)
    hkl = m.extract_original_index_miller_indices()
    b0 = m.batches()[0]
    for c in m.columns():
        if c.label() == 'I':
            i_lp = c.extract_valid_values()
        elif c.label() == 'SIGI':
            sigi = c.extract_valid_values()
        elif c.label() == 'XDET':
            xdet = c.extract_valid_values()
        elif c.label() == 'YDET':
            ydet = c.extract_valid_values()
        elif c.label() == 'ROT':
            rot = c.extract_valid_values()
        elif c.label() == 'LP':
            lp = c.extract_valid_values()
    xyz = []
    dx = b0.detlm()[1]
    dz = b0.phiend() - b0.phistt()
    z0 = b0.phistt()
    for x, y, r in zip(xdet, ydet, rot):
        _x = y
        _y = x
        _z = (r - z0) / dz
        xyz.append((_x, _y, _z))
    i = i_lp / lp
    print('Reference: %d observations' % len(hkl))
    return hkl, i, sigi, xyz


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 luhn(card_number):
    """
    Test whether a bankcard number passes the Luhn algorithm.
    """
    card_number = str(card_number)
    sum = 0
    num_digits = len(card_number)
    odd_even = num_digits & 1
    for i in range(0, num_digits):
        digit = int(card_number[i])
        if not i & 1 ^ odd_even:
            digit = digit * 2
        if digit > 9:
            digit = digit - 9
        sum = sum + digit
    return sum % 10 == 0


def get_server_angulars(server):
    """Return latitude and longitude from server

    :param server: a dictionary describing a server
    :returns: tuple with latitude and longitude
    """
    latitude = str(server['location']['lat'])
    longitude = str(server['location']['long'])
    return latitude, longitude


@staticmethod
def parameters_dict(parameters):
    """
        Create and return a dict from a list of PSO parameters.
        This is useful for printing the named parameters.

        :param parameters: List with PSO parameters assumed to be in the correct order.
        :return: Dict with PSO parameters.
        """
    return {'num_particles': parameters[0], 'omega': parameters[1], 'phi_p':
        parameters[2], 'phi_g': parameters[3]}


def get_calculation_annotation(calculation_field, calculation_method):
    """
    Returns the default django annotation
    @param calculation_field: the field to calculate ex 'value'
    @param calculation_method: the aggregation method ex: Sum
    @return: the annotation ex value__sum
    """
    return '__'.join([calculation_field.lower(), calculation_method.name.
        lower()])


def unset_property_button():
    """Clear the property and use default or generated value in operators

    """
    pass


def _multi(singular, plural, count):
    """
    Provides translations for plural and singular forms of a term.
    """
    if count == 1:
        return singular
    else:
        return plural


def format_delta(delta):
    """Get a nice looking string for a time delta.

    :param delta: The time difference in seconds, can be positive or negative.
        positive indicates time in the past, negative indicates time in the
        future. (usually time.time() - stored_time)
    :return: String formatted to show approximate resolution
    """
    delta = int(delta)
    if delta >= 0:
        direction = 'ago'
    else:
        direction = 'in the future'
        delta = -delta
    seconds = delta
    if seconds < 90:
        if seconds == 1:
            return '%d second %s' % (seconds, direction)
        else:
            return '%d seconds %s' % (seconds, direction)
    minutes = int(seconds / 60)
    seconds -= 60 * minutes
    if seconds == 1:
        plural_seconds = ''
    else:
        plural_seconds = 's'
    if minutes < 90:
        if minutes == 1:
            return '%d minute, %d second%s %s' % (minutes, seconds,
                plural_seconds, direction)
        else:
            return '%d minutes, %d second%s %s' % (minutes, seconds,
                plural_seconds, direction)
    hours = int(minutes / 60)
    minutes -= 60 * hours
    if minutes == 1:
        plural_minutes = ''
    else:
        plural_minutes = 's'
    if hours == 1:
        return '%d hour, %d minute%s %s' % (hours, minutes, plural_minutes,
            direction)
    return '%d hours, %d minute%s %s' % (hours, minutes, plural_minutes,
        direction)


def scan_setup_py():
    """Validate the contents of setup.py against Versioneer's expectations."""
    found = set()
    setters = False
    errors = 0
    with open('setup.py', 'r') as f:
        for line in f.readlines():
            if 'import versioneer' in line:
                found.add('import')
            if 'versioneer.get_cmdclass()' in line:
                found.add('cmdclass')
            if 'versioneer.get_version()' in line:
                found.add('get_version')
            if 'versioneer.VCS' in line:
                setters = True
            if 'versioneer.versionfile_source' in line:
                setters = True
    if len(found) != 3:
        print('')
        print('Your setup.py appears to be missing some important items')
        print('(but I might be wrong). Please make sure it has something')
        print('roughly like the following:')
        print('')
        print(' import versioneer')
        print(' setup( version=versioneer.get_version(),')
        print('        cmdclass=versioneer.get_cmdclass(),  ...)')
        print('')
        errors += 1
    if setters:
        print("You should remove lines like 'versioneer.VCS = ' and")
        print("'versioneer.versionfile_source = ' . This configuration")
        print('now lives in setup.cfg, and should be removed from setup.py')
        print('')
        errors += 1
    return errors


def ElementWiseSum(*args, **kwargs):
    """Adds all input arguments element-wise.

    .. math::
       add\\_n(a_1, a_2, ..., a_n) = a_1 + a_2 + ... + a_n

    ``add_n`` is potentially more efficient than calling ``add`` by `n` times.

    The storage type of ``add_n`` output depends on storage types of inputs

    - add_n(row_sparse, row_sparse, ..) = row_sparse
    - add_n(default, csr, default) = default
    - add_n(any input combinations longer than 4 (>4) with at least one default type) = default
    - otherwise, ``add_n`` falls all inputs back to default storage and generates default storage

    Defined in src/operator/tensor/elemwise_sum.cc:L155
    This function support variable length of positional input.

    Parameters
    ----------
    args : Symbol[]
        Positional input arguments

    name : string, optional.
        Name of the resulting symbol.

    Returns
    -------
    Symbol
        The result symbol.
    """
    return 0,


@classmethod
def _rebuild(cls, name, argtypes, cufunc, link, debug, call_helper,
    extensions, config):
    """
        Rebuild an instance.
        """
    instance = cls.__new__(cls)
    super(cls, instance).__init__()
    instance.entry_name = name
    instance.argument_types = tuple(argtypes)
    instance.linking = tuple(link)
    instance._type_annotation = None
    instance._func = cufunc
    instance.debug = debug
    instance.call_helper = call_helper
    instance.extensions = extensions
    instance._deserialize_config(config)
    return instance


def bin2dec(x):
    """Converts the binary array to decimal."""
    y = 0
    for i, j in enumerate(x):
        if j:
            y += 1 << i
    return y


def to50(theVal):
    """Converts a double to Rep code 0x32, 32bit floating point representation."""
    assert 0
    return 0.0


@staticmethod
def parsestring(value):
    """Parse a string with values."""
    return str.join(' ', value) if value else None


def is_filelike(obj):
    """Return whether ``obj`` is a file-like object."""
    return hasattr(obj, 'read')


def get_environment(message, slot):
    """Return the environment variables to use for running the process.

        `message` is the message received from the IPoller.next() method
        `slot` is the Launcher slot where the process will be running.
        """


def is_int(value):
    """Checks if a value is an integer.

    The type of the value is not important, it might be an int or a float."""
    try:
        return value == int(value)
    except Exception:
        return False


def authorize_db_security_group_ingress(DBSecurityGroupName=None, CIDRIP=
    None, EC2SecurityGroupName=None, EC2SecurityGroupId=None,
    EC2SecurityGroupOwnerId=None):
    """
    Enables ingress to a DBSecurityGroup using one of two forms of authorization. First, EC2 or VPC security groups can be added to the DBSecurityGroup if the application using the database is running on EC2 or VPC instances. Second, IP ranges are available if the application accessing your database is running on the Internet. Required parameters for this API are one of CIDR range, EC2SecurityGroupId for VPC, or (EC2SecurityGroupOwnerId and either EC2SecurityGroupName or EC2SecurityGroupId for non-VPC).
    For an overview of CIDR ranges, go to the Wikipedia Tutorial .
    See also: AWS API Documentation

    Examples
    This example authorizes access to the specified security group by the specified CIDR block.
    Expected Output:

    :example: response = client.authorize_db_security_group_ingress(
        DBSecurityGroupName='string',
        CIDRIP='string',
        EC2SecurityGroupName='string',
        EC2SecurityGroupId='string',
        EC2SecurityGroupOwnerId='string'
    )

    :type DBSecurityGroupName: string
    :param DBSecurityGroupName: [REQUIRED]
            The name of the DB security group to add authorization to.

    :type CIDRIP: string
    :param CIDRIP: The IP range to authorize.

    :type EC2SecurityGroupName: string
    :param EC2SecurityGroupName: Name of the EC2 security group to authorize. For VPC DB security groups, EC2SecurityGroupId must be provided. Otherwise, EC2SecurityGroupOwnerId and either EC2SecurityGroupName or EC2SecurityGroupId must be provided.

    :type EC2SecurityGroupId: string
    :param EC2SecurityGroupId: Id of the EC2 security group to authorize. For VPC DB security groups, EC2SecurityGroupId must be provided. Otherwise, EC2SecurityGroupOwnerId and either EC2SecurityGroupName or EC2SecurityGroupId must be provided.

    :type EC2SecurityGroupOwnerId: string
    :param EC2SecurityGroupOwnerId: AWS account number of the owner of the EC2 security group specified in the EC2SecurityGroupName parameter. The AWS Access Key ID is not an acceptable value. For VPC DB security groups, EC2SecurityGroupId must be provided. Otherwise, EC2SecurityGroupOwnerId and either EC2SecurityGroupName or EC2SecurityGroupId must be provided.

    :rtype: dict
    :return: {
        'DBSecurityGroup': {
            'OwnerId': 'string',
            'DBSecurityGroupName': 'string',
            'DBSecurityGroupDescription': 'string',
            'VpcId': 'string',
            'EC2SecurityGroups': [
                {
                    'Status': 'string',
                    'EC2SecurityGroupName': 'string',
                    'EC2SecurityGroupId': 'string',
                    'EC2SecurityGroupOwnerId': 'string'
                },
            ],
            'IPRanges': [
                {
                    'Status': 'string',
                    'CIDRIP': 'string'
                },
            ],
            'DBSecurityGroupArn': 'string'
        }
    }

    :returns:
    DescribeDBSecurityGroups
    AuthorizeDBSecurityGroupIngress
    CreateDBSecurityGroup
    RevokeDBSecurityGroupIngress

    """
    pass


@staticmethod
def p_source_optional(p):
    """source_optional : display_identifier
                           | qp_blob"""
    p[0] = p.slice[1].type, p[1]


def exp(data=None, out=None, name=None, **kwargs):
    """Returns element-wise exponential value of the input.

    .. math::
       exp(x) = e^x \\approx 2.718^x

    Example::

       exp([0, 1, 2]) = [1., 2.71828175, 7.38905621]

    The storage type of ``exp`` output is always dense

    Defined in src/operator/tensor/elemwise_unary_op_logexp.cc:L63

    Parameters
    ----------
    data : NDArray
        The input array.

    out : NDArray, optional
        The output NDArray to hold the result.

    Returns
    -------
    out : NDArray or list of NDArrays
        The output of this function.
    """
    return 0,


def get_related_model(model, source):
    """Try to find the other side of a model relationship given the name of a related field.

    :param model: one side of the relationship
    :param str source: related field name
    :return: related model or ``None``
    """
    try:
        descriptor = getattr(model, source)
        try:
            return descriptor.rel.related_model
        except Exception:
            return descriptor.field.remote_field.model
    except Exception:
        return None


def _set_default_configuration():
    """Return a default configuration based on fields defined on the
        schema.

        This should be a dictionary.  But, we have at least one
        exception: the css_class field simply has a string.  This
        might change in the future if this bites us.

        All fields with dictionaries must have, at least, the
        following attributes:

        visibility: (u'on', u'off')
            is the field visible? defaults to u'on'
            XXX: this could be a boolean in the future
        order: (u'1', u'2', ...)
            in which order we are going to display the field?
            XXX: until we fix the UI, we must start with 1 instead of 0
                 because is most intuitive for end users

        the following attribute is available only in TextLine fields:

        htmltag: (u'h1', u'h2', ...)
            defaults to u'h2'
            XXX: this name is a bad one, but I have no proposal for now

        the following attributes are available only in NamedImage fields:

        position: (u'inline', u'left', u'right')
            defaults to u'left'
            XXX: this should be named 'alignment' probably
        imgsize: (any of the available sizes for scaled down images)
            defaults to u'mini 200:200' or first available size
            XXX: this should be named 'scale' probably

        final result will be something like this:

        {'css_class': u'tile_default',
         'date': {'order': u'3', 'visibility': u'on', 'format': 'datetime'},
         'description': {'order': u'1', 'visibility': u'on'},
         'image': {'imgsize': u'mini 200:200',
                   'order': u'2',
                   'position': u'left',
                   'visibility': u'on'},
         'subjects': {'order': u'4', 'visibility': u'on'},
         'title': {'htmltag': u'h2', 'order': u'0', 'visibility': u'on'},
         'uuid': {'htmltag': u'h2', 'order': u'5', 'visibility': u'on'}}

        Obviously some of the fields are not meant to be displayed,
        like css_class, but that's another story.
        """


def shortest_path_select(use_face_step: bool=False, use_topology_distance:
    bool=False, use_fill: bool=False, nth: int=1, skip: int=1, offset: int=0):
    """Selected shortest path between two vertices/edges/faces

    :param use_face_step: Face Stepping, Traverse connected faces (includes diagonals and edge-rings)
    :type use_face_step: bool
    :param use_topology_distance: Topology Distance, Find the minimum number of steps, ignoring spatial distance
    :type use_topology_distance: bool
    :param use_fill: Fill Region, Select all paths between the source/destination elements
    :type use_fill: bool
    :param nth: Nth Selection
    :type nth: int
    :param skip: Skip
    :type skip: int
    :param offset: Offset
    :type offset: int
    """
    pass


def symmetric_transmission_constraint_rule(backend_model, loc_tech):
    """
    Constrain e_cap symmetrically for transmission nodes. Transmission techs only.

    .. container:: scrolling-wrapper

        .. math::

            energy_{cap}(loc1::tech:loc2) = energy_{cap}(loc2::tech:loc1)

    """
    lookup = backend_model.__calliope_model_data['data']['lookup_remotes']
    loc_tech_remote = lookup[loc_tech]
    return backend_model.energy_cap[loc_tech] == backend_model.energy_cap[
        loc_tech_remote]


def iterate_pairs(mylist):
    """Go through an iterable and return the current item and the next"""
    if len(mylist) < 2:
        return
    for i, d in enumerate(mylist[:-1]):
        yield mylist[i], mylist[i + 1]
    return


def isFile(path):
    """Returns True if the given path is a file."""


def stackdepth(frame):
    """Tells the stackdepth of a gdb frame."""
    depth = 0
    while frame:
        frame = frame.older()
        depth += 1
    return depth


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

        :param TfaRemoveExceptionType val:
        :rtype: EventType
        """
    return cls('tfa_remove_exception', val)


def get_text(node):
    """Get the contents of text nodes in a parent node"""
    return node.text


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


@classmethod
def register_package(cls, package):
    """Register a Package."""
    try:
        cls.package_by_name(package.name)
        raise Exception('Package with name %s already exists' % package.name)
    except IndexError:
        cls.packages.append(package)


@classmethod
def block_filter(cls, session, stop_id, stop_times):
    """
        we don't want to show stop times that are arrivals, so we look at the blocks and figure out whether
        the input stop is the ending stop, and that there's a next trip starting at this same stop.
        """
    ret_val = stop_times
    if stop_times and len(stop_times) > 1:
        from gtfsdb.model.block import Block
        keys = cls.get_service_keys_from_list(stop_times)
        blocks = Block.blocks_by_end_stop_id(session, stop_id, service_keys
            =keys)
        if blocks:
            ret_val = []
            for s in stop_times:
                block = None
                for b in blocks:
                    if (s.trip_id == b.trip_id and s.trip.block_id == b.
                        block_id):
                        block = b
                        blocks.remove(b)
                        break
                if block is None:
                    ret_val.append(s)
                elif not block.is_arrival(stop_id):
                    ret_val.append(s)
    return ret_val


@classmethod
def get_xpath_distance(cls, path1, path2):
    """
        Calculate distance between paths.
        Can be used for cost calculation of moved nodes.
        Path seperator has to be /.

        :param path1: source xpath
        :param path2: destination xpath
        """
    _arr1 = path1.split('/')
    _arr2 = path2.split('/')
    while True:
        if _arr1 == [] or _arr2 == []:
            return len(_arr1) + len(_arr2)
        if _arr1[0] == _arr2[0]:
            _arr1 = _arr1[1:]
            _arr2 = _arr2[1:]
        else:
            return len(_arr1) + len(_arr2)


def PandasDataFrametoDF(df):
    """Convert Pandas DataFrame to list of tuples."""
    if df is None:
        raise RuntimeError('PandasDataFrametoDF() empty DataFrame')
    DF = []
    for column in df.columns:
        DF.append((column, df.get(column).tolist()))
    return DF


def list_object_attributes(DirectoryArn=None, ObjectReference=None,
    NextToken=None, MaxResults=None, ConsistencyLevel=None, FacetFilter=None):
    """
    Lists all attributes that are associated with an object.
    See also: AWS API Documentation

    :example: response = client.list_object_attributes(
        DirectoryArn='string',
        ObjectReference={
            'Selector': 'string'
        },
        NextToken='string',
        MaxResults=123,
        ConsistencyLevel='SERIALIZABLE'|'EVENTUAL',
        FacetFilter={
            'SchemaArn': 'string',
            'FacetName': 'string'
        }
    )

    :type DirectoryArn: string
    :param DirectoryArn: [REQUIRED]
            The Amazon Resource Name (ARN) that is associated with the Directory where the object resides. For more information, see arns .

    :type ObjectReference: dict
    :param ObjectReference: [REQUIRED]
            The reference that identifies the object whose attributes will be listed.
            Selector (string) --A path selector supports easy selection of an object by the parent/child links leading to it from the directory root. Use the link names from each parent/child link to construct the path. Path selectors start with a slash (/) and link names are separated by slashes. For more information about paths, see Accessing Objects . You can identify an object in one of the following ways:
            $ObjectIdentifier - An object identifier is an opaque string provided by Amazon Cloud Directory. When creating objects, the system will provide you with the identifier of the created object. An object s identifier is immutable and no two objects will ever share the same object identifier
            /some/path - Identifies the object based on path
            #SomeBatchReference - Identifies the object in a batch call

    :type NextToken: string
    :param NextToken: The pagination token.

    :type MaxResults: integer
    :param MaxResults: The maximum number of items to be retrieved in a single call. This is an approximate number.

    :type ConsistencyLevel: string
    :param ConsistencyLevel: Represents the manner and timing in which the successful write or update of an object is reflected in a subsequent read operation of that same object.

    :type FacetFilter: dict
    :param FacetFilter: Used to filter the list of object attributes that are associated with a certain facet.
            SchemaArn (string) --The ARN of the schema that contains the facet.
            FacetName (string) --The name of the facet.

    :rtype: dict
    :return: {
        'Attributes': [
            {
                'Key': {
                    'SchemaArn': 'string',
                    'FacetName': 'string',
                    'Name': 'string'
                },
                'Value': {
                    'StringValue': 'string',
                    'BinaryValue': b'bytes',
                    'BooleanValue': True|False,
                    'NumberValue': 'string',
                    'DatetimeValue': datetime(2015, 1, 1)
                }
            },
        ],
        'NextToken': 'string'
    }

    """
    pass


def hue(value):
    """Hue of the light. This is a wrapping value between 0 and 65535."""
    value = int(value)
    if value < 0 or value > 65535:
        raise ValueError('Hue is a value between 0 and 65535')
    return value


def calcNeff(FWHMeff, platescale):
    """
    Calculate the effective number of pixels in a single gaussian PSF.
    This equation comes from LSE-40, equation 27.
    https://docushare.lsstcorp.org/docushare/dsweb/ImageStoreViewer/LSE-40
    @param [in] FWHMeff in arcseconds
       (the width of a single-gaussian that produces correct Neff for typical PSF profile)
    @param [in] platescale in arcseconds per pixel
    @param [out] the effective number of pixels contained in the PSF
    The FWHMeff is a way to represent the equivalent seeing value, if the
    atmosphere could be simply represented as a single gaussian (instead of a more
    complicated von Karman profile for the atmosphere, convolved properly with the
    telescope hardware additional blurring of 0.4").
    A translation from the geometric FWHM to the FWHMeff is provided in FWHMgeom2FWHMeff.
    """
    return 2.266 * (FWHMeff / platescale) ** 2


def exno(num, powers=False):
    """exno(...) --> str

	Return the Expanded Notation in a string
	optional argument powers defines the format for place value
	eg. False: 100000  True: 10^5"""
    if powers:
        func = lambda x: x
    else:
        func = lambda x: str(eval(x))
    if num < 0:
        start = '-'
        num = str(float(num)).replace('-', '')
    else:
        start = ''
        num = str(float(num))
    strings = []
    exponent = num.index('.') - 1
    num = num.replace('.', '')
    for n in num:
        if n != '0':
            strings.append(' '.join([start + '(', n, '*', func('10**' + str
                (exponent)), ')']))
        exponent -= 1
    return ' + '.join(strings)


def move_limits_to_user(apps, schema_editor):
    """Move limits from Pool to User."""
    LimitsPool = apps.get_model('limits', 'LimitsPool')
    UserObjectLimit = apps.get_model('limits', 'UserObjectLimit')
    ContentType = apps.get_model('contenttypes', 'ContentType')
    if not ContentType.objects.exists():
        return
    name_to_content_type = {'domains_limit': ContentType.objects.get(
        app_label='admin', model='domain'), 'domain_aliases_limit':
        ContentType.objects.get(app_label='admin', model='domainalias'),
        'mailboxes_limit': ContentType.objects.get(app_label='admin', model
        ='mailbox'), 'mailbox_aliases_limit': ContentType.objects.get(
        app_label='admin', model='alias'), 'domain_admins_limit':
        ContentType.objects.get(app_label='core', model='user')}
    to_create = []
    qset = LimitsPool.objects.select_related('user').prefetch_related(
        'limit_set')
    for pool in qset:
        for limit in pool.limit_set.all():
            objlimit = UserObjectLimit(user=pool.user, max_value=limit.
                maxvalue, name=limit.name.replace('_limit', ''),
                content_type=name_to_content_type[limit.name])
            to_create.append(objlimit)
    UserObjectLimit.objects.bulk_create(to_create)


def list_retirable_grants(Limit=None, Marker=None, RetiringPrincipal=None):
    """
    Returns a list of all grants for which the grant's RetiringPrincipal matches the one specified.
    A typical use is to list all grants that you are able to retire. To retire a grant, use  RetireGrant .
    See also: AWS API Documentation

    Examples
    The following example lists the grants that the specified principal (identity) can retire.
    Expected Output:

    :example: response = client.list_retirable_grants(
        Limit=123,
        Marker='string',
        RetiringPrincipal='string'
    )

    :type Limit: integer
    :param Limit: Use this parameter to specify the maximum number of items to return. When this value is present, AWS KMS does not return more than the specified number of items, but it might return fewer.
            This value is optional. If you include a value, it must be between 1 and 100, inclusive. If you do not include a value, it defaults to 50.

    :type Marker: string
    :param Marker: Use this parameter in a subsequent request after you receive a response with truncated results. Set it to the value of NextMarker from the truncated response you just received.

    :type RetiringPrincipal: string
    :param RetiringPrincipal: [REQUIRED]
            The retiring principal for which to list grants.
            To specify the retiring principal, use the Amazon Resource Name (ARN) of an AWS principal. Valid AWS principals include AWS accounts (root), IAM users, federated users, and assumed role users. For examples of the ARN syntax for specifying a principal, see AWS Identity and Access Management (IAM) in the Example ARNs section of the Amazon Web Services General Reference .

    :rtype: dict
    :return: {
        'Grants': [
            {
                'KeyId': 'string',
                'GrantId': 'string',
                'Name': 'string',
                'CreationDate': datetime(2015, 1, 1),
                'GranteePrincipal': 'string',
                'RetiringPrincipal': 'string',
                'IssuingAccount': 'string',
                'Operations': [
                    'Decrypt'|'Encrypt'|'GenerateDataKey'|'GenerateDataKeyWithoutPlaintext'|'ReEncryptFrom'|'ReEncryptTo'|'CreateGrant'|'RetireGrant'|'DescribeKey',
                ],
                'Constraints': {
                    'EncryptionContextSubset': {
                        'string': 'string'
                    },
                    'EncryptionContextEquals': {
                        'string': 'string'
                    }
                }
            },
        ],
        'NextMarker': 'string',
        'Truncated': True|False
    }

    :returns:
    (string) --

    """
    pass


def Add2(a, b):
    """Return the sum of 2d vectors, a+b."""
    return a[0] + b[0], a[1] + b[1]


def concatenate_version(major, minor, maintenance, extra):
    """ Construct full version string to pass to setup.py """
    _ver = [major, minor]
    if maintenance:
        _ver.append(maintenance)
    if extra:
        _ver.append(extra)
    return '.'.join(map(str, _ver))


def get_class(class_name):
    """Get a class from the class name throuth the 'reflection' property."""
    parts = class_name.split('.')
    module = '.'.join(parts[:-1])
    m = __import__(module)
    for comp in parts[1:]:
        m = getattr(m, comp)
    return m


def record_build_url(video_id):
    """Build video url."""
    return 'https://cds.cern.ch/api/record/{0}'.format(str(video_id))


def quaternion_real(quaternion):
    """Return real part of quaternion.

    >>> quaternion_real([3, 0, 1, 2])
    3.0

    """
    return float(quaternion[0])


def import_node(statement, context):
    """A node that executes the given import expression."""
    exec(statement, context.meta, context.params)


@staticmethod
def concatenate(tensors, axis=0):
    """Concatenate tensors along an axis.

        Parameters
        ----------
        tensors : list of tensor
            The tensors to concatenate. Non-empty tensors provided must have the
            same shape, except along the specified axis.
        axis : int, optional
            The axis to concatenate on. Default is 0.

        Returns
        -------
        tensor
        """
    raise NotImplementedError


@classmethod
def from_points(cls, obj):
    """
        create from points:
        (left,top,right,bottom)
        """
    return cls((obj[0], obj[1], obj[2] - obj[0], obj[3] - obj[1]))


def schedule_in_main_thread(func, *args):
    """Schedules a function to be run in the main thread.
    It will as soon as the mainloop schedules it, normally
    it happens within a few ms.
    """
    from gi.repository import GLib
    GLib.idle_add(func, *args)


def async_extract(user, criteria):
    """
    Given the user and the criteria, let's run an async extract.
    """
    from opal.core.search import tasks
    return tasks.extract.delay(user, criteria).id


def get_legacy_py_generator_body_template():
    """
    In Python 2 we cannot use `yield from` in the generated function body.
    This is a replacement, from PEP380 - see https://www.python.org/dev/peps/pep-0380/#formal-semantics

    note: we removed a few lines so that `StopIteration` exceptions are re-raised
    :return:
    """
    return """def %s
    _i = iter(_func_impl_(%s))    # initialize the generator
    _y = next(_i)                    # first iteration
    while 1:
        try:
            _s = yield _y            # yield the first output and retrieve the new input
        except GeneratorExit as _e:  # ---generator exit error---
            try:
                _m = _i.close        # if there is a close method
            except AttributeError:
                pass
            else:
                _m()                 # use it first
            raise _e                 # then re-raise exception
        except BaseException as _e:  # ---other exception
            _x = sys.exc_info()      # if captured exception, grab info
            try:
                _m = _i.throw        # if there is a throw method
            except AttributeError:
                raise _e             # otherwise re-raise
            else:
                _y = _m(*_x)         # use it
        else:                        # --- nominal case: the new input was received
            # if _s is None:
            #     _y = next(_i)
            # else:
            _y = _i.send(_s)     # let the implementation decide if None means "no new input" or "new input = None\"
"""


@classmethod
def get_shortcutsc(cls, ids=None, return_=False, verb=True, sep='  ', line=
    '-', just='l'):
    """ Display and/or return the builtin shortcuts for imas signal names

        By default (ids=None), only display shortcuts for stored ids
        To display all possible shortcuts, use ids='all'
        To display shortcuts for a specific ids, use ids=<idsname>

        These shortcuts can be customized (with self.set_shortcuts())
        They are useful for use with self.get_data()

        """
    return cls._shortcuts(cls, ids=ids, return_=return_, verb=verb, sep=sep,
        line=line, just=just)


def _np_ones_like(a):
    """
    Return an array of ones with the same shape and type as a given array.

    Parameters
    ----------
    a : ndarray
        The shape and data-type of `a` define these same attributes of
        the returned array.

    Returns
    -------
    out : ndarray
        Array of ones with the same shape and type as `a`.

    Examples
    --------
    >>> x = np.arange(6)
    >>> x = x.reshape((2, 3))
    >>> x
    array([[0., 1., 2.],
           [3., 4., 5.]])
    >>> np.ones_like(x)
    array([[1., 1., 1.],
           [1., 1., 1.]])

    >>> y = np.arange(3, dtype=float)
    >>> y
    array([0., 1., 2.], dtype=float64)
    >>>
    >>> np.ones_like(y)
    array([1., 1., 1.], dtype=float64)
    """
    pass


def to_serialized(ref, the_data):
    """Serialize the property

    Used for the retention store

    :param ref: Not used
    :type ref:
    :param the_data: dictionary to convert
    :type the_data: dict
    :return: serialized data
    :rtype: dict
    """
    if not the_data:
        return {}
    if not getattr(the_data, 'serialize', None):
        return the_data
    return the_data.serialize()


def article_file_path(instance, filename):
    """Returns the path of an associated article file."""
    return 'articles/{0}/{1}'.format(instance.article, filename)


def getid(obj):
    """Get obj's id or object itself if no id
    Abstracts the common pattern of allowing both an object or
    an object's ID as a parameter when dealing with relationships.
    """
    try:
        return obj.id
    except AttributeError:
        return obj


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 spheroid(eta=0):
    """
    Calculate value of spheroidal function used for gridding convolution function at a given value eta

    The rational approximation for this function is presented in F.R. Schwab's "Optimal Gridding of Visibility Data in Radio Interferometry" in Indirect Imaging: Measurement and Processing for Indirect Imaging, 1984
    m=5, alpha = 1

    Parameter
    _________
    eta: float between -1 and 1

    Returns
    _______
    out: float. Value of spheroidal function at eta

    """
    n = eta ** 2 - 1 ** 2
    if abs(eta) < 1.0000000000001:
        return (0.01624782 * pow(n, 6) + -0.05350728 * pow(n, 5) +
            0.1464354 * pow(n, 4) + -0.2347118 * pow(n, 3) + 0.2180684 *
            pow(n, 2) + -0.09858686 * n + 0.01466325) / (0.2177793 * n + 1)
    else:
        return 1e+30


def read_line_chunks(file_object, max_bytes):
    """
    Function that lazily reads file in chunks of lines
    it reads upto max_bytes and then till the end of the existing line
    returns the aray of lines read
    """
    while True:
        data = file_object.readlines(max_bytes)
        if not data:
            break
        yield data


def ensure_join(qs, lm, rm, on=None, **join_kwargs):
    """TODO: remove me when problem in Peewee will be fixed."""
    ctx = qs._query_ctx
    for join in qs._joins.get(lm, []):
        if join.dest is rm:
            return qs
    return qs.switch(lm).join(rm, on=on, **join_kwargs).switch(ctx)


def _check_large_sparse(X, accept_large_sparse=False):
    """Raise a ValueError if X has 64bit indices and accept_large_sparse=False
    """
    if not accept_large_sparse:
        supported_indices = ['int32']
        if X.getformat() == 'coo':
            index_keys = ['col', 'row']
        elif X.getformat() in ['csr', 'csc', 'bsr']:
            index_keys = ['indices', 'indptr']
        else:
            return
        for key in index_keys:
            indices_datatype = getattr(X, key).dtype
            if indices_datatype not in supported_indices:
                raise ValueError(
                    'Only sparse matrices with 32-bit integer indices are accepted. Got %s indices.'
                     % indices_datatype)


def last_index_of(array, value, from_index=None):
    """Gets the index at which the last occurrence of value is found.

    Args:
        array (list): List to search.
        value (mixed): Value to search for.
        from_index (int, optional): Index to search from.

    Returns:
        int: Index of found item or ``False`` if not found.

    Example:

        >>> last_index_of([1, 2, 2, 4], 2)
        2
        >>> last_index_of([1, 2, 2, 4], 2, from_index=1)
        1

    .. versionadded:: 1.0.0
    """
    index = array_len = len(array)
    try:
        from_index = int(from_index)
    except (TypeError, ValueError):
        pass
    else:
        index = max(0, index + from_index) if from_index < 0 else min(
            from_index, index - 1)
    while index:
        if index < array_len and array[index] == value:
            return index
        index -= 1
    return -1


@staticmethod
def p_env_var_aname(p):
    """env_var_aname : IDENT"""
    p[0] = p[1]


def __getModelClasses():
    """Import all classes not leaking any additional declarations"""
    import pkgutil
    from importlib import import_module
    from . import model
    package = '.'.join(model.__name__.split('.')[:-1])
    for mdata in pkgutil.iter_modules(model.__path__):
        mod = import_module('.'.join([package, 'model', mdata[1]]))
        globals()[mdata[1]] = getattr(mod, mdata[1])
    del globals()['__getModelClasses']


@classmethod
def get_rosh_hashanah(cls, year):
    """
        Return the gregorian date of the first day of Rosh Hashanah
        """
    return cls.search_hebrew_calendar(year, 7, 1)


def _check_unique_id(base, tag, id):
    """Find all child elements with a given group and check if the id is already used.

    Args:
        base: The base node element. (lxml node)
        tag: Child elements group tag used to select the elements. (string)
        id: The unique id to search for. (string)

    Returns:
        False if the id is already used, True if not.
    """
    for node in base:
        if node.tag.replace('{http://www.rdml.org}', '') == tag:
            if node.get('id') == id:
                return False
    return True


@classmethod
def check_all(cls, tools=True, encoding=True, c_ext=True):
    """
        Perform all checks.

        Return a tuple of booleans ``(errors, warnings, c_ext_warnings)``.

        :param bool tools: if ``True``, check aeneas tools
        :param bool encoding: if ``True``, check shell encoding
        :param bool c_ext: if ``True``, check Python C extensions
        :rtype: (bool, bool, bool)
        """
    if cls.check_ffprobe():
        return True, False, False
    if cls.check_ffmpeg():
        return True, False, False
    if cls.check_espeak():
        return True, False, False
    if tools and cls.check_tools():
        return True, False, False
    warnings = False
    c_ext_warnings = False
    if encoding:
        warnings = cls.check_shell_encoding()
    if c_ext:
        c_ext_warnings = cls.check_cdtw() or c_ext_warnings
        c_ext_warnings = cls.check_cmfcc() or c_ext_warnings
        c_ext_warnings = cls.check_cew() or c_ext_warnings
    return False, warnings, c_ext_warnings


def parse_out_sequence_file(sample):
    """
    Removes keys in argument sample that are not in sample_keys and
        stores them in sequence_file_dict

    arguments:
            sample -- Sample object
            the dictionary inside the Sample object is changed

    returns a dictionary containing keys not in sample_keys to be used to
        create a SequenceFile object
    """
    sample_keys = ['sampleName', 'description', 'sequencerSampleId',
        'sampleProject']
    sequence_file_dict = {}
    sample_dict = sample.get_dict()
    for key in sample_dict.keys()[:]:
        if key not in sample_keys:
            sequence_file_dict[key] = sample_dict[key]
            del sample_dict[key]
    return sequence_file_dict


@classmethod
def model_exists(cls, model_path):
    """
        Returns whether a trained model of this name or path exists.
        If `model_path` is the path to an existing directory, this
        directory is checked.
        Otherwise, a model by that name is searched for in the repository's
        `models` directory.
        """
    _, directory = cls._resolve_model(model_path)
    return directory.is_dir()


def render_git_describe_long(pieces):
    """TAG-DISTANCE-gHEX[-dirty].

    Like 'git describe --tags --dirty --always -long'.
    The distance/hash is unconditional.

    Exceptions:
    1: no tags. HEX[-dirty]  (note: no 'g' prefix)
    """
    if pieces['closest-tag']:
        rendered = pieces['closest-tag']
        rendered += '-%d-g%s' % (pieces['distance'], pieces['short'])
    else:
        rendered = pieces['short']
    if pieces['dirty']:
        rendered += '-dirty'
    return rendered


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

        :param SharedContentRestoreMemberType val:
        :rtype: EventType
        """
    return cls('shared_content_restore_member', val)


@staticmethod
def set_protocol(url, use_tls):
    """
        Sets the protocol of the `url` according to the `use_tls`-flag
        and returns the modified `url`. Does not check whether the `url`
        given as parameter is correct.
        """
    http = 'http://'
    https = 'https://'
    if url.startswith(http):
        url = url[len(http):]
    elif url.startswith(https):
        url = url[len(https):]
    if use_tls:
        url = f'{https}{url}'
    else:
        url = f'{http}{url}'
    return url


def exit(zelf):
    """ shutdown the UDP server. """
    zelf._status = ''
    zelf._sock.settimeout(0.01)
    zelf._sock.sendto(bytes('bla', 'utf-8'), (zelf.cfg.host, zelf.cfg.port))


@staticmethod
def extract_feature_importance(columns, model):
    """ Extract a sorted list of feature importances from an XGBoost model

            :param columns: Columns names in the same order than the input
            dataset.
            :param model: A trained model containing feature importances list
            and trained trees.

        """
    importances = list(zip(columns, model.feature_importances_))
    importances.sort(key=lambda x: x[1], reverse=True)
    return importances


def last_arg_byref(args):
    """Return the last C argument's value by reference."""
    return args[-1]._obj.value


def partition_string(s, segments):
    """
    Partition a string into a number of segments. If the given number of
    segments does not divide evenly into the string's length, extra characters
    are added to the leading segments in order to allow for the requested number
    of segments.

    This is useful when partitioning the checksum of a file to determine where
    it should be placed in a directory tree system.

    >>> partition_string("foobar", 2)
    ['foo', 'bar']
    >>> partition_string("foobar", 4)
    ['fo', 'ob', 'a', 'r']
    >>> partition_string("foobar", 6)
    ['f', 'o', 'o', 'b', 'a', 'r']

    If the string is not evenly divisible by the requested number of segments,
    then the length of trailing segments will be shorter than leading segments.

    >>> partition_string('d7ca25c5-b886-4a1b-87fe-5945313d350b', 11)
    ['d7ca', '25c5', '-b88', '6-4', 'a1b', '-87', 'fe-', '594', '531', '3d3',
     '50b']
    >>> partition_string('abcde', 2)
    ['abc', 'de']
    >>> partition_string('abcde', 4)
    ['ab', 'c', 'd', 'e']

    If the number of segments is greater than the number of characters in the
    input string, an assertion error is raised.

    >>> partition_string('a', 2)
    Traceback (most recent call last):
        ...
    AssertionError: Cannot split given string into more segments than there are
    characters in the string!

    :raises AssertionError: Segmentation value greater than the length of the
        string.

    :param s: String to partition.
    :type s: str

    :param segments: Number of segments to split the string into
    :type segments: int

    :return: A list of N segments. If the given number of segments does not
        divide evenly into the string's length, this function behaves
        erratically.
    :rtype: list[str]

    """
    assert segments <= len(s
        ), 'Cannot split given string into more segments than there are characters in the string!'
    seg_len = len(s) // segments
    extra_iters = len(s) % segments
    r = []
    i = 0
    for k in range(segments):
        j = i + seg_len + (k < extra_iters)
        r.append(s[i:j])
        i = j
    return r


def search_menu():
    """Pop-up a search menu over all available operators in current context

    """
    pass


def fetch_bases(samFile, chrom, POS, cell_tag='CR', UMI_tag='UR', min_MAPQ=
    20, max_FLAG=255, min_LEN=30):
    """ Fetch bases from all reads mapped to a given genome position.
    Filtering is also applied, including cell and UMI tags and read mapping
    quality.
    """
    base_list, qual_list, UMIs_list, cell_list = [], [], [], []
    if samFile is None or chrom is None or POS is None:
        if samFile is None:
            print('Warning: samFile is None')
        if chrom is None:
            print('Warning: chrom is None')
        if POS is None:
            print('Warning: POS is None')
        return base_list, qual_list, UMIs_list, cell_list
    if type(POS) != int:
        POS = int(POS)
    for _read in samFile.fetch(chrom, POS - 1, POS):
        try:
            idx = _read.positions.index(POS - 1)
        except:
            continue
        if _read.mapq < min_MAPQ or _read.flag > max_FLAG or len(_read.
            positions) < min_LEN:
            continue
        if cell_tag is not None and _read.has_tag(cell_tag) == False:
            continue
        if UMI_tag is not None and _read.has_tag(UMI_tag) == False:
            continue
        if UMI_tag is not None:
            UMIs_list.append(_read.get_tag(UMI_tag))
        if cell_tag is not None:
            cell_list.append(_read.get_tag(cell_tag))
        _base = _read.query_alignment_sequence[idx].upper()
        base_list.append(_base)
        qual_list.append(_read.qqual[idx])
    return base_list, qual_list, UMIs_list, cell_list


def create_choice(klass, choices, subsets, kwargs):
    """Create an instance of a ``Choices`` object.

    Parameters
    ----------
    klass : type
        The class to use to recreate the object.
    choices : list(tuple)
        A list of choices as expected by the ``__init__`` method of ``klass``.
    subsets : list(tuple)
        A tuple with an entry for each subset to create. Each entry is a list with two entries:
        - the name of the subsets
        - a list of the constants to use for this subset
    kwargs : dict
        Extra parameters expected on the ``__init__`` method of ``klass``.

    Returns
    -------
    Choices
        A new instance of ``Choices`` (or other class defined in ``klass``).

    """
    obj = klass(*choices, **kwargs)
    for subset in subsets:
        obj.add_subset(*subset)
    return obj


def convert_dateranges(kwargs):
    """Creates the DateRange object from the parameters dictionary.

  Args:
    kwargs: a dict containing the parameters passed in the request.
  Returns:
    A list containing a DateRange object.
  """
    date_range = {'startDate': kwargs.get('start_date', None), 'endDate':
        kwargs.get('end_date', None)}
    return [date_range]


def atse_getDefaultSchemaId():
    """ returns default schema id """


@classmethod
def cache_key(cls, model_metadata):
    """This key is used to cache components.

        If a component is unique to a model it should return None. Otherwise, an instantiation of the
        component will be reused for all models where the metadata creates the same key."""
    from rasa_nlu.model import Metadata
    return None


def is_valid_selection(ext):
    """ Checks if selection is correct """
    formats = ['System', 'Protein', 'Protein-H', 'C-alpha', 'Backbone',
        'MainChain', 'MainChain+Cb', 'MainChain+H', 'SideChain',
        'SideChain-H', 'Prot-Masses', 'non-Protein', 'Water', 'SOL',
        'non-Water', 'Ion', 'NA', 'CL', 'Water_and_ions']
    return ext in formats


def kget(container, *keys):
    """Get a value from a container trying multiples keys in order."""
    for key in keys:
        if key in container:
            return container[key]


def max_response_from_str(src):
    """A simple restriction of integer:

    <xs:simpleType name="MaxResponse">
            <xs:restriction base="xs:integer">
                    <xs:maxInclusive value="32767"/>
                    <xs:minInclusive value="1"/>
            </xs:restriction>
    </xs:simpleType>"""
    value = int(src)
    if value < 1 or value > 32767:
        raise ValueError('Value exceeds bounds for MaxResponse: %i' % value)
    return value


def _get_mask(start, end):
    """Make default mask.

    :type start: int
    :type end:  int
    :rtype: int
    """
    return (1 << end) - (1 << start)


def query_backend(criteria):
    """
		Given a dictionary of criteria, perform a query in the search backend
		and return a list of dicts with the results. Backends should ignore any
		criteria it does not know how to deal with.

		Returns a tuple of (total result count, list of results).  Each results
		is a dict with keys: title, score, source, summary, date, author.
		When multiple providers return results for a source score is used to
		order the results.

		Example:
		criteria = {
			'q': 'trac help',
			'author: ['admin', 'joe'],
			'source': ['wiki'],
			'date_start': '2011-04-01',
			'date_end': '2011-04-30',
		}

		return (
			200,
			[
				{
					'title': 'TracHelp',
					'score': 0.876,
					'source': 'wiki',
					'summary': '==Trac Help== ....'
					'date': '2011-02-34 23:34',
					'author': 'admin',
				},
				...
			]
		)
		"""


@staticmethod
def load_image(filename_or_data):
    """
        Given a filename, load an image. If the data is already loaded, return it.

        :param filename_or_data: The input filename (or data)
        :return: The image or None

        """
    import six.moves.cPickle as pickle
    if not filename_or_data:
        return None
    if isinstance(filename_or_data, tuple):
        return filename_or_data
    with open(filename_or_data, 'rb') as fh:
        image = pickle.load(fh)
    if not isinstance(image, tuple):
        image = image,
    return image


def calculate_cumulative_co2_v1(phases_co2_emissions, phases_distances):
    """
    Calculates cumulative CO2 of cycle phases [CO2g].

    :param phases_co2_emissions:
        CO2 emission of cycle phases [CO2g/km].
    :type phases_co2_emissions: numpy.array

    :param phases_distances:
        Cycle phases distances [km].
    :type phases_distances: numpy.array

    :return:
        Cumulative CO2 of cycle phases [CO2g].
    :rtype: numpy.array
    """
    return phases_co2_emissions * phases_distances


def correct_trend(trend):
    """Correct a indicator based trend model for closure (probabilities sum to 1.0).
    :param trend: ndarray [ny,nx,ncut]
    :return: nadarray [ny,nx,ncut] corrected for closure
    """
    ny = trend.shape[0]
    nx = trend.shape[1]
    ncut = trend.shape[2]
    for iy in range(0, ny):
        for ix in range(0, nx):
            sum = 0.0
            for ic in range(0, ncut):
                sum = sum + trend[iy, ix, ic]
            if sum > 0.0:
                for icut in range(0, ncut):
                    trend[iy, ix, ic] = trend[iy, ix, ic] / sum
    return trend


def minify_html(html):
    """Perform a template-specific, rudimentary HTML minification for displaCy.
    Disclaimer: NOT a general-purpose solution, only removes indentation and
    newlines.

    html (unicode): Markup to minify.
    RETURNS (unicode): "Minified" HTML.
    """
    return html.strip().replace('    ', '').replace('\n', '')


@staticmethod
def escape(s):
    """
        Double { and } characters in a string to 'escape' them so ``str.format``
        doesn't treat them as template characters. NB This is NOT idempotent!
        Escaping more than once (when { or } are present ) = ERROR.
        """
    return s.replace('{', '{{').replace('}', '}}')


def maybe_unwrap_results(results):
    """
    Gets raw results back from wrapped results.

    Can be used in plotting functions or other post-estimation type
    routines.
    """
    return getattr(results, '_results', results)


def titulo(conteudo='', tam=1, classe='', iDentificador=''):
    """Retorna um titulo para o codigo que o chamou"""
    return "<h%d class='%s' id='%s'>%s</h%d>" % (tam, str(classe), str(
        iDentificador), str(conteudo), tam)


def print0(s):
    """Print the statement at any verbosity level"""
    print(s)


def read_param(F):
    """
    Reads the sampling parameters. used by sampling_load()
    """
    """
        given F, an opend file , retrieve all parameters found in file header
        read_param returns  values in a plain dictionnary
    """
    dic = {}
    for l in F:
        if not l.startswith('#'):
            break
        v = l.rstrip().split(':')
        if len(v) < 2:
            pass
        else:
            entry = v[0][1:].strip()
            dic[entry] = v[1].lstrip()
    return dic


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 utcnow(cls):
    """[!91sgk] (disabled)"""
    raise TypeError("UTCDateTime: 'utcnow()' is disabled. Use 'now()' instead."
        )


def __check_number(items):
    """Checks a list of strings whether items are valid numbers.

    Args:
        items (list of [str,]): The list of items to test.

    Returns:
        list of [float,]: The list of items converted to floats. Returns None
            if any one test fails.
    """
    for i, item in enumerate(items):
        try:
            items[i] = float(item)
        except ValueError:
            print('Failed on item: "{}"'.format(item))
            return None
    return items


def mpi_rank_or_zero():
    """
    Return the MPI rank if mpi is installed. Otherwise, return 0.
    :return: (int)
    """
    try:
        import mpi4py
        return mpi4py.MPI.COMM_WORLD.Get_rank()
    except ImportError:
        return 0


def __new__(cls, major, minor=0, micro=0, modifier='release'):
    """
        Create new instance of `VersionInfo(major, minor, micro, modifier)`.
        """
    assert isinstance(major, int)
    assert isinstance(minor, int)
    assert isinstance(micro, int)
    assert isinstance(modifier, str)
    return tuple.__new__(cls, (major, minor, micro, modifier))


def render_git_describe(pieces):
    """TAG[-DISTANCE-gHEX][-dirty].

    Like 'git describe --tags --dirty --always'.

    Exceptions:
    1: no tags. HEX[-dirty]  (note: no 'g' prefix)
    """
    if pieces['closest-tag']:
        rendered = pieces['closest-tag']
        if pieces['distance']:
            rendered += '-%d-g%s' % (pieces['distance'], pieces['short'])
    else:
        rendered = pieces['short']
    if pieces['dirty']:
        rendered += '-dirty'
    return rendered


def regroup_dims(point, space):
    """Take a list of items representing a point and regroup them appropriately as
    a point from `space`.

    Parameters
    ----------
    point: array
        Points to be regrouped.
    space: `orion.algo.space.Space`
        The optimization space.

    Returns
    -------
    list or tuple

    """
    regrouped = []
    idx = 0
    for dimension in space.values():
        shape = dimension.shape
        if shape:
            assert len(shape) == 1
            next_dim = idx + shape[0]
            regrouped.append(tuple(point[idx:next_dim]))
            idx = next_dim
        else:
            regrouped.append(point[idx])
            idx += 1
    if regrouped not in space:
        raise AttributeError('The point {} is not a valid point of space {}'
            .format(point, space))
    return regrouped


def make_location_header(request, pk):
    """Make the Location header for the newly-created resource.

    :param request: the POST request object.
    :param pk: the primary key of the resource.
    """
    return '%s/%s' % (request.uri.rstrip('/'), pk)


def enable_remote_registration():
    """Enable remote registration service

    WARNING: Remote command registration allows to deploy arbitrary python code on LiQuer server,
    therefore it is a HUGE SECURITY RISK and it only should be used if other security measures are taken
    (e.g. on localhost or intranet where only trusted users have access).
    This is on by default on Jupyter server extension.
    """
    global _remote_registration
    _remote_registration = True


def set_procname(newname):
    """Change a process name"""
    from ctypes import cdll, byref, create_string_buffer
    libc = cdll.LoadLibrary('libc.so.6')
    buff = create_string_buffer(len(newname) + 1)
    buff.value = newname
    libc.prctl(15, byref(buff), 0, 0, 0)


def fileheader2dic(header):
    """
    Convert a fileheader list into a Sparky parameter dictionary.
    """
    dic = dict()
    dic['ident'] = str(header[0].decode()).strip('\x00')
    dic['naxis'] = ord(header[1].decode())
    dic['ncomponents'] = ord(header[2].decode())
    dic['encoding'] = ord(header[3].decode())
    dic['version'] = ord(header[4].decode())
    dic['owner'] = str(header[5].decode()).strip('\x00')
    dic['date'] = str(header[6].decode()).strip('\x00')
    dic['comment'] = str(header[7].decode()).strip('\x00')
    dic['seek_pos'] = header[8]
    dic['scratch'] = str(header[9].decode()).strip('\x00')
    return dic


@classmethod
def normalize_email(cls, email):
    """
        Normalize the email address by lowercasing the domain part of the it.
        """
    email = email or ''
    try:
        email_name, domain_part = email.strip().rsplit('@', 1)
    except ValueError:
        pass
    else:
        email = '@'.join([email_name, domain_part.lower()])
    return email


@classmethod
def from_color(cls, color):
    """
        Gets a string formateed color from a QColor
        :param color: QColor, color to parse
        :return: (str)
        """
    color = 'rgb(%d, %d, %d, %d)' % color.getRgb()
    return cls.from_string(color)


@classmethod
def clear_expired(cls):
    """
        Remove expired sessions from the session store.

        If this operation isn't possible on a given backend, it should raise
        NotImplementedError. If it isn't necessary, because the backend has
        a built-in expiration mechanism, it should be a no-op.
        """
    raise NotImplementedError('This backend does not support clear_expired().')


def theta_Cl_H2PO4_HFM89(T, P):
    """a-a': chloride dihydrogen-phosphate [HFM89]."""
    theta = 0.1
    valid = T == 298.15
    return theta, valid


@staticmethod
def clean_plot(plc):
    """
        Scrub the plot for any lines and text.
        """
    while len(plc.axes.lines) > 0:
        plc.axes.lines.pop(0)
    while len(plc.axes.texts) > 0:
        plc.axes.texts.pop(0)


@classmethod
def to_string(cls, u):
    """
        Convert a unit object to a string.
        """
    raise NotImplementedError(f'Can not output in {cls.__name__} format')


def findRootsWithPredicate(c, root, predicate=None):
    """
    Commands often want to find one or more **roots**, given a position p.
    A root is the position of any node matching a predicate.

    This function formalizes the search order used by the black,
    pylint, pyflakes and the rst3 commands, returning a list of zero
    or more found roots.
    """
    seen = []
    roots = []
    if predicate is None:

        def predicate(p):
            return p.isAnyAtFileNode() and p.h.strip().endswith('.py')
    for p in root.self_and_subtree(copy=False):
        if predicate(p) and p.v not in seen:
            seen.append(p.v)
            roots.append(p.copy())
    if roots:
        return roots
    for p in root.parents():
        if predicate(p):
            return [p.copy()]
    clones = []
    for p in root.self_and_parents(copy=False):
        if p.isCloned():
            clones.append(p.v)
    if clones:
        for p in c.all_positions(copy=False):
            if predicate(p):
                for p2 in p.self_and_subtree():
                    if p2.v in clones:
                        return [p.copy()]
    return []


def get_supported_dcv_partition():
    """Return a list of all the partition supported by DCV."""
    return ['aws']


def strip_transient(nb):
    """Strip transient values that shouldn't be stored in files.

    This should be called in *both* read and write.
    """
    nb.pop('orig_nbformat', None)
    nb.pop('orig_nbformat_minor', None)
    for ws in nb['worksheets']:
        for cell in ws['cells']:
            cell.get('metadata', {}).pop('trusted', None)
            cell.pop('trusted', None)
    return nb


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 '+'


@staticmethod
def __isNumeric(arr):
    """Checks if an array is of a numeric type"""
    try:
        return arr.dtype.kind in 'biufc'
    except AttributeError:
        return False


def _show_opt(term, keys):
    """ Display characters ``key`` highlighted as keystroke """
    return u''.join((term.bold_black(u'['), term.bold_green_underline(keys),
        term.bold_black(u']')))


def grams(kilograms, format_spec=''):
    """Convert kilograms to grams, return a string with the unit appended."""
    return ('{:' + format_spec + '} g').format(kilograms * 1000.0)


@staticmethod
def LoopHasKey(loop, key):
    """Returns True if the key (string) exist in the array called loop"""
    try:
        loop.index(key)
        return True
    except ValueError:
        return False


@staticmethod
def write_sorted_long(buf, offset, value):
    """
        Writes a packed sorted long integer starting at the given buffer offset
        and returns the next offset to be written.

        :param buf: the buffer to write to.
        :type buf: bytearray
        :param offset: the offset in the buffer at which to start writing.
        :type offset: int
        :param value: the long integer to be written.
        :type value: int for python 3 and long for python 2
        :returns: the offset past the bytes written.
        :rtype: int

        Values in the inclusive range [-119,120] are stored in a single byte.
        For values outside that range, the first byte stores the number of
        additional bytes. The additional bytes store (value + 119 for negative
        and value - 121 for positive) as an unsigned big endian integer.
        """
    b1 = offset
    offset += 1
    if value < -119:
        """
            If the value < -119, then first adjust the value by adding 119. Then
            the adjusted value is stored as an unsigned big endian integer.
            """
        value += 119
        """
            Store the adjusted value as an unsigned big endian integer. For an
            negative integer, from left to right, the first significant byte is
            the byte which is not equal to 0xFF. Also please note that, because
            the adjusted value is stored in big endian integer, we extract the
            significant byte from left to right.

            In the left to right order, if the first byte of the adjusted value
            is a significant byte, it will be stored in the 2nd byte of the buf.
            Then we will look at the 2nd byte of the adjusted value to see if
            this byte is the significant byte, if yes, this byte will be stored
            in the 3rd byte of the buf, and the like.
            """
        if value | 72057594037927935 != 18446744073709551615:
            buf[offset] = value >> 56 & 255
            offset += 1
        if value | 281474976710655 != 18446744073709551615:
            buf[offset] = value >> 48 & 255
            offset += 1
        if value | 1099511627775 != 18446744073709551615:
            buf[offset] = value >> 40 & 255
            offset += 1
        if value | 4294967295 != 18446744073709551615:
            buf[offset] = value >> 32 & 255
            offset += 1
        if value | 16777215 != 18446744073709551615:
            buf[offset] = value >> 24 & 255
            offset += 1
        if value | 65535 != 18446744073709551615:
            buf[offset] = value >> 16 & 255
            offset += 1
        if value | 255 != 18446744073709551615:
            buf[offset] = value >> 8 & 255
            offset += 1
        buf[offset] = value & 255
        offset += 1
        """
            value_len is the length of the value part stored in buf. Because the
            first byte of buf is used to stored the length, so we need to minus
            one.
            """
        value_len = offset - b1 - 1
        """
            The first byte stores the number of additional bytes. Here we store
            the result of 0x08 - value_len, rather than directly store
            value_len. The reason is to implement nature sort order for
            byte-by-byte comparison.
            """
        buf[b1] = 8 - value_len & 255
    elif value > 120:
        """
            If the value > 120, then first adjust the value by subtracting 119.
            Then the adjusted value is stored as an unsigned big endian integer.
            """
        value -= 121
        """
            Store the adjusted value as an unsigned big endian integer. For a
            positive integer, from left to right, the first significant byte is
            the byte which is not equal to 0x00.

            In the left to right order, if the first byte of the adjusted value
            is a significant byte, it will be stored in the 2nd byte of the buf.
            Then we will look at the 2nd byte of the adjusted value to see if
            this byte is the significant byte, if yes, this byte will be stored
            in the 3rd byte of the buf, and the like.
            """
        if value & 18374686479671623680 != 0:
            buf[offset] = value >> 56 & 255
            offset += 1
        if value & 18446462598732840960 != 0:
            buf[offset] = value >> 48 & 255
            offset += 1
        if value & 18446742974197923840 != 0:
            buf[offset] = value >> 40 & 255
            offset += 1
        if value & 18446744069414584320 != 0:
            buf[offset] = value >> 32 & 255
            offset += 1
        if value & 18446744073692774400 != 0:
            buf[offset] = value >> 24 & 255
            offset += 1
        if value & 18446744073709486080 != 0:
            buf[offset] = value >> 16 & 255
            offset += 1
        if value & 18446744073709551360 != 0:
            buf[offset] = value >> 8 & 255
            offset += 1
        buf[offset] = value & 255
        offset += 1
        """
            value_en is the length of the value part stored in buf. Because the
            first byte of buf is used to stored the length, so we need to minus
            one.
            """
        value_len = offset - b1 - 1
        """
            The first byte stores the number of additional bytes. Here we store
            the result of 0xF7 + value_len, rather than directly store
            value_len. The reason is to implement nature sort order for
            byte-by-byte comparison.
            """
        buf[b1] = 247 + value_len & 255
    else:
        """
            If -119 <= value <= 120, only one byte is needed to store the value.
            The stored value is the original value adds 127.
            """
        buf[b1] = value + 127 & 255
    return offset


def pytest_html_report_title(report):
    """ Called before adding the title to the report """


def determine_overall_grade():
    """Just submitting: 1
        points assigned by reviewer: 1 , 2, 3
        points for just doing review: 1
        points for quality of review (assigned by submitter): 1, 2
        points for reviewing reviewer: 1
    """
    submission = {'automatic': 1}
    reviewing = {'automatic': 1}
    review_review = {'automatic': 1}


def opsite(siteli, tsl=0):
    """
    open a list of websites.
    siteli must be a list, each element of which is one of the websites that you want to open in one single web browser.
    """
    import time
    import numpy as np
    from selenium import webdriver
    osite = webdriver.Chrome()
    n = 1
    for i in siteli:
        osite.get(i)
        time.sleep(tsl * np.random.rand() + 0.002)
        osite.execute_script('window.open()')
        handles = osite.window_handles
        osite.switch_to.window(handles[n])
        n += 1
    osite.close()
    osite.switch_to.window(handles[0])


@classmethod
def dict_objid_to_str(cls, data):
    """ obj(_id) => str(_id)
        """
    try:
        data['_id'] = str(data['_id'])
    except Exception:
        pass
    return data


def ex(fsm, phi):
    """
    Return the set of states of fsm satisfying EX phi.

    fsm -- a MAS representing the system
    phi -- a BDD representing the set of states of fsm satisfying phi
    """
    return fsm.pre(phi)


def assert_path(dist, attr, value):
    """Assert attribute describes a valid path.

       Various keyword variables, in calls to ``setuptools.setup``, allow the specification
       of paths where other qmesh packages should look for resources, such as third-party
       packages. This function asserts the value of such keywords is a string describing a
       valid path.

       Args:
           dist (setuptools.Distribution): The ``Distribution`` instance of ``setuptools``,
               orchestrating the installation or packaging procedure.
           attr (str): The name of the attribute, specified as a keyword argument in
               ``setuptools.setup`` calls.
           value (str): The value of the attribute (keyword), which should be a gmsh path.
       Raises:
           DistutilsSetupError: If the keyword value is not a valid path.
    """
    from os import path
    from setuptools import distutils
    if not path.exists(value):
        msg = '%r must be a path (%r is not a path)' % (attr, value)
        dist.announce(msg, distutils.log.FATAL)
        raise distutils.errors.DistutilsSetupError(msg)


def meta_toggle():
    """Toggle a metastrip (to edit enclosed strips)

    """
    pass


def ExpMag(x: float, params):
    """Compute surface brightness for a profile consisting of an exponential,
    given input parameters in vector params:
        params[0] = mu_0
        params[1] = h
    """
    mu_0 = params[0]
    h = params[1]
    return mu_0 + 1.085736 * (x / h)


def convert_matrix_to_image(m, shape):
    """Convert a column matrix of pixels to a 3D image given by shape.
    The number of channels is taken from m, not shape.  If shape has
    length 2, the matrix is returned unchanged.  This is the inverse
    of convert_image_to_matrix:

    im == convert_matrix_to_image(convert_image_to_matrix(im),
    im.shape)

    """
    if len(shape) == 2:
        return m
    return m.T.reshape(shape[:-1] + (m.shape[0],))


def delete(requestor, service, nodeIdentifier):
    """
        Called when a node deletion request has been received.

        @param requestor: The entity the request originated from.
        @type requestor: L{JID<twisted.words.protocols.jabber.jid.JID>}
        @param service: The entity the request was addressed to.
        @type service: L{JID<twisted.words.protocols.jabber.jid.JID>}
        @param nodeIdentifier: The identifier of the node to be delete.
        @type nodeIdentifier: C{unicode}
        """


def usage():
    """ print usage info """
    print('usage: mnnconvert [-h]')
    print('    [--framework {TF,CAFFE,ONNX,TFLITE,MNN}')
    print('    [--modelFile MODELFILE]')
    print('    [--prototxt PROTOTXT]')
    print('    [--MNNModel MNNMODEL]')
    print('    [--fp16 {True,False}]')


@classmethod
def createFromPair(cls, pair, n):
    """
        Given "pair"=[t,s], return the corresponding canonical factor.

        The list [t,s] should denote the generator a_{ts}.
        If a negative generator a^{-1} is represented,
            then return the permutation corresponding to Da^{-1}.

        >>> CanonicalFactor.createFromPair([5, 2], 7)
        CanonicalFactor([0, 4, 2, 3, 1, 5, 6])
        >>> CanonicalFactor.createFromPair([2, 5], 7)
        CanonicalFactor([6, 3, 1, 2, 0, 4, 5])

        """
    if pair[0] > pair[1]:
        lst = list(range(0, n))
        lst[pair[0] - 1] = pair[1] - 1
        lst[pair[1] - 1] = pair[0] - 1
    elif pair[0] < pair[1]:
        lst = [n - 1] + list(range(0, n - 1))
        lst[pair[0] - 1] = (pair[1] - 2) % n
        lst[pair[1] - 1] = (pair[0] - 2) % n
    else:
        lst = list(range(0, n))
    return cls(lst, size=n)


@classmethod
def from_files(cls, A_file, B_file, C_file, D_file=None, E_file=None,
    cont_time=True, state_id='STATE', solver_options=None, estimator=None,
    visualizer=None, cache_region='memory', name=None):
    """Create |LTIModel| from matrices stored in separate files.

        Parameters
        ----------
        A_file
            The name of the file (with extension) containing A.
        B_file
            The name of the file (with extension) containing B.
        C_file
            The name of the file (with extension) containing C.
        D_file
            `None` or the name of the file (with extension) containing D.
        E_file
            `None` or the name of the file (with extension) containing E.
        cont_time
            `True` if the system is continuous-time, otherwise `False`.
        state_id
            Id of the state space.
        solver_options
            The solver options to use to solve the Lyapunov equations.
        estimator
            An error estimator for the problem. This can be any object with an
            `estimate(U, mu, model)` method. If `estimator` is not `None`, an `estimate(U, mu)`
            method is added to the model which will call `estimator.estimate(U, mu, self)`.
        visualizer
            A visualizer for the problem. This can be any object with a `visualize(U, model, ...)`
            method. If `visualizer` is not `None`, a `visualize(U, *args, **kwargs)` method is added
            to the model which forwards its arguments to the visualizer's `visualize` method.
        cache_region
            `None` or name of the cache region to use. See :mod:`pymor.core.cache`.
        name
            Name of the system.

        Returns
        -------
        lti
            The |LTIModel| with operators A, B, C, D, and E.
        """
    from pymor.tools.io import load_matrix
    A = load_matrix(A_file)
    B = load_matrix(B_file)
    C = load_matrix(C_file)
    D = load_matrix(D_file) if D_file is not None else None
    E = load_matrix(E_file) if E_file is not None else None
    return cls.from_matrices(A, B, C, D, E, cont_time=cont_time, state_id=
        state_id, solver_options=solver_options, estimator=estimator,
        visualizer=visualizer, cache_region=cache_region, name=name)


@classmethod
def notification_payload(cls, method, params=None):
    """JSON v1  notification payload.  Params and id are mandatory."""
    return {'method': method, 'params': params or [], 'id': None}


def escape_markdown(text: str):
    """
    return text escaped given entity types
    :param text: text to escape
    :param entity_type: entities to escape
    :return:
    """
    return text.replace('\\*', '*').replace('\\`', '`').replace('\\_', '_'
        ).replace('\\~', '~').replace('\\>', '>').replace('\\[', '[').replace(
        '\\]', ']').replace('\\(', '(').replace('\\)', ')').replace('*', '\\*'
        ).replace('`', '\\`').replace('_', '\\_').replace('~', '\\~').replace(
        '>', '\\>').replace('[', '\\[').replace(']', '\\]').replace('(', '\\('
        ).replace(')', '\\)')


def clamp(x, lb, ub):
    """Return the value of ``x`` clamped to the range ``[lb, ub]``."""
    return min(max(x, lb), ub)


@staticmethod
def p_daq_list_can_id_optional(p):
    """daq_list_can_id_optional : daq_list_can_id_type_variable
                                    | daq_list_can_id_type_fixed"""
    p[0] = p.slice[1].type, p[1]


def get_headers(referer):
    """Returns the headers needed for the transfer request."""
    return {'Content-Type': 'application/json; charset=UTF-8',
        'X-Requested-With': 'XMLHttpRequest', 'Referer': referer}


@classmethod
def list(cls):
    """ Return the ordered bloks

        :rtype: list of blok name ordered by loading
        """
    return cls.ordered_bloks


def is_unibipartite(graph):
    """Internal function that returns whether the given graph is a uni-directional
    bipartite graph.

    Parameters
    ----------
    graph : GraphIndex
        Input graph

    Returns
    -------
    bool
        True if the graph is a uni-bipartite.
    """
    src, dst, _ = graph.edges()
    return set(src.tonumpy()).isdisjoint(set(dst.tonumpy()))


def master_then_spare(data):
    """Return the provided satellites list sorted as:
        - alive first,
        - then spare
        - then dead
        satellites.

    :param data: the SatelliteLink list
    :type data: list
    :return: sorted list
    :rtype: list
    """
    master = []
    spare = []
    for sdata in data:
        if sdata.spare:
            spare.append(sdata)
        else:
            master.append(sdata)
    rdata = []
    rdata.extend(master)
    rdata.extend(spare)
    return rdata


def _matching_budgets(budgets, account_name, date_active):
    """Find matching budgets.

    Returns:
        The budget that is active on the specifed date for the
        specified account.
    """
    last_seen_budgets = {}
    for budget in budgets[account_name]:
        if budget.date_start <= date_active:
            last_seen_budgets[budget.currency] = budget
        else:
            break
    return last_seen_budgets


@staticmethod
def _dpi(px_per_meter):
    """
        Return the integer pixels per inch from *px_per_meter*, defaulting to
        96 if *px_per_meter* is zero.
        """
    if px_per_meter == 0:
        return 96
    return int(round(px_per_meter * 0.0254))


@staticmethod
def _get_schema(instance):
    """
        Return the DataFrame's schema from an instance
        """
    raise NotImplementedError


@classmethod
def backend_version(cls):
    """ Returns which backend is used.

        Returns:
            `str`: The name and version of the backend(s).
        """
    cls._setup_backends()
    return ', '.join(cls._backend_versions)


def create_iso(archive, compression, cmd, verbosity, interactive, filenames):
    """Create an ISO archive."""
    cmdlist = [cmd, '-r', '-J']
    if verbosity > 1:
        cmdlist.append('-v')
        if verbosity > 2:
            cmdlist.append('-v')
    cmdlist.extend(['-o', archive])
    cmdlist.extend(filenames)
    return cmdlist


def castagna_vp_to_vs(vp):
    """Calculate vp from vs using castagna's relation.

    Castagna's relation (the mudrock line) is an empirical relation for vp/vs
    for siliciclastic rocks (i.e. sandstones and shales). [Castagna et al.,
    1985]

        vp = 1.16 * vs + 1360 [m/s]

    :param vp: P-wave velocity [m/s]
    :returns: S-wave velocity [m/s]
    """
    return (vp - 1360.0) / 1.16


def _const_compare_digest_backport(a, b):
    """
    Compare two digests of equal length in constant time.

    The digests must be of type str/bytes.
    Returns True if the digests match, and False otherwise.
    """
    result = abs(len(a) - len(b))
    for l, r in zip(bytearray(a), bytearray(b)):
        result |= l ^ r
    return result == 0


def bin2int(s):
    """
    binary string to integer
    """
    o = 0
    k = len(s) - 1
    for i, v in enumerate(s):
        o = o + int(v) * 2 ** (k - i)
    return o


def is_user_authenticated(handler):
    """Check if the current user is authenticated."""
    current_user = getattr(handler, 'current_user', False)
    return bool(current_user)


def rshift(val, n):
    """python port for '>>>'(right shift with padding)
    """
    return val % 4294967296 >> n


def get_object_env_key(account, container, obj):
    """
    Get the keys for env (env_key) where info about object is cached
    :param   account: The name of the account
    :param container: The name of the container
    :param obj: The name of the object
    :returns a string env_key
    """
    env_key = 'swift.object/%s/%s/%s' % (account, container, obj)
    return env_key


def context_cycle_int(data_path: str='', reverse: bool=False, wrap: bool=False
    ):
    """Set a context value (useful for cycling active material, vertex keys, groups, etc.)

    :param data_path: Context Attributes, RNA context string
    :type data_path: str
    :param reverse: Reverse, Cycle backwards
    :type reverse: bool
    :param wrap: Wrap, Wrap back to the first/last values
    :type wrap: bool
    """
    pass


@classmethod
def observer_level(cls, game, power_name):
    """ Create and return a game observer level with given game data and power name. """
    return cls(game, 'observer', power_name)


def copybuffer():
    """Selected objects are copied to the clipboard

    """
    pass


def is_apple_os(os_):
    """returns True if OS is Apple one (Macos, iOS, watchOS or tvOS"""
    return str(os_) in ['Macos', 'iOS', 'watchOS', 'tvOS']


def get_probs(x):
    """
    calculate sample probability of each distinct value
    in a discrete array/series.

    Parameters
    ----------
    x: pandas series or numpy array containing value counts

    Returns
    -------
    sample probability of each value
    """
    return x / x.sum()


def key_vector(rows):
    """
    Empty key vector
    :param rows:
    :return:
    """
    return [None] * rows


def scan_setup_py():
    """Validate the contents of setup.py against Versioneer's expectations."""
    found = set()
    setters = False
    errors = 0
    with open('setup.py', 'r') as f:
        for line in f.readlines():
            if 'import versioneer' in line:
                found.add('import')
            if 'versioneer.get_cmdclass()' in line:
                found.add('cmdclass')
            if 'versioneer.get_version()' in line:
                found.add('get_version')
            if 'versioneer.VCS' in line:
                setters = True
            if 'versioneer.versionfile_source' in line:
                setters = True
    if len(found) != 3:
        print('')
        print('Your setup.py appears to be missing some important items')
        print('(but I might be wrong). Please make sure it has something')
        print('roughly like the following:')
        print('')
        print(' import versioneer')
        print(' setup( version=versioneer.get_version(),')
        print('        cmdclass=versioneer.get_cmdclass(),  ...)')
        print('')
        errors += 1
    if setters:
        print("You should remove lines like 'versioneer.VCS = ' and")
        print("'versioneer.versionfile_source = ' . This configuration")
        print('now lives in setup.cfg, and should be removed from setup.py')
        print('')
        errors += 1
    return errors


def assign_identity(list_of_fragments):
    """Identifies the individual fragments recursively, based on the value of
    P2

    Parameters
    ----------
    list_of_fragments : <ListOfFragments object>
        collection of the individual fragments and associated methods
    """
    list_of_fragments.compute_P2_vectors()
    number_of_unidentified_individual_fragments = (list_of_fragments.
        get_number_of_unidentified_individual_fragments())
    while number_of_unidentified_individual_fragments != 0:
        fragment = list_of_fragments.get_next_fragment_to_identify()
        fragment.assign_identity()
        number_of_unidentified_individual_fragments -= 1


@staticmethod
def _remove_node(node, nodes, constraints):
    """
        Returns a new set where node has been removed from nodes, subject to
        symmetry constraints. We know, that for every constraint we have
        those subgraph nodes are equal. So whenever we would remove the
        lower part of a constraint, remove the higher instead.
        """
    while True:
        for low, high in constraints:
            if low == node and high in nodes:
                node = high
                break
        else:
            break
    return frozenset(nodes - {node})


@classmethod
def get(cls, project_id, model_id):
    """ Retrieve a missing report.

        Parameters
        ----------
        project_id : str
            The project's id.
        model_id : str
            The model's id.

        Returns
        -------
        MissingValuesReport
            The queried missing report.
        """
    url = 'projects/{}/models/{}/missingReport/'.format(project_id, model_id)
    return cls.from_location(url)


def ansibleResults(result, extraKeys=()):
    """
  Returns a dictionary containing at least:

  stderr
  stdout
  returncode (None if the process didn't complete)
  error if an exception was raised
  """
    result = result.clean_copy()
    resultDict = {'returncode': result._check_key('rc')}
    keyMap = {'msg': ['msg'], 'error': ['exception', 'module_stderr'],
        'stdout': ['stdout', 'module_stdout']}
    for name, keys in keyMap.items():
        for key in keys:
            val = result._check_key(key)
            if val:
                resultDict[name] = val
                break
    for key in extraKeys:
        resultDict[key] = result._check_key(key)
    return resultDict


def set_analog_src(lucid, srcval):
    """Call lucid8824.set_analog_src"""
    lucid.set_analog_src(srcval)


def render_git_describe(pieces):
    """TAG[-DISTANCE-gHEX][-dirty].

    Like 'git describe --tags --dirty --always'.

    Exceptions:
    1: no tags. HEX[-dirty]  (note: no 'g' prefix)
    """
    if pieces['closest-tag']:
        rendered = pieces['closest-tag']
        if pieces['distance']:
            rendered += '-%d-g%s' % (pieces['distance'], pieces['short'])
    else:
        rendered = pieces['short']
    if pieces['dirty']:
        rendered += '-dirty'
    return rendered


@staticmethod
def _user_callback_example(pkt_dict: dict) ->None:
    """
        This is an user_callback example method.
        It manages the pkt dictionary
        :param pkt_dict: The packet dictionary
        :return: None
        """
    return None


def _decode_field(field):
    """
    Read a field's type and value

    :param field: Raw DynamoDB request field of the form ``{'typename':'value'}``

    :return: (typename, value) string tuple
    """
    return field.items()[0]


def create_dam_path(local_path, local_import_root, dam_import_root):
    """ Returns <ok>, <path> """
    ret = local_path.replace(local_import_root, dam_import_root)
    ret = ret.replace('\\', '/')
    return ret


def insert(text: str=''):
    """Insert text at cursor position

    :param text: Text, Text to insert at the cursor position
    :type text: str
    """
    pass


def format_snap_name(snap, *, allow_empty_version: bool=False) ->str:
    """Return a filename representing the snap depending on snap attributes.

    :param dict snap: a dictionary of keys containing name, version and arch.
    :param bool allow_empty_version: if set a filename without a version is
                                     allowed.
    """
    if allow_empty_version and snap.get('version') is None:
        extension = '{name}_{arch}.snap'
    else:
        extension = '{name}_{version}_{arch}.snap'
    if 'arch' not in snap:
        snap['arch'] = snap.get('architectures', None)
    if not snap['arch']:
        snap['arch'] = 'all'
    elif len(snap['arch']) == 1:
        snap['arch'] = snap['arch'][0]
    else:
        snap['arch'] = 'multi'
    return extension.format(**snap)


@classmethod
def detect(cls, old_config, new_config):
    """Detect if user's script's config file in `new_config` differs from `old_config`"""
    old_script_config = cls.get_nameless_config(old_config)
    new_script_config = cls.get_nameless_config(new_config)
    if old_script_config != new_script_config:
        yield cls(old_config, new_config)


@classmethod
def sampler(cls, format_, *args, **kwargs):
    """Fetch a method to generate an initial binary sample

        Parameters
        ----------
        format : str
            the method name; Choose from 'independent' or 'multidim'

        *args
            the arguments necessary for the registered sample
            method; see help(InitialBinaryTable.sampler('independent')
            to see the arguments necessary for the independent sample
        """
    from .sampler.sampler import get_sampler
    sampler = get_sampler(format_, cls)
    return sampler(*args, **kwargs)


def _copy_axis_visibility(source, target):
    """
    Copies visibility and color properties from each X/Y axis in the source
    axes object to the target axes object.
    """
    if not source.get_xaxis().get_visible():
        target.get_xaxis().set_visible(False)
    if not source.get_yaxis().get_visible():
        target.get_yaxis().set_visible(False)
    target.set_facecolor(source.get_facecolor())


def type2str(cls):
    """Convert type to type name."""
    return cls.__qualname__


def get_config(context):
    """
    Helper method extract config from click.Context

    :param context: Context object passed in by Click

    :return: Config object within Context
    """
    return context.obj.get('config')