工程师平台
Abaqus 实战2026-09-07

两个用得少但各有一个必踩的结构坑

damage 块下面还有两个模型用得少但坑不小:剪切损伤和成形极限图。 剪切损伤的那个 ks 参数是个标量,不是表的一列, 当成列写进去会得到一条看起来毫不相干的报错;成形极限图的两列顺序是次应变在前、主应变在后,写反了不报错,但你的极限曲线会整个翻过来。 这篇把两个模型的字段讲清楚,最后给一张四个损伤模型的校验策略对照表 —— 那张表是把插件源码四个分支逐行比出来的,比记规则管用。
ks 写在表外面
它是和 table 并列的一个标量字段,塞进表里会让行宽多一列,触发表宽或缺键报错。
FLD 是 minor 在前
两列的顺序是 minorStrain、majorStrain,和 FLD 图的横纵轴一致,但和大多数人报数的习惯相反。
负的次应变是合法的
插件对 fld 两列一个校验都没做,因为 FLD 左半支的次应变本来就是负值。

01剪切损伤的三列,和那个不是列的 ks

damage.shear 的表结构和韧性损伤长得很像,也是三列:

_rows(sub, ('fractureStrain', 'shearStressRatio', 'strainRate'), 'damage.shear')
字段名含义取值
第 1 列fractureStrain该剪切应力比下的等效塑性断裂应变≥ 0(0 合法)
第 2 列shearStressRatio剪切应力比按标定
第 3 列strainRate等效塑性应变率≥ 0
第 4 列(温度)多写一列时才有按你的温标

和韧性损伤的差别只在第 2 列:那边是应力三轴度,这边是剪切应力比。 两个模型可以同时挂在一个材料上,分别捕捉拉伸主导和剪切主导两种失效路径, Abaqus 会各自判断。

真正要注意的是 ks。源码里它是这么处理的:

if 'ks' in sub:
    kwargs['ks'] = float(sub['ks'])

它被放进 kwargs,和 table并列的两个参数。 换成 JSON 的话就是:

"damage": {
  "shear": {
    "ks": 0.3,
    "table": [
      [0.30, 1.0, 0.001],
      [0.22, 2.0, 0.001]
    ],
    "evolution": { "type": "ENERGY", "fractureEnergy": 10 }
  }
}
这些数字是结构示意值,示例库里没有 shear 块
上面这些数字是结构示意值,只为演示层级和列数。 插件自带的示例库里没有 shear 块,所以这里给不出可对照的演示数据, 更不能拿别处的数字冒充。真做项目必须用自己标定的参数。

kstable 外面、和它同级。写进表里会怎样? 假设你把它当第 4 个数写进每一行,插件的表宽推断会把它当成温度列 (规则见 温度相关表那篇), 于是不报错、静默变成温度相关表,而 ks 根本没传给 Abaqus。 要是只在某一行加了,就会撞上:

damage.shear: all rows must have the same length

这条报错指向表宽,你会以为是列数问题,其实根因是把标量当列了。ks 不写就是不传,Abaqus 用它自己的默认值。

02FLD 只有两列,而且次应变在前

成形极限图的表最简单,只有两列 —— 但顺序是最容易写反的:

_rows(sub, ('minorStrain', 'majorStrain'), 'damage.fld')
字段名含义符号
第 1 列minorStrain次应变,板面内较小的那个主应变可正可负
第 2 列majorStrain主应变,板面内较大的那个主应变通常为正
第 3 列(温度)多写一列时才有按你的温标
次应变在前、主应变在后
次应变在前、主应变在后。这个顺序和 FLD 图的画法一致(横轴次应变、纵轴主应变), 但和大多数人报数时"先说主应变"的习惯正好相反。写反了两列都是合法数字,插件不会报错,你得到的是一条镜像翻转的极限曲线。

怎么自查?看第 1 列有没有负数。一条完整的成形极限曲线必然跨过纵轴: 左半支是拉—压变形(深拉延),次应变为负;右半支是双向拉伸(胀形),次应变为正。 所以正常的 FLD 表,第 1 列一定有负值。如果第 1 列全是正数、 第 2 列反而出现负数,基本可以断定两列写反了。

插件对这两列一个校验都没做,源码里 fld 分支没有任何_checkColumn 调用。这正是因为负的次应变是物理必需的 —— 要是照韧性损伤那样查非负,FLD 的左半支就没法填了。

"damage": {
  "fld": {
    "table": [
      [-0.20, 0.52],
      [-0.10, 0.42],
      [ 0.00, 0.36],
      [ 0.10, 0.40],
      [ 0.20, 0.46]
    ],
    "evolution": { "type": "DISPLACEMENT", "value": 0.2 }
  }
}
同样是结构示意值,看的是形状不是数值
同样是结构示意值,示例库里没有 fld 块可供对照。 这里想演示的是形状:次应变从负到正、主应变在次应变为 0 附近取到最低点, 两侧回升 —— 这就是 FLD 曲线的典型 V 形。真实曲线要用自己的成形极限试验数据。

fld 支持温度相关,多给一列就是温度。这一点和Johnson-Cook不同 —— 那个模型的源码把温度标志丢弃了,因为温度已经是它的显式参数。

还有一点要清楚:FLD 是板料成形的准则, 用在壳单元上才有意义。拿它去评价一个实体单元建的锻件,模型跑得动,结论不可信。

03四个损伤模型的校验策略对照表

这张表是把插件源码 _addDamage() 的四个分支逐行比出来的, 记住它比记住每个模型的规则划算 —— 因为插件查不查,反映的是那一列是不是物理量

模型列数第 1 列查非负吗接温度列吗额外标量
ductile3fractureStrain查(0 合法)
shear3fractureStrain查(0 合法)ks
johnsonCook8d1不查不接
fld2minorStrain不查
逐行对照 materialImporterKernel.py 的 _addDamage() 四个分支得出

读法:

  • 查非负的那两个(ductile、shear),第 1 列都是断裂应变 —— 一个真实的物理量,负数无意义,所以插件拦。
  • 不查的那两个,一个第 1 列是拟合系数 d1(示例里就是 -0.77), 一个第 1 列是次应变(左半支必须为负)。都是负值合法,所以插件不拦。
  • 唯一不接温度列的是 johnsonCook,因为温度是它表里的第 6、7 列, 已经显式给了。
  • 唯一有额外标量的是 shear,就是那个 ks

那两个"查非负"的报错串是这个形状(形容词会随允许零与否变化):

damage.shear: fractureStrain must be non-negative, got -0.1

而演化那一层的校验没带允许零的参数,所以它的形容词是另一个:

damage.fld.evolution: displacementAtFailure must be positive, got 0

这两个词(non-negativepositive)是判断报错来自哪一层的最快线索,韧性损伤那篇的第 4 节把这对差别讲透了。

04演化子块:四个模型共用同一套规则

好消息是 evolution 的规则四个模型完全一致,源码里就是同一个函数在处理。 所以韧性损伤那篇学到的东西,剪切和 FLD 直接照搬:

字段不写会怎样说明
type插件按 DISPLACEMENT 处理决定下面读哪个字段名
displacementAtFailuretype 为 DISPLACEMENT 时读它,量纲是长度
fractureEnergytype 为 ENERGY 时读它,量纲是能量除面积
value前两个都没写时才会去读的兜底字段名
softening插件不传,走 Abaqus 那端的默认软化规律
degradation插件不传,走 Abaqus 那端的默认多个损伤准则并存时怎么合并

注意后两行和第一行的区别。type 的默认值是插件给的 —— 源码里无条件解析了一次,不写就是 DISPLACEMENT。 而 softeningdegradation写了才传, 不写的话插件根本不把这两个参数交给 Abaqus,最终用什么由 Abaqus 那一端决定。

degradation 在剪切损伤这里特别值得显式写出来。如果你给同一个材料同时挂了韧性损伤和剪切损伤(这是常见做法), Abaqus 手里就有两个损伤变量,得决定怎么合并。写 MAXIMUM 是取两者较大值, 也就是哪条路径先坏就按那条算 —— 这通常是你想要的。 既然插件不写就不传,那就别赌,直接写出来

演化值必须严格大于 0,四个模型都一样
演化值必须严格大于 0,四个模型都一样。 起始表里的断裂应变可以是 0,演化值不行 —— 源码里这两处调用同一个校验函数,区别只在一个参数。

单位问题也一样:displacementAtFailure 是长度,跟着单位制走, 而且和网格尺寸耦合;fractureEnergy 是单位面积能量,网格细化时收敛。 换算表在单位制那篇里。

05这两个模型上会看到的报错,以及它们的真实原因

插件的表解析报错是四个模型共用的,串的开头会带上路径(比如damage.sheardamage.fld.evolution), 所以先看冒号前面那一段,就知道错在哪一层

报错串字面意思在这两个模型上的常见真实原因
all rows must have the same length各行列数不一致把 ks 当列塞进了部分行
missing key(s) value缺 value 字段evolution 的 type 和字段名不配套,比如写了 ENERGY 却填 displacementAtFailure
"table" is empty表是空的留了 "table": [] 占位没删
row ... is not a list of numbers某行不是数字列表FLD 数据从表格里拷来,某行带了引号或空串
values must be numbers值不是数字负号写成了全角,或者数字里混了空格
expected an object with ...这一层不是对象直接写成 "fld": [[...]],漏了外面的 { "table": ... }

最后一条值得单独说。fld 只有两列,看着像个纯数组, 于是很多人会直接写 "fld": [[-0.2, 0.52], ...]插件要的是一个对象,表得放在里面的 table 键下 —— 因为还得有地方放 evolution。报错串会告诉你它期望什么, 照着字面改就行。

全角负号那一条在实际支持里出现频率不低,因为中文输入法下打减号很容易带出全角。 这类字符问题在 JSON 字段说明里也提过, 用编辑器的 JSON 校验先过一遍能省不少时间。

06提交前照着过一遍

  1. 剪切损伤:每行正好三个数,顺序是断裂应变、剪切应力比、应变率;第 1 列没有负数。
  2. ks 写在 table 外面、和它同级; 不需要就整个不写。
  3. FLD:每行正好两个数,次应变在前; 第 1 列应该有负值,全是正数就要怀疑写反了。
  4. FLD 的主应变随次应变呈 V 形,最低点在次应变 0 附近。
  5. FLD 用在壳单元上;实体单元建的模型别套这个准则。
  6. 两个模型都有 evolution 子块,值大于 0type 和字段名配套。
  7. 同时挂了多个损伤准则时,显式写出 degradation, 别依赖不传时 Abaqus 那端的默认。
  8. 材料里已经有 plastic 块 —— 损伤是叠在塑性之上的, 塑性表本身的坑见塑性表那六种报错
一眼就能做完的自查
FLD 那条自查最好用:第 1 列有没有负数。 一行代码都不用跑,扫一眼就知道两列有没有写反 —— 而这是这个模型上唯一一个不报错却会让结果整个失真的错法。

常见问题

ks 应该写在 table 里还是外面?

外面,和 table 同级。插件源码把它当标量处理,放进 kwargs 传给 Abaqus,和 table 是并列的两个参数。如果你把它当第 4 个数写进每一行,插件的表宽推断会把它当成温度列,不报错但 ks 根本没传进去;只在某一行加,会报 damage.shear: all rows must have the same length。不需要这个参数就整个不写,Abaqus 用自己的默认值。

FLD 表的两列哪个在前?

次应变在前,主应变在后,字段名是 minorStrain 和 majorStrain。这个顺序和 FLD 图的横纵轴一致,但和大多数人报数时先说主应变的习惯相反。写反了两列都是合法数字,插件不会报错,你会得到一条镜像翻转的极限曲线。自查方法是看第 1 列有没有负数,正常的成形极限曲线一定跨过纵轴,左半支的次应变为负。

minorStrain 是负数插件为什么不拦?

因为负的次应变是物理必需的。FLD 左半支对应拉压变形也就是深拉延,次应变本来就是负值。插件源码里 fld 分支没有任何列校验调用,而 ductile 和 shear 分支都要求第一列非负,那两列是断裂应变,负数无意义。看插件查不查,就能判断那一列是物理量还是可以取负的量。

韧性损伤和剪切损伤能同时用吗?

能,而且是常见做法,分别捕捉拉伸主导和剪切主导两种失效路径。这时 Abaqus 手里有两个损伤变量,怎么合并由 evolution 里的 degradation 决定,写 MAXIMUM 是取两者较大值也就是哪条路径先坏就按那条算。要注意插件对这个字段是写了才传,不写就整个参数不交给 Abaqus,最终用什么由 Abaqus 那一端决定,所以想明确控制就显式写出来,别赌默认值。

FLD 能加温度列吗?

能。fld 分支接收并使用了插件的温度相关标志,多给一列就是温度。这一点和 Johnson-Cook 失效不同,那个模型的源码把温度标志丢弃了,因为温度已经是它表里的第 6、7 列。四个损伤模型里只有 johnsonCook 不接温度列。

为什么我写 "fld": [[-0.2, 0.52]] 会报 expected an object?

因为插件要的是一个对象,表得放在对象里的 table 键下面。fld 只有两列,看着像纯数组,很容易直接写成数组,但那样就没地方放 evolution 子块了。正确写法是 "fld": { "table": [[-0.2, 0.52], ...], "evolution": {...} }。报错串里会写明它期望什么字段,照着字面改即可。

这一步可以不自己做

FLD 表扫一眼第 1 列有没有负数 —— 一行代码都不用跑, 就能抓住这个模型上唯一一个不报错却让结果整个失真的错法。

在线材料库需要 Abaqus 2023 或更高版本;2022 及更早只能用本地 JSON 材料库。