# Calculate Data from Expressions

Use the Calculate tool to create new field quantities using a python expression. The new fields can be derived from existing fields or be completely independent of other results in the dataset.

There are some important characteristics of the Calculate tool that need to be understood to use it effectively. When a new function is created, it is not immediately evaluated. Rather, the expression syntax is parsed and checked for validity. If an expression contains invalid functions or variables it will not be accepted by the calculate context and the text will revert back to the previous state. Once the expression is validated, it is added to the global variable list within the session of HyperMesh CFD. It is not until that expression is selected to use for contouring, streamline tracing, or generating an iso-surface that it is evaluated. When the expression is evaluated, it is evaluated on a local basis. For example, you create an expression for total pressure:

pTot = 0.5*density*velocity**2 + pressure

If you then choose to color a slice plane by pTot, it is calculated based on the local coordinates and results variables available on that slice plane. No information from the parent volume dataset is accessed. This is done to minimize memory overhead of the derived variables and to improve performance. However, if your expression includes gradients of quantities, it is important to note that the gradients will not be calculated on a global level. Rather, they will be evaluated using the data on the surface. In the case of a slice plane, this means that the gradients will not be accurate in the plane normal direction. This “calculate on demand” approach also has some implications for querying the fields prior to use. A number of features in the user interface rely on the ability to query the function range. One example is the range setting of the colormap. For pre-existing variables, the range is populated based on a query of the range of the scalar. Since derived fields are not computed a priori, the range inputs will not be populated with proper values.

Function/Variable | Description | Example | |
---|---|---|---|

Name | Expression | ||

gradient() | Calculates the gradient of a field | gradVel | gradient(velocity) |

mag() | Calculates the magnitude of an array | velMag | mag(velocity) |

strain() | Calculates the strain of a vector | velStrain | strain(velocity) |

eigenvalue() | Calculates the eigenvalue of an array | lambda2 | eigenvalue(velStrain**2.0 + (gradVel-velStrain)**2.0) |

cross() | Calculates the cross product of two vectors | powellParameter | cross(vorticity,velocity) |

curl() | Calculates the curl of a vector | vorticity | curl(velocity) |

divergence() | Calculates the divergence of an array | divVel | divergence(velocity) |

make_vector() | Creates a vector from three scalar fields | velocity_xy | make_vector(velocity[:,0],velocity[:,1],velocity[:,2]*0.0) |

Some functions above return vector and tensor quantities. At the current time, HyperMesh CFD has no way to know a priori what the return dimension of a given function will be. As such, results may be unpredictable for complex expressions. The expression validation also becomes more complex as nested functions are used. It is best to use multiple fields to build up complex expressions. For example, to compute the Q-criterion, first compute the gradient of the velocity, then sum the gradients in a separate expression to evaluate Q:

Name | Expression |
---|---|

gradVel | gradient(velocity) |

Q_criterion | -0.5*( gradVel[:,0,0]*gradVel[:,0,0] + gradVel[:,1,0]*gradVel[:,0,1] + gradVel[:,2,0]*gradVel[:,0,2] + gradVel[:,0,1]*gradVel[:,1,0] + gradVel[:,1,1]*gradVel[:,1,1] + gradVel[:,2,1]*gradVel[:,1,2] + gradVel[:,0,2]*gradVel[:,2,0] + gradVel[:,1,2]*gradVel[:,2,1] + gradVel[:,2,2]*gradVel[:,2,2] ) |