Neural Acceleration (MLP Surrogate): - Add run_nn_optimization.py with hybrid FEA/NN workflow - MLP architecture: 4-layer (64->128->128->64) with BatchNorm/Dropout - Three workflow modes: - --all: Sequential export->train->optimize->validate - --hybrid-loop: Iterative Train->NN->Validate->Retrain cycle - --turbo: Aggressive single-best validation (RECOMMENDED) - Turbo mode: 5000 NN trials + 50 FEA validations in ~12 minutes - Separate nn_study.db to avoid overloading dashboard Performance Results (bracket_pareto_3obj study): - NN prediction errors: mass 1-5%, stress 1-4%, stiffness 5-15% - Found minimum mass designs at boundary (angle~30deg, thick~30mm) - 100x speedup vs pure FEA exploration Protocol Operating System: - Add .claude/skills/ with Bootstrap, Cheatsheet, Context Loader - Add docs/protocols/ with operations (OP_01-06) and system (SYS_10-14) - Update SYS_14_NEURAL_ACCELERATION.md with MLP Turbo Mode docs NX Automation: - Add optimization_engine/hooks/ for NX CAD/CAE automation - Add study_wizard.py for guided study creation - Fix FEM mesh update: load idealized part before UpdateFemodel() New Study: - bracket_pareto_3obj: 3-objective Pareto (mass, stress, stiffness) - 167 FEA trials + 5000 NN trials completed - Demonstrates full hybrid workflow 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
10 KiB
Extractors Catalog Module
Last Updated: December 5, 2025 Version: 1.0 Type: Optional Module
This module documents all available extractors in the Atomizer framework. Load this when the user asks about result extraction or needs to understand what extractors are available.
When to Load
- User asks "what extractors are available?"
- User needs to extract results from OP2/BDF files
- Setting up a new study with custom extraction needs
- Debugging extraction issues
PR.1 Extractor Catalog
| ID | Extractor | Module | Function | Input | Output | Returns |
|---|---|---|---|---|---|---|
| E1 | Displacement | optimization_engine.extractors.extract_displacement |
extract_displacement(op2_file, subcase=1) |
.op2 |
mm | {'max_displacement': float, 'max_disp_node': int, 'max_disp_x/y/z': float} |
| E2 | Frequency | optimization_engine.extractors.extract_frequency |
extract_frequency(op2_file, subcase=1, mode_number=1) |
.op2 |
Hz | {'frequency': float, 'mode_number': int, 'eigenvalue': float, 'all_frequencies': list} |
| E3 | Von Mises Stress | optimization_engine.extractors.extract_von_mises_stress |
extract_solid_stress(op2_file, subcase=1, element_type='cquad4') |
.op2 |
MPa | {'max_von_mises': float, 'max_stress_element': int} |
| E4 | BDF Mass | optimization_engine.extractors.bdf_mass_extractor |
extract_mass_from_bdf(bdf_file) |
.dat/.bdf |
kg | float (mass in kg) |
| E5 | CAD Expression Mass | optimization_engine.extractors.extract_mass_from_expression |
extract_mass_from_expression(prt_file, expression_name='p173') |
.prt + _temp_mass.txt |
kg | float (mass in kg) |
| E6 | Field Data | optimization_engine.extractors.field_data_extractor |
FieldDataExtractor(field_file, result_column, aggregation) |
.fld/.csv |
varies | {'value': float, 'stats': dict} |
| E7 | Stiffness | optimization_engine.extractors.stiffness_calculator |
StiffnessCalculator(field_file, op2_file, force_component, displacement_component) |
.fld + .op2 |
N/mm | {'stiffness': float, 'displacement': float, 'force': float} |
| E11 | Part Mass & Material | optimization_engine.extractors.extract_part_mass_material |
extract_part_mass_material(prt_file) |
.prt |
kg + dict | {'mass_kg': float, 'volume_mm3': float, 'material': {'name': str}, ...} |
For Zernike extractors (E8-E10), see the zernike-optimization module.
PR.2 Extractor Code Snippets (COPY-PASTE)
E1: Displacement Extraction
from optimization_engine.extractors.extract_displacement import extract_displacement
disp_result = extract_displacement(op2_file, subcase=1)
max_displacement = disp_result['max_displacement'] # mm
max_node = disp_result['max_disp_node'] # Node ID
Return Dictionary:
{
'max_displacement': 0.523, # Maximum magnitude (mm)
'max_disp_node': 1234, # Node ID with max displacement
'max_disp_x': 0.123, # X component at max node
'max_disp_y': 0.456, # Y component at max node
'max_disp_z': 0.234 # Z component at max node
}
E2: Frequency Extraction
from optimization_engine.extractors.extract_frequency import extract_frequency
# Get first mode frequency
freq_result = extract_frequency(op2_file, subcase=1, mode_number=1)
frequency = freq_result['frequency'] # Hz
# Get all frequencies
all_freqs = freq_result['all_frequencies'] # List of all mode frequencies
Return Dictionary:
{
'frequency': 125.4, # Requested mode frequency (Hz)
'mode_number': 1, # Mode number requested
'eigenvalue': 6.21e5, # Eigenvalue (rad/s)^2
'all_frequencies': [125.4, 234.5, 389.2, ...] # All mode frequencies
}
E3: Stress Extraction
from optimization_engine.extractors.extract_von_mises_stress import extract_solid_stress
# For shell elements (CQUAD4, CTRIA3)
stress_result = extract_solid_stress(op2_file, subcase=1, element_type='cquad4')
# For solid elements (CTETRA, CHEXA)
stress_result = extract_solid_stress(op2_file, subcase=1, element_type='ctetra')
max_stress = stress_result['max_von_mises'] # MPa
Return Dictionary:
{
'max_von_mises': 187.5, # Maximum von Mises stress (MPa)
'max_stress_element': 5678, # Element ID with max stress
'mean_stress': 45.2, # Mean stress across all elements
'stress_distribution': {...} # Optional: full distribution data
}
E4: BDF Mass Extraction
from optimization_engine.extractors.bdf_mass_extractor import extract_mass_from_bdf
mass_kg = extract_mass_from_bdf(str(dat_file)) # kg
Note: Calculates mass from element properties and material density in the BDF/DAT file.
E5: CAD Expression Mass
from optimization_engine.extractors.extract_mass_from_expression import extract_mass_from_expression
mass_kg = extract_mass_from_expression(model_file, expression_name="p173") # kg
Note: Requires _temp_mass.txt to be written by solve journal. The expression name is the NX expression that contains the mass value.
E6: Field Data Extraction
from optimization_engine.extractors.field_data_extractor import FieldDataExtractor
# Create extractor
extractor = FieldDataExtractor(
field_file="results.fld",
result_column="Temperature",
aggregation="max" # or "min", "mean", "sum"
)
result = extractor.extract()
value = result['value'] # Aggregated value
stats = result['stats'] # Full statistics
E7: Stiffness Calculation
# Simple stiffness from displacement (most common)
applied_force = 1000.0 # N - MUST MATCH YOUR MODEL'S APPLIED LOAD
stiffness = applied_force / max(abs(max_displacement), 1e-6) # N/mm
# Or using StiffnessCalculator for complex cases
from optimization_engine.extractors.stiffness_calculator import StiffnessCalculator
calc = StiffnessCalculator(
field_file="displacement.fld",
op2_file="results.op2",
force_component="Fz",
displacement_component="Tz"
)
result = calc.calculate()
stiffness = result['stiffness'] # N/mm
E11: Part Mass & Material Extraction
from optimization_engine.extractors import extract_part_mass_material, extract_part_mass
# Full extraction with all properties
result = extract_part_mass_material(prt_file)
mass_kg = result['mass_kg'] # kg
volume = result['volume_mm3'] # mm³
area = result['surface_area_mm2'] # mm²
cog = result['center_of_gravity_mm'] # [x, y, z] mm
material = result['material']['name'] # e.g., "Aluminum_2014"
# Simple mass-only extraction
mass_kg = extract_part_mass(prt_file) # kg
Return Dictionary:
{
'mass_kg': 0.1098, # Mass in kg
'mass_g': 109.84, # Mass in grams
'volume_mm3': 39311.99, # Volume in mm³
'surface_area_mm2': 10876.71, # Surface area in mm²
'center_of_gravity_mm': [0, 42.3, 39.6], # CoG in mm
'material': {
'name': 'Aluminum_2014', # Material name (or None)
'density': None, # Density if available
'density_unit': 'kg/mm^3'
},
'num_bodies': 1 # Number of solid bodies
}
Prerequisites: Run the NX journal first to create the temp file:
run_journal.exe nx_journals/extract_part_mass_material.py -args model.prt
Extractor Selection Guide
| Need | Extractor | When to Use |
|---|---|---|
| Max deflection | E1 | Static analysis displacement check |
| Natural frequency | E2 | Modal analysis, resonance avoidance |
| Peak stress | E3 | Strength validation, fatigue life |
| FEM mass | E4 | When mass is from mesh elements |
| CAD mass | E5 | When mass is from NX expression |
| Temperature/Custom | E6 | Thermal or custom field results |
| k = F/δ | E7 | Stiffness maximization |
| Wavefront error | E8-E10 | Telescope/mirror optimization |
| Part mass + material | E11 | Direct from .prt file with material info |
Engineering Result Types
| Result Type | Nastran SOL | Output File | Extractor |
|---|---|---|---|
| Static Stress | SOL 101 | .op2 |
E3: extract_solid_stress |
| Displacement | SOL 101 | .op2 |
E1: extract_displacement |
| Natural Frequency | SOL 103 | .op2 |
E2: extract_frequency |
| Buckling Load | SOL 105 | .op2 |
extract_buckling |
| Modal Shapes | SOL 103 | .op2 |
extract_mode_shapes |
| Mass | - | .dat/.bdf |
E4: bdf_mass_extractor |
| Stiffness | SOL 101 | .fld + .op2 |
E7: stiffness_calculator |
Common Objective Formulations
Stiffness Maximization
- k = F/δ (force/displacement)
- Maximize k or minimize 1/k (compliance)
- Requires consistent load magnitude across trials
Mass Minimization
- Extract from BDF element properties + material density
- Units: typically kg (NX uses kg-mm-s)
Stress Constraints
- Von Mises < σ_yield / safety_factor
- Account for stress concentrations
Frequency Constraints
- f₁ > threshold (avoid resonance)
- Often paired with mass minimization
Adding New Extractors
When the study needs result extraction not covered by existing extractors (E1-E10):
STEP 1: Check existing extractors in this catalog
├── If exists → IMPORT and USE it (done!)
└── If missing → Continue to STEP 2
STEP 2: Create extractor in optimization_engine/extractors/
├── File: extract_{feature}.py
├── Follow existing extractor patterns
└── Include comprehensive docstrings
STEP 3: Add to __init__.py
└── Export functions in optimization_engine/extractors/__init__.py
STEP 4: Update this module
├── Add to Extractor Catalog table
└── Add code snippet
STEP 5: Document in SYS_12_EXTRACTOR_LIBRARY.md
See EXT_01_CREATE_EXTRACTOR for full guide.
Cross-References
- System Protocol: SYS_12_EXTRACTOR_LIBRARY
- Extension Guide: EXT_01_CREATE_EXTRACTOR
- Zernike Extractors: zernike-optimization module
- Core Skill: study-creation-core