Skip to content

single_trail

SingleTrailGenerator

Bases: BaseGenerator

Builds a single chain of CEM trail edges from the origin node to a fixed end node.

Source code in src/torch_structure/generators/single_trail.py
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
class SingleTrailGenerator(BaseGenerator):
    """Builds a single chain of CEM trail edges from the origin node to a fixed end node."""

    def __init__(self, **overrides):
        super().__init__(**overrides)
        self.max_attempts = 1

        self.node_attrs = {
            "coords": torch.empty((0, 3), dtype=torch.float),
            "load": torch.empty((0, 3), dtype=torch.float),
            "support_condition": torch.empty((0, 3), dtype=torch.long),
            "is_origin_node": torch.empty((0, 1), dtype=torch.bool),
            "sequence": torch.empty((0, 1), dtype=torch.long),
        }

        self.edge_attrs = {
            "force": torch.empty((0, 1), dtype=torch.float),
            "length": torch.empty((0, 1), dtype=torch.float),
            "is_trail_edge": torch.empty((0, 1), dtype=torch.bool),
            "force_sign": torch.empty((0, 1), dtype=torch.float),
        }

        self.default_attrs = {
            "coords": torch.full((3,), torch.nan),
            "load": torch.zeros(3, dtype=torch.float),
            "support_condition": torch.zeros(3, dtype=torch.bool),
            "is_origin_node": torch.tensor(0, dtype=torch.bool),
            "sequence": torch.tensor(-1, dtype=torch.long),
            "force": torch.tensor([torch.nan]),
            "length": torch.tensor([torch.nan]),
            "is_trail_edge": torch.tensor(True, dtype=torch.bool),
            "force_sign": torch.tensor(-1.0, dtype=torch.float),
        }

    def sample_input(self, **kwargs):
        """
        No sampling required
        """
        return kwargs

    def validate_input(self, **kwargs):
        """
        No validation required
        """
        pass

    def generate(self, 
                n_nodes : int,
                nodal_load : list,
                trail_element_length : float,
                origin_node_load : list,
                ):
        """Build a single trail of ``n_nodes`` nodes from an origin node to a supported end node.

        Args:
            n_nodes (int): total number of nodes in the trail, including the
                origin and end node.
            nodal_load (list): load applied to every intermediate node.
            trail_element_length (float): length assigned to every trail
                edge.
            origin_node_load (list): additional load applied only to the
                origin node (on top of ``nodal_load``).

        Returns:
            StructData: the constructed (not yet form-found) trail graph.
        """
        # Initialize graph
        graph = StructData(
                node_attrs=self.node_attrs,
                edge_attrs=self.edge_attrs,
                default_attrs=self.default_attrs,
            )

        # Parse data as numpy arrays
        origin_node_coords = np.zeros(3)
        nodal_load = np.array(nodal_load)
        origin_node_load = np.array(origin_node_load)
        support_condition = torch.tensor([False, False, False])

        # Add origin nodes
        graph.add_node(
            f"node_0",
            coords=origin_node_coords,
            is_origin_node=torch.tensor(True),
            sequence=torch.tensor(0),
            load=nodal_load + origin_node_load,
        )
        for j in range(1,n_nodes-1):

            # Add node
            graph.add_node(
                f"node_{j}",
                is_origin_node=torch.tensor(False),
                sequence=torch.tensor(j),
                load=nodal_load,
                support_condition=support_condition,
            )
            # Add new edge with the created node and its previous node
            graph.add_edge(
                f"node_{j-1}",
                f"node_{j}",
                is_trail_edge=torch.tensor(True),
                length=trail_element_length,
                force_sign=torch.tensor(-1.0),
            )

        # Add node
        j = n_nodes - 1 
        graph.add_node(
            f"node_{j}",
            is_origin_node=torch.tensor(False),
            sequence=torch.tensor(j),
            load=nodal_load,
            support_condition=torch.tensor([True, True, True]),
        )
        # Add new edge with the created node and its previous node
        graph.add_edge(
            f"node_{j-1}",
            f"node_{j}",
            is_trail_edge=torch.tensor(True),
            length=trail_element_length,
            force_sign=torch.tensor(-1.0),
        )

        return graph

generate(n_nodes, nodal_load, trail_element_length, origin_node_load)

Build a single trail of n_nodes nodes from an origin node to a supported end node.

Parameters:

Name Type Description Default
n_nodes int

total number of nodes in the trail, including the origin and end node.

required
nodal_load list

load applied to every intermediate node.

required
trail_element_length float

length assigned to every trail edge.

required
origin_node_load list

additional load applied only to the origin node (on top of nodal_load).

required

Returns:

Name Type Description
StructData

the constructed (not yet form-found) trail graph.

Source code in src/torch_structure/generators/single_trail.py
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
def generate(self, 
            n_nodes : int,
            nodal_load : list,
            trail_element_length : float,
            origin_node_load : list,
            ):
    """Build a single trail of ``n_nodes`` nodes from an origin node to a supported end node.

    Args:
        n_nodes (int): total number of nodes in the trail, including the
            origin and end node.
        nodal_load (list): load applied to every intermediate node.
        trail_element_length (float): length assigned to every trail
            edge.
        origin_node_load (list): additional load applied only to the
            origin node (on top of ``nodal_load``).

    Returns:
        StructData: the constructed (not yet form-found) trail graph.
    """
    # Initialize graph
    graph = StructData(
            node_attrs=self.node_attrs,
            edge_attrs=self.edge_attrs,
            default_attrs=self.default_attrs,
        )

    # Parse data as numpy arrays
    origin_node_coords = np.zeros(3)
    nodal_load = np.array(nodal_load)
    origin_node_load = np.array(origin_node_load)
    support_condition = torch.tensor([False, False, False])

    # Add origin nodes
    graph.add_node(
        f"node_0",
        coords=origin_node_coords,
        is_origin_node=torch.tensor(True),
        sequence=torch.tensor(0),
        load=nodal_load + origin_node_load,
    )
    for j in range(1,n_nodes-1):

        # Add node
        graph.add_node(
            f"node_{j}",
            is_origin_node=torch.tensor(False),
            sequence=torch.tensor(j),
            load=nodal_load,
            support_condition=support_condition,
        )
        # Add new edge with the created node and its previous node
        graph.add_edge(
            f"node_{j-1}",
            f"node_{j}",
            is_trail_edge=torch.tensor(True),
            length=trail_element_length,
            force_sign=torch.tensor(-1.0),
        )

    # Add node
    j = n_nodes - 1 
    graph.add_node(
        f"node_{j}",
        is_origin_node=torch.tensor(False),
        sequence=torch.tensor(j),
        load=nodal_load,
        support_condition=torch.tensor([True, True, True]),
    )
    # Add new edge with the created node and its previous node
    graph.add_edge(
        f"node_{j-1}",
        f"node_{j}",
        is_trail_edge=torch.tensor(True),
        length=trail_element_length,
        force_sign=torch.tensor(-1.0),
    )

    return graph

sample_input(**kwargs)

No sampling required

Source code in src/torch_structure/generators/single_trail.py
41
42
43
44
45
def sample_input(self, **kwargs):
    """
    No sampling required
    """
    return kwargs

validate_input(**kwargs)

No validation required

Source code in src/torch_structure/generators/single_trail.py
47
48
49
50
51
def validate_input(self, **kwargs):
    """
    No validation required
    """
    pass