Пример #1
0
        public Matrix BuildStabilizingConductivityMatrix()
        {
            int numDofs    = Nodes.Count;
            var convection = Matrix.CreateZero(numDofs, numDofs);
            IReadOnlyList <double[]> shapeFunctions =
                Interpolation.EvaluateFunctionsAtGaussPoints(QuadratureForConsistentMass);
            IReadOnlyList <Matrix> shapeGradientsNatural =
                Interpolation.EvaluateNaturalGradientsAtGaussPoints(QuadratureForConsistentMass);

            for (int gp = 0; gp < QuadratureForConsistentMass.IntegrationPoints.Count; ++gp)
            {
                Vector shapeFunctionMatrix     = BuildShapeFunctionMatrix(shapeFunctions[gp]);
                var    jacobian                = new IsoparametricJacobian2D(Nodes, shapeGradientsNatural[gp]);
                Matrix shapeGradientsCartesian =
                    jacobian.TransformNaturalDerivativesToCartesian(shapeGradientsNatural[gp]);
                Matrix deformation  = BuildDeformationMatrix(shapeGradientsCartesian);
                Vector deformationX = deformation.GetRow(0);
                Vector deformationY = deformation.GetRow(1);
                //Matrix partial = shapeFunctionMatrix.TensorProduct(shapeFunctionMatrix);
                Matrix partial = deformationX.TensorProduct(deformationY);
                double dA      = jacobian.DirectDeterminant * QuadratureForConsistentMass.IntegrationPoints[gp].Weight;
                convection.AxpyIntoThis(partial, dA);
            }

            //WARNING: the following needs to change for non uniform density. Perhaps the integration order too.
            convection.ScaleIntoThis(-Math.Pow(material.ThermalConvection, 2));
            return(convection);
        }
Пример #2
0
        public Matrix BuildDiffusionConductivityMatrix()
        {
            int numDofs      = Nodes.Count;
            var conductivity = Matrix.CreateZero(numDofs, numDofs);
            IReadOnlyList <Matrix> shapeGradientsNatural =
                Interpolation.EvaluateNaturalGradientsAtGaussPoints(QuadratureForStiffness);

            for (int gp = 0; gp < QuadratureForStiffness.IntegrationPoints.Count; ++gp)
            {
                // Calculate the necessary quantities for the integration
                //Matrix constitutive = (Matrix)(materialsAtGaussPoints[gp].ConstitutiveMatrix); // ugly cast will be removed along with the legacy Matrix classes
                var    jacobian = new IsoparametricJacobian2D(Nodes, shapeGradientsNatural[gp]);
                Matrix shapeGradientsCartesian =
                    jacobian.TransformNaturalDerivativesToCartesian(shapeGradientsNatural[gp]);
                Matrix deformation = BuildDeformationMatrix(shapeGradientsCartesian);

                // Contribution of this gauss point to the element stiffness matrix
                Matrix partialK = deformation.Transpose() * deformation;
                //Matrix partialΚ = deformation.Transpose() * (constitutive * deformation);
                //partialK.Scale(materialsAtGaussPoints[gaussPoint].ThermalConductivity);

                double dA = jacobian.DirectDeterminant * QuadratureForStiffness.IntegrationPoints[gp].Weight; //TODO: this is used by all methods that integrate. I should cache it.
                conductivity.AxpyIntoThis(partialK, dA * material.ThermalConductivity);
            }

            conductivity.ScaleIntoThis(Thickness);
            return(conductivity);
        }
Пример #3
0
        public EvalInterpolation2D(IReadOnlyList <Node> elementNodes, double[] shapeFunctions, Matrix shapeGradientsNatural,
                                   IsoparametricJacobian2D jacobian)
        {
            int numNodes = elementNodes.Count;

#if DEBUG
            if ((shapeFunctions.Length != numNodes) || (shapeGradientsNatural.NumRows != numNodes))
            {
                throw new ArgumentException($"There are {numNodes} nodes, but {ShapeFunctions.Length} shape functions"
                                            + $" and {shapeGradientsNatural.NumRows} natural shape derivatives.");
            }
#endif
            this.elementNodes          = elementNodes;
            this.ShapeFunctions        = shapeFunctions;
            this.ShapeGradientsNatural = shapeGradientsNatural;
            this.Jacobian = jacobian;
            this.ShapeGradientsCartesian = jacobian.TransformNaturalDerivativesToCartesian(shapeGradientsNatural);
        }
        /// <summary>
        /// Calculate strains (exx, eyy, 2exy) and stresses (sxx, syy, sxy) at integration points, store them in the materials
        /// and return them (e.g. for postprocessing). The order of the tensors is the same as the order of the integration
        /// points defined by <see cref="QuadratureForStiffness"/>.
        /// </summary>
        /// <param name="localDisplacements"></param>
        /// <returns></returns>
        public (IReadOnlyList <double[]> strains, IReadOnlyList <double[]> stresses) UpdateStrainsStressesAtGaussPoints(
            double[] localDisplacements)
        {
            int numGPs   = QuadratureForStiffness.IntegrationPoints.Count;
            var strains  = new double[numGPs][];
            var stresses = new double[numGPs][];
            IReadOnlyList <Matrix> shapeGradientsNatural =
                Interpolation.EvaluateNaturalGradientsAtGaussPoints(QuadratureForStiffness);

            for (int gp = 0; gp < numGPs; ++gp)
            {
                IMatrixView constitutive             = materialsAtGaussPoints[gp].ConstitutiveMatrix;
                var         jacobian                 = new IsoparametricJacobian2D(Nodes, shapeGradientsNatural[gp]);
                Matrix      shapeGrandientsCartesian =
                    jacobian.TransformNaturalDerivativesToCartesian(shapeGradientsNatural[gp]);
                Matrix deformation = BuildDeformationMatrix(shapeGrandientsCartesian);

                strains[gp]  = deformation.Multiply(localDisplacements);
                stresses[gp] = constitutive.Multiply(strains[gp]);
            }

            return(strains, stresses);
        }
        public Matrix BuildStiffnessMatrix()
        {
            int numDofs   = 2 * Nodes.Count;
            var stiffness = Matrix.CreateZero(numDofs, numDofs);
            IReadOnlyList <Matrix> shapeGradientsNatural =
                Interpolation.EvaluateNaturalGradientsAtGaussPoints(QuadratureForStiffness);

            for (int gp = 0; gp < QuadratureForStiffness.IntegrationPoints.Count; ++gp)
            {
                // Calculate the necessary quantities for the integration
                IMatrixView constitutive            = materialsAtGaussPoints[gp].ConstitutiveMatrix;
                var         jacobian                = new IsoparametricJacobian2D(Nodes, shapeGradientsNatural[gp]);
                Matrix      shapeGradientsCartesian =
                    jacobian.TransformNaturalDerivativesToCartesian(shapeGradientsNatural[gp]);
                Matrix deformation = BuildDeformationMatrix(shapeGradientsCartesian);

                // Contribution of this gauss point to the element stiffness matrix
                Matrix partial = deformation.ThisTransposeTimesOtherTimesThis(constitutive);
                double dA      = jacobian.DirectDeterminant * QuadratureForStiffness.IntegrationPoints[gp].Weight;            //TODO: this is used by all methods that integrate. I should cache it.
                stiffness.AxpyIntoThis(partial, dA);
            }
            stiffness.ScaleIntoThis(Thickness);
            return(stiffness);
        }