Four brackets, one square design domain, one steel, one pair of bolts, one load point, and exactly the same number of cells of metal. Each is pulled down at the tip of its shelf until it collapses.
| shape | |
|---|---|
sharp |
an L-bracket with a square inside corner |
fillet |
the same L with that corner rounded |
gusset |
the same L with a triangular gusset across the corner |
topopt |
whatever SIMP topology optimisation does with the same budget |
Everything here is one file, reproduce.py, using only NumPy, SciPy and
Matplotlib. It runs on a CPU in a couple of minutes.
python -m pip install -r requirements.txt
python reproduce.py # 120 x 120 grid, about 3 minutes
python reproduce.py --quick # 80 x 80, about 1 minute
python reproduce.py --full # 160 x 160, the production mesh
python reproduce.py --mesh-study # adds the convergence evidence
Results land in results/: baseline_results.json, summary.csv and
figures/.
A sharp 90-degree re-entrant corner is an elastic stress singularity. The
field there goes as r^(λ-1) with λ ≈ 0.5445, so some material at that
corner is above yield at any load, however small. The sharp bracket has no
finite first-yield load. A number read off the peak element stress does not
measure one — it measures the element size, and it halves every time the mesh
does.
Less obvious, and found while building this: the filleted bracket's peak
stress does not settle either. A rasterised fillet is a staircase, and every
step is its own tiny re-entrant corner. Run --mesh-study and watch both peak
stresses wander by 20–30% between meshes while the collapse loads move by a
few per cent. Peak stress is simply not a rankable quantity on a grid.
So two mesh-independent numbers are reported instead:
P_limit— the collapse load, from an elastic–perfectly-plastic displacement-controlled path. This is the trophy. It converges because plasticity spreads the singular field over a finite plastic zone.P_damage— the load at which the yielded area first reaches 1% of the bracket. It converges because it integrates a field instead of sampling a singular one, and because it is an area fraction it does not quietly favour thick members over thin ones the way a fixed averaging length does.
Ranking rule, locked before the first production run: highest P_limit
wins; within 3% of each other, the higher P_damage takes it.
An earlier draft used the Theory of Critical Distances — von Mises averaged
over a disc of fixed radius L_c. It was dropped because L_c interacts with
member width: the optimised bracket's limbs are barely wider than the disc, so
the average diluted their stress and handed them a "yield load" 2.4× their own
local first yield. A length scale that is small compared with one candidate and
large compared with another is not a fair measurement.
Fairness here is asserted on the geometry that was actually built, never on the procedure that was supposed to build it.
- Equal mass is exact, not approximate. Each candidate's shape family is
written as an inclusion level — the smallest leg thickness at which a given
cell joins the shape — and the
n_solidcells of lowest level are taken. Every candidate therefore has the identical integer cell count. Bisecting a thickness until the count is close cannot do better than close, because the count is a step function of the thickness. - Bolts and load pad land on solid metal in every candidate, and
dof_of_nodesraises if they do not. There is no nearest-node fallback, on purpose: a silent fallback is how a fairness bug turns into a physics result. - The load is applied through a rigid pad, not at a point. A point load on a continuum is its own singularity.
- The optimiser cannot cheat: the metal under the bolts and under the pad is passive solid, its density field is thresholded to strict black-and-white at exactly the same cell count as the others, repaired to a single connected load path, and then analysed by the same solver with no SIMP penalisation anywhere. It competes as a plain shape.
- The optimiser was given stiffness, not strength. Minimum compliance is what topology optimisation is actually for. It is then judged on collapse load like everyone else. That mismatch is a disclosure, not a bug.
Two of them are identities, and they are the ones that matter:
| check | right answer | measured |
|---|---|---|
| patch test | a uniform strain field comes back exactly | ~4e-16 |
| plain bar in tension | collapses at exactly σ_y · A |
0.999996 |
| equal mass | identical integer cell count | exact |
--mesh-study adds the convergence evidence: the ranking is unchanged across
80/120/160, the collapse loads move by a few per cent, and the peak stresses do
not settle at all.
Not run here but run in production (see the video's report.md): a cantilever
against Timoshenko beam theory, a double-edge-notched bar reproducing the
plane-stress constraint factor 2/√3, an independent constant-strain-triangle
discretisation of the same meshes, Betti reciprocity, a symmetry check, the
Kirsch stress profile around a circular hole, and confound sweeps over the
damage threshold, the fillet radius, the load-pad size and the optimiser's
filter radius.
- 2D plane stress. A real bracket is a plate with out-of-plane bending and a bolt that clamps; none of that is here.
- Perfect plasticity, small strain. No hardening (deliberate — with hardening the load never plateaus and "the collapse load" becomes a displacement threshold somebody picked), no necking, no fracture, no buckling of the thin optimised limbs out of plane.
- The optimised bracket is a 2D optimum for this load case only. Give it a second load direction and it will look completely different.
Video: YOUTUBE_URL_HERE Code: GITHUB_URL_HERE