예제 #1
0
def connect(source, destination):
    """Connects two components or ports.

    Defines a power bond between the source and destination ports such that
    the bond tail is at the source, and the bond head is at the destination.
    We assume that either the source and/or destination is or has a free
    port.

    Args:
        source (Port or BondGraphBase):      The tail of the power bond
        destination (Port or BondGraphBase): The head of the power bond

    Raises:
        InvalidPortException, InvalidComponentException

    See Also:
        :func:`disconnect`
    """

    tail = _find_or_make_port(source, is_tail=True)
    head = _find_or_make_port(destination)

    model = tail.component.parent
    model_prime = head.component.parent
    if not model:
        raise InvalidComponentException(f"{tail.component} is not in a model")
    elif not model_prime:
        raise InvalidComponentException(f"{head.component} is not in a model")
    elif model is not model_prime:
        raise InvalidComponentException("Components are in different models")

    bond = Bond(tail, head)
    model.bonds.add(bond)
예제 #2
0
def swap(old_component, new_component):
    """
    Replaces the old component with a new component.
    Components must be of compatible classes; 1 one port cannot replace an
    n-port, for example.
    The old component will be completely removed from the system model.

    Args:
        old_component: The component to be replaced. Must already be in the
         model.
        new_component: The substitute component which must not be in the
         model

    Raises:
        InvalidPortException, InvalidComponentException

    """

    # TODO: More validation required

    def is_swap_valid(old_comp, new_comp):  # noqa
        if not isinstance(new_comp, BondGraphBase):
            return False
        return True

    model = old_component.parent
    if not model:
        raise InvalidComponentException("No parent model.")
    elif new_component in model.components:
        raise InvalidComponentException("Component is already in the model")
    elif not is_swap_valid(old_component, new_component):
        raise InvalidComponentException("Cannot swap components")

    model.add(new_component)

    swaps = []
    for bond in model.bonds:
        try:
            if bond.tail.component is old_component:
                tail = new_component.get_port()
                head = bond.head
            elif bond.head.component is old_component:
                tail = bond.tail
                head = new_component.get_port()
            else:
                continue
        except InvalidPortException:
            raise InvalidComponentException(
                "Cannot swap components: Incompatible ports")

        swaps.append((bond, Bond(tail, head)))

    for old_bond, new_bond in swaps:
        disconnect(old_bond.tail, old_bond.head)
        connect(new_bond.tail, new_bond.head)

    model.remove(old_component)
예제 #3
0
    def test_compare(self):
        from BondGraphTools.base import Bond
        from BondGraphTools.actions import new
        c = new('C')
        one = new('1')

        b_1 = Bond(head=(c, 0), tail=(one, 0))

        assert b_1 == ((one, 0), (c, 0))
예제 #4
0
 def remove(self, bond):
     tail = bond.tail
     head = bond.head
     if bond in self:
         super().remove(bond)
     else:
         super().remove(Bond(head, tail))
     head.is_connected = False
     tail.is_connected = False
예제 #5
0
    def test_create(self):
        from BondGraphTools.base import Bond
        from BondGraphTools.actions import new

        c = new('C')
        one = new('1')

        b_1 = Bond(head=(c, 0), tail=(one, 0))

        assert c in b_1
        assert one in b_1
        assert (c, 0) in b_1
        assert (one, 0) in b_1
        assert (one, 1) not in b_1