Script Tip Friday- Reconstructing specific APDL results with DPF
Before enjoying his Labor Day Weekend, Pierre Thieffry, Senior Principal R&D Engineer at Ansys, got busy writing another Script Tip Friday for all of us! Today, he writes about reconstructing specific APDL results with DPF. Thanks, Pierre.
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.CornerNodeIds
??? values=[]
??? # 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.
华为 - 博士后研究员
1 年good!