Skip to content

4.1 数学运算指令

本节将介绍PLC的数学运算指令

学习目标

  • 掌握基本数学运算指令
  • 理解数据溢出的处理
  • 能够进行复杂的数学计算

1. 数学运算概述

1.1 运算指令分类

PLC数学运算指令分类:

┌─────────────────────────────────────────────────────┐
│                   数学运算指令                       │
├────────────┬────────────┬────────────┬──────────────┤
│  基本运算   │  高级运算  │  数学函数  │  类型转换    │
├────────────┼────────────┼────────────┼──────────────┤
│ · ADD加    │ · MOD取模  │ · SIN正弦  │ · INT→REAL  │
│ · SUB减    │ · INC递增  │ · COS余弦  │ · REAL→INT  │
│ · MUL乘    │ · DEC递减  │ · TAN正切  │ · BCD↔BIN   │
│ · DIV除    │ · NEG取反  │ · SQRT平方根│ · 符号转换  │
└────────────┴────────────┴────────────┴──────────────┘

1.2 数据类型与运算

数据类型位数范围运算指令
INT16位-32768~32767ADD, SUB
DINT32位±21亿ADD_DI, SUB_DI
REAL32位浮点数ADD_R, SUB_R
UINT16位0~65535无符号运算

2. 加法指令(ADD)

2.1 基本概念

加法指令:将两个数相加,结果存入目标地址。

加法运算:

   ┌───────┐
   │ 加数1 │─────┐
   └───────┘     │    ┌───────┐
                 ├───→│  结果  │
   ┌───────┐     │    └───────┘
   │ 加数2 │─────┘
   └───────┘

公式:结果 = 加数1 + 加数2

2.2 加法指令梯形图

【梯形图】
              ┌──────────┐
   条件 ─────┤   ADD    │
              │          │
   加数1 ────┤IN1   OUT ├───── 结果
   加数2 ────┤IN2       │
              └──────────┘

【逻辑表达】
结果 := 加数1 + 加数2;

【数据类型】
· 整数加法(16位)
· 双整数加法(32位)
· 实数加法(浮点)

2.3 加法指令格式

【梯形图】
       条件
    ───┤├───────[ADD 源1 源2 目标]───

【指令格式】
ADD  [S1]  [S2]  [D]
· S1:加数1
· S2:加数2
· D:结果存储地址

【示例】
ADD  数据1  数据2  结果    // 结果 = 数据1 + 数据2
ADD  100    数据   结果    // 结果 = 100 + 数据

【连续加法(累加)】
ADD  数据   累加器  累加器   // 累加器 = 数据 + 累加器

2.4 溢出处理

加法溢出示例:

16位整数加法:
数据1 = 30000
数据2 = 10000
───────────────
结果 = 30000 + 10000 = 40000

但16位有符号整数最大值为32767
结果溢出!得到错误值

【解决方法】
1. 使用32位运算
2. 先判断是否会溢出
3. 使用浮点数运算

【溢出标志】
各品牌PLC都有溢出标志位,可用于检测运算溢出

3. 减法指令(SUB)

3.1 减法指令梯形图

【梯形图】
              ┌──────────┐
   条件 ─────┤   SUB    │
              │          │
   被减数 ───┤IN1   OUT ├───── 结果
   减数 ─────┤IN2       │
              └──────────┘

【逻辑表达】
结果 := 被减数 - 减数;

【数据类型】
· 整数减法(16位)
· 双整数减法(32位)
· 实数减法(浮点)

3.2 减法指令格式

【梯形图】
       条件
    ───┤├───────[SUB 源1 源2 目标]───

【指令格式】
SUB  [S1]  [S2]  [D]
· D = S1 - S2

【示例】
SUB  数据1  数据2  结果    // 结果 = 数据1 - 数据2
SUB  100    数据   结果    // 结果 = 100 - 数据

4. 乘法指令(MUL)

4.1 乘法特点

乘法运算注意事项:

16位 × 16位 = 可能需要32位结果

示例:
  30000 × 3 = 90000(超过16位范围)

因此乘法通常:
· 输入:16位
· 输出:32位(占用连续两个字)

三菱:
D0 × D10 → (D21,D20)
         高16位  低16位

4.2 乘法指令梯形图

【梯形图】
              ┌──────────┐
   条件 ─────┤   MUL    │
              │          │
   乘数1 ────┤IN1   OUT ├───── 结果
   乘数2 ────┤IN2       │
              └──────────┘

【逻辑表达】
结果 := 乘数1 × 乘数2;  // 结果用双整数存储

【数据类型】
· 整数乘法(16位输入,32位输出)
· 双整数乘法
· 实数乘法

4.3 乘法指令格式

【梯形图】
       条件
    ───┤├───────[MUL 源1 源2 目标]───

【16位乘法】
MUL  数据1  数据2  结果
· 数据1 × 数据2 → 结果(32位)
· 结果存储在连续两个字单元

【32位乘法】
· 对于大数据,使用32位乘法指令
· 结果可能为64位

5. 除法指令(DIV)

5.1 除法特点

除法运算结果:

被除数 ÷ 除数 = 商 ... 余数

示例:
17 ÷ 5 = 3 ... 2
    商=3,余数=2

三菱DIV指令结果存储:
D20 = 商
D21 = 余数

5.2 除法指令梯形图

【梯形图】
              ┌──────────┐
   条件 ─────┤   DIV    │
              │          │
   被除数 ───┤IN1   OUT ├───── 结果
   除数 ─────┤IN2       │
              └──────────┘

【逻辑表达】
商 := 被除数 / 除数;
余数 := 被除数 MOD 除数;

【数据类型】
· 整数除法(得商和余数)
· 双整数除法
· 实数除法(无余数)

5.3 除法指令格式

【梯形图】
       条件
    ───┤├───────[DIV 源1 源2 目标]───

【指令格式】
DIV  [S1]  [S2]  [D]
· D = S1 ÷ S2 的商
· D+1 = 余数(整数除法)

【示例】
DIV  17  5  结果
· 结果 = 3(商)
· 结果+1 = 2(余数)

【除零保护】
       条件         [除数<>0]
    ───┤├───────────┤├───────[DIV 被除数 除数 结果]───

重要:必须检查除数不为零!

5.4 除零错误处理

除零错误处理:

【错误做法】
DIV  数据  0  结果    // 除数为0,运行错误!

【正确做法】
// 先检查除数
       始终          [除数 <> 0]
    ───┤├───────────┤├───────[DIV 被除数 除数 结果]───

// 或使用条件判断(逻辑表达)
IF 除数 <> 0 THEN
    结果 := 被除数 / 除数;
ELSE
    结果 := 0;  // 或设置错误标志
END_IF;

6. 取模运算(MOD)

6.1 取模概念

取模运算:求除法的余数

示例:
17 MOD 5 = 2(17÷5=3...2)
10 MOD 3 = 1(10÷3=3...1)
8 MOD 4 = 0(8÷4=2...0,整除)

应用场景:
· 判断奇偶:N MOD 2(0为偶,1为奇)
· 循环计数:N MOD 10(0-9循环)
· 周期判断

6.2 取模指令使用

【逻辑表达】
余数 := 被除数 MOD 除数;

【示例】
// 判断奇偶
IF (计数器 MOD 2) = 0 THEN
    // 偶数
ELSE
    // 奇数
END_IF;

【通过DIV指令获取余数】
       条件
    ───┤├───────[DIV 被除数 除数 结果]───

结果+1单元中存储的就是余数

【提取余数】
MOV  结果+1  余数存储   // 将余数存入指定位置

7. 递增与递减指令

7.1 递增指令(INC)

递增:将指定地址的值加1

【梯形图】
              ┌──────────┐
   条件 ─────┤   INC    │
              │          │
   数据 ─────┤IN/OUT    │
              └──────────┘

或:
       条件
    ───┤├───────[INC 数据]───

效果:数据 = 数据 + 1

7.2 递减指令(DEC)

递减:将指定地址的值减1

【梯形图】
              ┌──────────┐
   条件 ─────┤   DEC    │
              │          │
   数据 ─────┤IN/OUT    │
              └──────────┘

或:
       条件
    ───┤├───────[DEC 数据]───

效果:数据 = 数据 - 1

8. 三角函数与数学函数

8.1 常用数学函数

函数功能说明输入单位
SIN正弦求角度正弦值弧度
COS余弦求角度余弦值弧度
TAN正切求角度正切值弧度
ASIN反正弦反三角函数-
SQRT平方根开平方-
LN自然对数以e为底-
EXPe的幂指数函数-
ABS绝对值取绝对值-

8.2 数学函数梯形图

【梯形图】
              ┌──────────┐
   条件 ─────┤   SIN    │
              │          │
   角度 ─────┤IN    OUT ├───── 结果
              └──────────┘

【逻辑表达】
// 三角函数(输入为弧度)
结果 := SIN(角度);     // 正弦
结果 := COS(角度);     // 余弦
结果 := TAN(角度);     // 正切

// 其他数学函数
结果 := SQRT(数值);    // 平方根
结果 := ABS(数值);     // 绝对值
结果 := LN(数值);      // 自然对数
结果 := EXP(数值);     // e的幂

// 角度转弧度
弧度 := 角度 × 3.14159 / 180.0;

8.3 数学函数应用示例

【SIN正弦】
       条件
    ───┤├───────[SIN 角度 结果]───
· 角度:输入角度值
· 结果:正弦值

【COS余弦】
       条件
    ───┤├───────[COS 角度 结果]───

【TAN正切】
       条件
    ───┤├───────[TAN 角度 结果]───

【SQRT平方根】
       条件
    ───┤├───────[SQRT 数据 结果]───
· 数据:被开方数
· 结果:平方根值

9. 数据类型转换

9.1 整数与实数转换

类型转换梯形图:

【整数→实数】
              ┌──────────┐
   条件 ─────┤ INT_TO_  │
              │  REAL    │
   整数 ─────┤IN    OUT ├───── 实数
              └──────────┘

【实数→整数】
              ┌──────────┐
   条件 ─────┤ REAL_TO_ │
              │  INT     │
   实数 ─────┤IN    OUT ├───── 整数
              └──────────┘

【逻辑表达】
实数值 := INT_TO_REAL(整数值);
整数值 := REAL_TO_INT(实数值);  // 四舍五入
整数值 := TRUNC(实数值);        // 截断

【取整方式】
TRUNC : 截断(3.7→3,-3.7→-3)
ROUND : 四舍五入(3.5→4)
FLOOR : 向下取整(3.7→3,-3.2→-4)
CEIL  : 向上取整(3.2→4)

9.2 BCD与BIN转换

BCD码与二进制转换:

BCD(Binary Coded Decimal):
· 每4位表示一个十进制数字
· 用于数码管显示

示例:
数值 1234
BIN: 0000 0100 1101 0010(0x04D2)
BCD: 0001 0010 0011 0100(0x1234)

【BIN→BCD】(用于数码管显示)
       条件
    ───┤├───────[BCD 数据 显示输出]───
· 将二进制数据转为BCD码输出到数码管

【BCD→BIN】(读取拨码开关)
       条件
    ───┤├───────[BIN 拨码输入 数据]───
· 将BCD输入转为二进制存入数据寄存器

10. 应用实例

10.1 温度换算(华氏↔摄氏)

公式:
°F = °C × 9/5 + 32
°C = (°F - 32) × 5/9

【梯形图实现】(整数运算避免小数)
// °F = °C × 9 / 5 + 32

       始终
    ───┤├───────[MUL 摄氏温度 9 中间值]───   // 中间值 = °C × 9
               [DIV 中间值 5 中间值]───      // 中间值 = 中间值 / 5
               [ADD 中间值 32 华氏温度]───   // °F = 中间值 + 32

【逻辑表达】(浮点运算)
华氏温度 := 摄氏温度 × 1.8 + 32.0;
摄氏温度 := (华氏温度 - 32.0) / 1.8;

10.2 流量计算

需求:根据流速和管径计算流量

公式:Q = π × r² × v × 3600
· Q:流量(m³/h)
· r:管道半径(m)
· v:流速(m/s)

【逻辑表达】
    半径 := 0.05;    // 50mm半径
    流量 := 3.14159 × 半径 × 半径 × 流速 × 3600.0;

10.3 平均值计算

需求:计算10个采样值的平均值

数据:采样值[0]-[9]存储10个采样值
结果:平均值

【梯形图】
       始终
    ───┤├───────[MOV 0 累加和]───         // 清零
               [ADD 采样值0 累加和 累加和]───  // 累加
               [ADD 采样值1 累加和 累加和]───
               ...
               [ADD 采样值9 累加和 累加和]───
               [DIV 累加和 10 平均值]───   // 除以10

【逻辑表达】(使用循环)
累加和 := 0;
FOR i := 0 TO 9 DO
    累加和 := 累加和 + 采样值[i];
END_FOR;
平均值 := 累加和 / 10;

10.4 PID增量计算

PID增量式算法:
Δu = Kp × (e(k) - e(k-1)) + Ki × e(k) + Kd × (e(k) - 2e(k-1) + e(k-2))

【逻辑表达】
// 定义变量
误差[0..2]   // 当前、上次、上上次误差
Kp, Ki, Kd  // PID参数
增量输出    // 输出增量

// 比例项
比例项 := Kp × (误差[0] - 误差[1]);

// 积分项
积分项 := Ki × 误差[0];

// 微分项
微分项 := Kd × (误差[0] - 2.0×误差[1] + 误差[2]);

// 总输出
增量输出 := 比例项 + 积分项 + 微分项;

// 误差移位(保存历史)
误差[2] := 误差[1];
误差[1] := 误差[0];

本节小结

数学运算指令要点:

┌────────────────────────────────────────────────────┐
│  基本运算                                          │
│  · ADD加法、SUB减法、MUL乘法、DIV除法            │
│  · 注意数据类型和溢出处理                         │
│  · 除法前检查除数不为零                           │
├────────────────────────────────────────────────────┤
│  特殊运算                                          │
│  · MOD取模:求余数                                │
│  · INC/DEC:递增/递减                             │
│  · NEG:取反                                      │
├────────────────────────────────────────────────────┤
│  数学函数                                          │
│  · 三角函数:SIN/COS/TAN(输入为弧度)           │
│  · 其他:SQRT/ABS/LN/EXP                         │
├────────────────────────────────────────────────────┤
│  类型转换                                          │
│  · INT↔REAL:整数与实数互转                      │
│  · BCD↔BIN:用于数码管显示                       │
└────────────────────────────────────────────────────┘

练习题

  1. 编写程序计算两个16位整数的平均值。
  2. 设计一个温度转换程序(摄氏转华氏)。
  3. 如何避免除法运算时的除零错误?
  4. 说明16位乘法结果为什么需要32位存储。

返回目录 | 下一节:4.2 移位与循环指令 →

本教程由 AI (Claude Opus 4.5) 生成,仅供学习参考