SPPAS 4.22

https://sppas.org/

Module sppas.src.anndata

Class sppasAnnotation

Description

Represents an annotation.

A sppasAnnotation() is a container for:

  • a sppasLocation()
  • a list of sppasLabel()
Example
Example
 >>> location = sppasLocation(sppasPoint(1.5, radius=0.01))
 >>> labels = sppasLabel(sppasTag("foo"))
 >>> ann = sppasAnnotation(location, labels)

Constructor

Create a new sppasAnnotation instance.

Parameters
  • location: (sppasLocation) the location(s) where the annotation happens
  • labels: (sppasLabel, list) the label(s) to stamp this annotation, or a list of them.
View Source
def __init__(self, location, labels=list()):
    """Create a new sppasAnnotation instance.

    :param location: (sppasLocation) the location(s) where the annotation    happens
    :param labels: (sppasLabel, list) the label(s) to stamp this    annotation, or a list of them.

    """
    super(sppasAnnotation, self).__init__()
    if isinstance(location, sppasLocation) is False:
        raise AnnDataTypeError(location, 'sppasLocation')
    self.__parent = None
    self.__location = location
    self.__labels = list()
    self.__score = None
    self.set_labels(labels)

Public functions

get_parent

Return the parent tier or None.

View Source
def get_parent(self):
    """Return the parent tier or None."""
    return self.__parent

get_score

Return the score of this annotation or None if no score is set.

View Source
def get_score(self):
    """Return the score of this annotation or None if no score is set."""
    return self.__score

get_location

Return the sppasLocation() of this annotation.

View Source
def get_location(self):
    """Return the sppasLocation() of this annotation."""
    return self.__location

get_labels

Return the list of sppasLabel() of this annotation.

View Source
def get_labels(self):
    """Return the list of sppasLabel() of this annotation."""
    return self.__labels

copy

Return a full copy of the annotation.

The location, the labels and the metadata are all copied. The 'id' of the returned annotation is then the same.

Returns
  • sppasAnnotation()
View Source
def copy(self):
    """Return a full copy of the annotation.

        The location, the labels and the metadata are all copied. The 'id'
        of the returned annotation is then the same.

        :returns: sppasAnnotation()

        """
    location = self.__location.copy()
    labels = list()
    for l in self.__labels:
        labels.append(l.copy())
    other = sppasAnnotation(location, labels)
    other.set_parent(self.__parent)
    other.set_score(self.__score)
    for key in self.get_meta_keys():
        other.set_meta(key, self.get_meta(key))
    return other

set_parent

Set a parent tier.

Parameters
  • parent: (sppasTier) The parent tier of this annotation.
Raises

CtrlVocabContainsError, HierarchyContainsError, HierarchyTypeError

View Source
def set_parent(self, parent=None):
    """Set a parent tier.

        :param parent: (sppasTier) The parent tier of this annotation.
        :raises: CtrlVocabContainsError, HierarchyContainsError,         HierarchyTypeError

        """
    if parent is not None:
        parent.validate_annotation_location(self.__location)
        for label in self.__labels:
            parent.validate_annotation_label(label)
    self.__parent = parent

set_score

Set or reset the score to this annotation.

Parameters
  • score: (float)
View Source
def set_score(self, score=None):
    """Set or reset the score to this annotation.

        :param score: (float)

        """
    if score is not None:
        try:
            self.__score = float(score)
        except ValueError:
            raise AnnDataTypeError(score, 'float')
    else:
        self.__score = None

set_labels

Fix/reset the list of labels of this annotation.

Parameters
  • labels: (sppasLabel, list) the label(s) to stamp this annotation, or a list of them.
Raises

AnnDataTypeError, TypeError, CtrlVocabContainsError, HierarchyContainsError, HierarchyTypeError

View Source
def set_labels(self, labels=[]):
    """Fix/reset the list of labels of this annotation.

        :param labels: (sppasLabel, list) the label(s) to stamp this         annotation, or a list of them.
        :raises: AnnDataTypeError, TypeError, CtrlVocabContainsError,         HierarchyContainsError, HierarchyTypeError

        """
    self.__labels = list()
    if labels is None:
        return
    if isinstance(labels, sppasLabel) is True:
        self.validate_label(labels)
        self.__labels.append(labels)
    elif isinstance(labels, list) is True:
        for label in labels:
            if label is not None:
                self.validate_label(label)
                self.__labels.append(label)
    else:
        raise AnnDataTypeError(labels, 'sppasLabel/list')

validate

Validate the annotation.

Check if the labels and location match the requirements.

Raises

TypeError, CtrlVocabContainsError, HierarchyContainsError, HierarchyTypeError

View Source
def validate(self):
    """Validate the annotation.

        Check if the labels and location match the requirements.

        :raises: TypeError, CtrlVocabContainsError, HierarchyContainsError,         HierarchyTypeError

        """
    for label in self.__labels:
        self.validate_label(label)
    if self.__parent is not None:
        self.__parent.validate_annotation_location(self.__location)

validate_label

Validate the label.

Check if the label matches the requirements of this annotation.

Raises

CtrlVocabContainsError, TypeError

Parameters
  • label
View Source
def validate_label(self, label):
    """Validate the label.

        Check if the label matches the requirements of this annotation.

        :raises: CtrlVocabContainsError, TypeError

        """
    if label is None:
        return
    if isinstance(label, sppasLabel) is False:
        raise AnnDataTypeError(label, 'sppasLabel')
    if len(self.__labels) > 0:
        current_type = set((l.get_type() for l in self.__labels if l is not None))
        if len(current_type) > 0 and label.get_type() not in current_type:
            raise TypeError()
    if self.__parent is not None:
        self.__parent.validate_annotation_label(label)

is_labelled

Return True if at least a sppasTag exists and is not None.

View Source
def is_labelled(self):
    """Return True if at least a sppasTag exists and is not None."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label is not None:
            if label.is_tagged() is True:
                return True
    return False

get_label_type

Return the current type of tags, or an empty string.

View Source
def get_label_type(self):
    """Return the current type of tags, or an empty string."""
    if len(self.__labels) == 0:
        return ''
    for label in self.__labels:
        if label is not None:
            if label.is_tagged() is True:
                return label.get_type()
    return ''

append_label

Append a label into the list of labels.

Parameters
  • label: (sppasLabel)
View Source
def append_label(self, label):
    """Append a label into the list of labels.

        :param label: (sppasLabel)

        """
    self.validate_label(label)
    self.__labels.append(label)

get_labels_best_tag

Return a list with the best tag of each label.

View Source
def get_labels_best_tag(self):
    """Return a list with the best tag of each label."""
    tags = list()
    for label in self.__labels:
        best = label.get_best()
        if best is not None:
            tags.append(best)
        else:
            tags.append(sppasTag(''))
    return tags

get_best_tag

Return the tag with the highest score of a label or an empty str.

Parameters
  • label_idx: (int)
View Source
def get_best_tag(self, label_idx=0):
    """Return the tag with the highest score of a label or an empty str.

        :param label_idx: (int)

        """
    if len(self.__labels) == 0:
        return sppasTag('')
    try:
        label = self.__labels[label_idx]
    except IndexError:
        raise IndexError('Invalid label index')
    if label is None:
        return sppasTag('')
    best = label.get_best()
    if best is not None:
        return best
    return sppasTag('')

add_tag

Append an alternative tag in a label.

Parameters
  • tag: (sppasTag)
  • score: (float)
  • label_idx: (int)
Raises

AnnDataTypeError, IndexError

View Source
def add_tag(self, tag, score=None, label_idx=0):
    """Append an alternative tag in a label.

        :param tag: (sppasTag)
        :param score: (float)
        :param label_idx: (int)
        :raises: AnnDataTypeError, IndexError

        """
    if len(self.__labels) == 0:
        label = sppasLabel(tag, score)
        self.__labels.append(label)
    else:
        try:
            label = self.__labels[label_idx]
            if label is None:
                label = sppasLabel(tag, score)
            else:
                label.append(tag, score)
        except IndexError:
            raise IndexError('Invalid label index')
    try:
        self.validate_label(label)
    except:
        label.remove(tag)
        raise

remove_tag

Remove an alternative tag of the label.

Parameters
  • tag: (sppasTag) the tag to be removed of the list.
  • label_idx: (int)
View Source
def remove_tag(self, tag, label_idx=0):
    """Remove an alternative tag of the label.

        :param tag: (sppasTag) the tag to be removed of the list.
        :param label_idx: (int)

        """
    try:
        label = self.__labels[label_idx]
    except IndexError:
        raise IndexError('Invalid label index')
    label.remove(tag)

contains_tag

Return True if the given tag is in the label.

Parameters
  • tag: (sppasTag)
  • function: Search function
  • reverse: Reverse the function.
  • label_idx: (int)
View Source
def contains_tag(self, tag, function='exact', reverse=False, label_idx=0):
    """Return True if the given tag is in the label.

        :param tag: (sppasTag)
        :param function: Search function
        :param reverse: Reverse the function.
        :param label_idx: (int)

        """
    if len(self.__labels) == 0:
        return False
    try:
        label = self.__labels[label_idx]
    except IndexError:
        raise IndexError('Invalid label index')
    if label is None:
        return False
    if label.is_tagged() is False:
        return False
    t = sppasTagCompare()
    tag_functions = list()
    tag_functions.append((t.get(function), tag.get_typed_content(), reverse))
    r = label.match(tag_functions)
    if reverse is False:
        return r
    return not r

label_is_filled

Return True if at least one BEST tag is filled.

View Source
def label_is_filled(self):
    """Return True if at least one BEST tag is filled."""
    for label in self.__labels:
        if label is not None:
            if label.is_tagged() is True:
                if label.get_best().get_content() != '':
                    return True
    return False

label_is_string

Return True if the type of the labels is 'str'.

View Source
def label_is_string(self):
    """Return True if the type of the labels is 'str'."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label.is_tagged() is True:
            return label.is_string()
    return False

label_is_float

Return True if the type of the labels is 'float'.

View Source
def label_is_float(self):
    """Return True if the type of the labels is 'float'."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label.is_tagged() is True:
            return label.is_float()
    return False

label_is_int

Return True if the type of the labels is 'int'.

View Source
def label_is_int(self):
    """Return True if the type of the labels is 'int'."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label.is_tagged() is True:
            return label.is_int()
    return False

label_is_bool

Return True if the type of the labels is 'bool'.

View Source
def label_is_bool(self):
    """Return True if the type of the labels is 'bool'."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label.is_tagged() is True:
            return label.is_bool()
    return False

label_is_point

Return True if the type of the labels is 'point'.

View Source
def label_is_point(self):
    """Return True if the type of the labels is 'point'."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label.is_tagged() is True:
            return label.is_point()
    return False

label_is_rect

Return True if the type of the labels is 'rect'.

View Source
def label_is_rect(self):
    """Return True if the type of the labels is 'rect'."""
    if len(self.__labels) == 0:
        return False
    for label in self.__labels:
        if label.is_tagged() is True:
            return label.is_rect()
    return False

serialize_labels

DEPRECATED. Return labels serialized into a string.

TODO: REMOVE THIS METHOD. Use aioutils.serialize_labels() instead.

Parameters
  • separator: (str) String to separate labels.
  • empty: (str) The text to return if a tag is empty or not set.
  • alt: (bool) Include alternative tags
Returns
  • (str)
View Source
def serialize_labels(self, separator='\n', empty='', alt=True):
    """DEPRECATED. Return labels serialized into a string.

        TODO: REMOVE THIS METHOD. Use aioutils.serialize_labels() instead.

        :param separator: (str) String to separate labels.
        :param empty: (str) The text to return if a tag is empty or not set.
        :param alt: (bool) Include alternative tags
        :returns: (str)

        """
    warnings.warn('Use serialize_labels(ann.get_labels()) of aioutils package instead', DeprecationWarning)
    if len(self.__labels) == 0:
        return empty
    if len(self.__labels) == 1:
        return self.__labels[0].serialize(empty, alt)
    c = list()
    for label in self.__labels:
        c.append(label.serialize(empty, alt))
    return separator.join(c)

set_best_localization

Set the best localization of the location.

Parameters
  • localization: (sppasBaseLocalization)
View Source
def set_best_localization(self, localization):
    """Set the best localization of the location.

        :param localization: (sppasBaseLocalization)

        """
    old_loc = self.__location.get_best().copy()
    self.__location.get_best().set(localization)
    if self.__parent is not None:
        try:
            self.__parent.validate_annotation_location(self.__location)
        except Exception:
            self.__location.get_best().set(old_loc)
            raise

location_is_point

Return True if the location is made of sppasPoint locs.

View Source
def location_is_point(self):
    """Return True if the location is made of sppasPoint locs."""
    return self.__location.is_point()

location_is_interval

Return True if the location is made of sppasInterval locs.

View Source
def location_is_interval(self):
    """Return True if the location is made of sppasInterval locs."""
    return self.__location.is_interval()

location_is_disjoint

Return True if the location is made of sppasDisjoint locs.

View Source
def location_is_disjoint(self):
    """Return True if the location is made of sppasDisjoint locs."""
    return self.__location.is_disjoint()

get_highest_localization

Return a copy of the sppasPoint with the highest loc.

View Source
def get_highest_localization(self):
    """Return a copy of the sppasPoint with the highest loc."""
    return self.__location.get_highest_localization()

get_lowest_localization

Return a copy of the sppasPoint with the lowest localization.

View Source
def get_lowest_localization(self):
    """Return a copy of the sppasPoint with the lowest localization."""
    return self.__location.get_lowest_localization()

get_all_points

Return the list of a copy of all points of this annotation.

View Source
def get_all_points(self):
    """Return the list of a copy of all points of this annotation."""
    points = list()
    if self.__location.is_point():
        for localization, score in self.__location:
            points.append(localization.copy())
    elif self.__location.is_interval():
        for localization, score in self.__location:
            points.append(localization.get_begin().copy())
            points.append(localization.get_end().copy())
    elif self.__location.is_disjoint():
        for localization, score in self.__location:
            for interval in localization.get_intervals():
                points.append(interval.get_begin().copy())
                points.append(interval.get_end().copy())
    return points

contains_localization

Return True if the given localization is contained in the location.

Parameters
  • localization
View Source
def contains_localization(self, localization):
    """Return True if the given localization is contained in the location."""
    return self.__location.contains(localization)

inside_localization

Return True if the given localization is inside the location.

Parameters
  • localization
View Source
def inside_localization(self, localization):
    """Return True if the given localization is inside the location."""
    return self.__location.inside(localization)

validate_location

Validate the location of the annotation.

Raises
View Source
def validate_location(self):
    """Validate the location of the annotation.

        :raises:

        """
    if self.__parent is not None:
        self.__parent.validate_annotation_location(self.__location)

Overloads

__format__

View Source
def __format__(self, fmt):
    return str(self).__format__(fmt)

__repr__

View Source
def __repr__(self):
    return 'Annotation {:s}: {:s} {:s}'.format(self.get_meta('id'), str(self.__location), str(self.__labels))

__str__

View Source
def __str__(self):
    return '{:s} {:s} {:s}'.format(self.get_meta('id'), str(self.__location), str(self.__labels))

__hash__

View Source
def __hash__(self):
    return hash(self.get_id())

__eq__

View Source
def __eq__(self, other):
    if other is None:
        return False
    if isinstance(other, sppasAnnotation) is False:
        return False
    if self.__score != other.get_score():
        return False
    if self.__location != other.get_location():
        return False
    if len(self.__labels) != len(other.get_labels()):
        return False
    for label1, label2 in zip(self.__labels, other.get_labels()):
        if label1 != label2:
            return False
    return True

__ne__

View Source
def __ne__(self, other):
    return not self == other