Skip to main content

Reconstructing specific APDL results with DPF

| 09.02.2022

This week’s Script Tip comes from Pierre Thieffry, Senior Principal R&D Engineer at Ansys.

While Mechanical offers a wide coverage of the capabilities available in our Structural solver, there are occasions where you will not find a specific result. Recently, a customer was asking for the ability to display SDSG results in Mechanical.

What is SDSG? Well, the documentation says, ‘Absolute value of the maximum variation of any nodal stress component’. In other words, SDSG is an element quantity that is the maximum difference between the nodal average value and the elemental nodal value for all nodes of the element (for all components of stress). This could for example help assess how well your results are converged and where you need to pay attention to your results

This very specific result is not available in standard. But DPF (the Data Processing Framework I was mentioning in an earlier Script Tip Friday) is there to help in such situations.

If we look at the definition of SDSG, we see two components in it: the nodal averaged values and the elemental nodal value for all nodes. Both results are standard results available through DPF (the following example is meant to be run in Mechanical):


dataSource = dpf.DataSources(your_result_file)

# Elemental nodal

stresses = 
dpf.operators.result.stress(data_sources=dataSource,requested_location='ElementalNodal')

stresses_field=stresses.outputs.getfields_container()[0]

# Nodal averaged

stresses_nodal=dpf.operators.averaging.elemental_nodal_to_nodal(field=stresses)

stresses_nodal_field=stresses_nodal.outputs.getfield()

So we just need to get the difference between both fields and we’ll be done. Yet this is not as simple as computing stresses_field-stresses_nodal_field since one field carries one value per node per element (so multiple values for a given node) and the other one carries one value per node. To work around this, we are going to create a new tensor field that will have the values of the nodal averaged field but defined on each node of each element. Then we’ll just have to perform the subtraction.


# New field to compute difference

elems=stresses.outputs.getfields_container()[0].MeshedRegionSupport.Elements

num_elems=len(elems)

nodal_toelemnodal_field=dpf.FieldsFactory.CreateTensorField(num_elems,'ElementalNodal')

# Loop over elements and their corner nodes

for el in elems:

nodes=el.CornerNodeIdsvalues=[]

# for each node, get nodal averaged value and affect it to new tensor field

for nid in nodes:

values.extend(stresses_nodal_field.GetEntityDataById(nid))

nodal_toelemnodal_field.Add(el.Id,values)

# compute stress difference

stress_difference=stresses-nodal_toelemnodal_field

Are we done? Not entirely. SDSG is an elemental quantity — so one value per element. There is a final step to take: for each element, compute the maximum (absolute) value of the above difference. Here again, we create a new scalar field on elemental location and simply find the value we are looking for.

# sdsg to compute difference

sdsg_field=dpf.FieldsFactory.CreateScalarField(num_elems,’Elemental’)

stress_difference_field=stress_difference.outputs.getfields_container()[0]

for el in elems:

eid=el.Id

str_values=stress_difference_field.GetEntityDataById(eid)

value=max(max(str_values),abs(min(str_values)))

sdsg_field.Add(eid,[value])

Et voilà! We’ve reconstructed our results. Checking on a very simple model shows that both APDL results and our DPF result match.

Static structural Python result and SDSG test
Static Structural Python Result and SDSG Test