Skip to content

1D Line Element

Bases: Element

An abitrary order 1d line finite element

The node ordering for the nth order line element looks like: ::

0 --- 2 --- 3 ... n-1 --- n --- 1

Inherits from

Element : FEMpy.Elements.Element The FEMpy element base class

Source code in FEMpy/Elements/LineElement1D.py
 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
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
class LineElement1D(Element):
    """An abitrary order 1d line finite element

    The node ordering for the nth order line element looks like: ::

        0 --- 2 --- 3 ... n-1 --- n --- 1

    Inherits from
    -------------
    Element : FEMpy.Elements.Element
        The FEMpy element base class
    """

    def __init__(self, order=1, numStates=None, quadratureOrder=None):
        """Create a new 1d line element object

        Parameters
        ----------
        order : int, optional
            _description_, by default 1
        numStates : _type_, optional
            _description_, by default None
        quadratureOrder : _type_, optional
            _description_, by default None
        """
        if order < 1:
            raise ValueError("Order must be greater than 0")
        self.order = order
        numNodes = order + 1
        if quadratureOrder is None:
            # Compute quadrature order necessary to exactly intergrate polynomials of the same order as this element's
            # shape functions
            quadratureOrder = int(np.ceil((order + 1) / 2))

        super().__init__(numNodes, numDim=1, quadratureOrder=quadratureOrder, numStates=numStates)

        self.name = f"Order{self.order}-LagrangeLine"

        self.shapeFuncToNodeOrder = self._getNodeReordering(self.order)

    # ==============================================================================
    # Public methods
    # ==============================================================================
    def computeShapeFunctions(self, paramCoords):
        """Compute the shape function values at a given set of parametric coordinates

        Parameters
        ----------
        paramCoords : numPoint x numDim array
            Array of parametric point coordinates to evaluate shape functions at

        Returns
        -------
        N: numPoint x numNodes array
            Array of shape function values at the given parametric coordinates, N[i][j] is the value of the jth shape
            function at the ith parametric point
        """
        N = LP.LagrangePoly1d(paramCoords, self.order + 1)
        return np.ascontiguousarray(N[:, self.shapeFuncToNodeOrder])

    def computeShapeFunctionGradients(self, paramCoords):
        """Compute the derivatives of the shape functions with respect to the parametric coordinates at a given set of parametric coordinates



        Parameters
        ----------
        paramCoords : numPoint x numDim array
            Array of parametric point coordinates to evaluate shape function gradients at

        Returns
        -------
        NGrad: numPoint x numDim x numNodes array
            Shape function gradient values, NGrad[i][j][k] is the value of the kth shape function at the ith point w.r.t the kth
            parametric coordinate
        """
        NPrimeParam = np.zeros((paramCoords.shape[0], self.numDim, self.numNodes))
        NPrimeParam[:, 0, :] = LP.LagrangePoly1dDeriv(paramCoords, self.order + 1)
        return np.ascontiguousarray(NPrimeParam[:, :, self.shapeFuncToNodeOrder])

    def getIntegrationPointWeights(self, order=None):
        """Compute the integration point weights for a given quadrature order on this element

        Parameters
        ----------
        order : int
            Integration order

        Returns
        -------
        array of length numIntpoint
            Integration point weights
        """
        if order is None:
            order = self.quadratureOrder
        return getGaussQuadWeights(self.numDim, order)

    def getIntegrationPointCoords(self, order=None):
        """Compute the integration point parameteric coordinates for a given quadrature order on this element

        Parameters
        ----------
        order : int
            Integration order

        Returns
        -------
        numIntpoint x numDim array
            Integration point coordinates
        """
        if order is None:
            order = self.quadratureOrder
        return getGaussQuadPoints(self.numDim, order)

    def getReferenceElementCoordinates(self):
        """Get the node coordinates for the reference element, a.k.a the element on which the shape functions are defined

        For the quad element, the nodes of the reference element are simply in a order+1 x order+1 grid over the range [-1, 1] in both x and y, reordered as described by _getNodeReordering

        Returns
        -------
        numNodes x numDim array
            Element node coordinates
        """
        x = np.atleast_2d(np.linspace(-1, 1, self.numNodes)).T
        return x[self.shapeFuncToNodeOrder]

    # ==============================================================================
    # Private methods
    # ==============================================================================

    @staticmethod
    def _getNodeReordering(order):
        """Compute the reordering required between shape functions and nodes

        The 1d lagrange polynomial shape functions are ordered left to right, but the node ordering is defined
        differently, (e.g for a four node element it is 0-2-3-1). This method computes the reordering required to map
        the shape functions to the correct node ordering.

        Parameters
        ----------
        order : int
            Line element order

        Returns
        -------
        np.array
            Reordering array, array[i] = j indicates that the ith shape function should be reordered to the jth node
        """
        ordering = np.arange(order + 1)
        ordering[-1] = 1
        ordering[1:-1] += 1
        return ordering

__init__(order=1, numStates=None, quadratureOrder=None)

Create a new 1d line element object

Parameters

order : int, optional description, by default 1 numStates : type, optional description, by default None quadratureOrder : type, optional description, by default None

Source code in FEMpy/Elements/LineElement1D.py
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
def __init__(self, order=1, numStates=None, quadratureOrder=None):
    """Create a new 1d line element object

    Parameters
    ----------
    order : int, optional
        _description_, by default 1
    numStates : _type_, optional
        _description_, by default None
    quadratureOrder : _type_, optional
        _description_, by default None
    """
    if order < 1:
        raise ValueError("Order must be greater than 0")
    self.order = order
    numNodes = order + 1
    if quadratureOrder is None:
        # Compute quadrature order necessary to exactly intergrate polynomials of the same order as this element's
        # shape functions
        quadratureOrder = int(np.ceil((order + 1) / 2))

    super().__init__(numNodes, numDim=1, quadratureOrder=quadratureOrder, numStates=numStates)

    self.name = f"Order{self.order}-LagrangeLine"

    self.shapeFuncToNodeOrder = self._getNodeReordering(self.order)

computeShapeFunctionGradients(paramCoords)

Compute the derivatives of the shape functions with respect to the parametric coordinates at a given set of parametric coordinates

Parameters

paramCoords : numPoint x numDim array Array of parametric point coordinates to evaluate shape function gradients at

Returns

NGrad: numPoint x numDim x numNodes array Shape function gradient values, NGrad[i][j][k] is the value of the kth shape function at the ith point w.r.t the kth parametric coordinate

Source code in FEMpy/Elements/LineElement1D.py
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
def computeShapeFunctionGradients(self, paramCoords):
    """Compute the derivatives of the shape functions with respect to the parametric coordinates at a given set of parametric coordinates



    Parameters
    ----------
    paramCoords : numPoint x numDim array
        Array of parametric point coordinates to evaluate shape function gradients at

    Returns
    -------
    NGrad: numPoint x numDim x numNodes array
        Shape function gradient values, NGrad[i][j][k] is the value of the kth shape function at the ith point w.r.t the kth
        parametric coordinate
    """
    NPrimeParam = np.zeros((paramCoords.shape[0], self.numDim, self.numNodes))
    NPrimeParam[:, 0, :] = LP.LagrangePoly1dDeriv(paramCoords, self.order + 1)
    return np.ascontiguousarray(NPrimeParam[:, :, self.shapeFuncToNodeOrder])

computeShapeFunctions(paramCoords)

Compute the shape function values at a given set of parametric coordinates

Parameters

paramCoords : numPoint x numDim array Array of parametric point coordinates to evaluate shape functions at

Returns

N: numPoint x numNodes array Array of shape function values at the given parametric coordinates, N[i][j] is the value of the jth shape function at the ith parametric point

Source code in FEMpy/Elements/LineElement1D.py
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
def computeShapeFunctions(self, paramCoords):
    """Compute the shape function values at a given set of parametric coordinates

    Parameters
    ----------
    paramCoords : numPoint x numDim array
        Array of parametric point coordinates to evaluate shape functions at

    Returns
    -------
    N: numPoint x numNodes array
        Array of shape function values at the given parametric coordinates, N[i][j] is the value of the jth shape
        function at the ith parametric point
    """
    N = LP.LagrangePoly1d(paramCoords, self.order + 1)
    return np.ascontiguousarray(N[:, self.shapeFuncToNodeOrder])

getIntegrationPointCoords(order=None)

Compute the integration point parameteric coordinates for a given quadrature order on this element

Parameters

order : int Integration order

Returns

numIntpoint x numDim array Integration point coordinates

Source code in FEMpy/Elements/LineElement1D.py
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
def getIntegrationPointCoords(self, order=None):
    """Compute the integration point parameteric coordinates for a given quadrature order on this element

    Parameters
    ----------
    order : int
        Integration order

    Returns
    -------
    numIntpoint x numDim array
        Integration point coordinates
    """
    if order is None:
        order = self.quadratureOrder
    return getGaussQuadPoints(self.numDim, order)

getIntegrationPointWeights(order=None)

Compute the integration point weights for a given quadrature order on this element

Parameters

order : int Integration order

Returns

array of length numIntpoint Integration point weights

Source code in FEMpy/Elements/LineElement1D.py
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
def getIntegrationPointWeights(self, order=None):
    """Compute the integration point weights for a given quadrature order on this element

    Parameters
    ----------
    order : int
        Integration order

    Returns
    -------
    array of length numIntpoint
        Integration point weights
    """
    if order is None:
        order = self.quadratureOrder
    return getGaussQuadWeights(self.numDim, order)

getReferenceElementCoordinates()

Get the node coordinates for the reference element, a.k.a the element on which the shape functions are defined

For the quad element, the nodes of the reference element are simply in a order+1 x order+1 grid over the range [-1, 1] in both x and y, reordered as described by _getNodeReordering

Returns

numNodes x numDim array Element node coordinates

Source code in FEMpy/Elements/LineElement1D.py
142
143
144
145
146
147
148
149
150
151
152
153
def getReferenceElementCoordinates(self):
    """Get the node coordinates for the reference element, a.k.a the element on which the shape functions are defined

    For the quad element, the nodes of the reference element are simply in a order+1 x order+1 grid over the range [-1, 1] in both x and y, reordered as described by _getNodeReordering

    Returns
    -------
    numNodes x numDim array
        Element node coordinates
    """
    x = np.atleast_2d(np.linspace(-1, 1, self.numNodes)).T
    return x[self.shapeFuncToNodeOrder]