[西门子] 西门子 TIA Portal 中用 SCL 语言进行浮点数计算精度分析

[复制链接]
查看906 | 回复0 | 2024-5-17 07:38:18 | 显示全部楼层 |阅读模式
介绍

熟悉不同的数据类型对于编写 PLC 程序至关重要。Real 是编程中广泛使用的数据类型之一。大多数 PLC 程序员都会忽略 TIA Portal 软件以六位小数的精度定义和计算 Real 数据类型,LReal 数据类型以十五位十进制数字的精度进行处理。这可能会导致意外结果。本教程将详细讨论这个问题以及可能的解决方案。

必备条件

学习本教程需要满足以下条件:

1.在计算机上安装 TIA Portal 软件。本教程将使用 TIA Portal V16,其它 TIA Portal 版本也适用。

2.知道如何在 TIA Portal 中创建 SCL 块。

3.了解 SCL 的基本指令。

浮点数精度表示

TIA Portal PLC 程序定义并计算数据类型 Real,精度为小数点后六位(10进制表示)。需要强调的是,这个精度一般适用于浮点数(Real)计算的每一步计算。

当您对浮点数进行加法和减法时,指数会进行调整。加减运算时,底数和指数都相等(对阶),只加尾数。

如图 1 所示,先将两个数据类型为 Real 的操作数(a 和 b)相加,再减去一个数据类型为 Real 的操作数(c)才能完成第一行计算。在第二个计算行中,将常量 1 除以之前的结果 (y),并将结果存储在操作数 z 中。

要完成此任务,您需要创建一个全局数据块,在其中定义操作数并创建一个函数,在其中对计算过程进行编程。



图 1 :计算公式示例

以下值被分配给操作数:



图 2 :操作数的值

首先,创建数据块“DB_GlobalData”。为此,请在左侧窗口中项目树下的“添加新块”上双击,然后将出现名为“添加新块”的对话框。选择数据块(DB)按钮并输入名称 DB_GlobalData 。然后,选择全局 DB 作为数据块类型,然后按 OK 按钮。



图 3 :创建全局数据块

在名称列下创建 a、b 和 c 标签作为静态变量,数据类型选择 Real,然后输入相关起始值,如图 4 所示。a 和 c 标签的起始值为 100000000.0(十进制)。通过数据类型浮点数 Real,该初始值被转换为 1.0E+08。



图 4 :在数据块中创建标签

现在,创建一个 SCL 函数。双击左侧窗口中的“添加新块”,将打开“添加新块”窗口。选择函数(FC)按钮并输入名称 FC_Calculate。然后,从语言下拉菜单中选择 SCL,然后按“确定”按钮。



图 5 :创建 SCL 块

当创建的 SCL 块打开时,单击向下箭头打开块接口。将 z 和 y 标签定义为名称列下的临时变量,并选择 Real 作为其数据类型。接下来,在 SCL 编辑器窗口中输入计算公式,如图 6 所示。



图 6 :.创建临时变量并编写程序代码

对于要在每个 PLC 循环扫描中执行的函数,必须由循环组织 OB Main 调用。为此,双击左侧窗口中的 OB Main,当 PLC 编程主窗口打开时,将创建的 SCL 块拖放到网络 1 上,如图 7 所示。



图 7 :在 OB Main 中调用 FC

现在可以通过建立与 PLC 的在线连接来查看功能中的结果。为此,左键单击顶部工具栏上的“启动仿真”图标,“下载预览”窗口将与 S7-PLCSIM Advanced(PLC 仿真器)一起打开。

在 TIA Portal 软件底部的巡视窗口中可以看到,整个 PLC 程序已成功编译,没有发现任何错误或警告。要继续,请按“装载”按钮。



图 8 :将程序下载到仿真器 - 第1步

当弹出“装载结果”窗口时,按“完成”按钮,程序开始下载到 PLC 仿真器。最后,通过单击 S7-PLCSIM Advanced 界面上的 RUN 按钮,将 PLC 仿真器置于运行模式。



图 9 :将程序下载到仿真器 - 第2步

现在,左键单击 SCL 编辑器工具栏中的眼镜图标(启用/禁用监视)即可以在线模式显示程序代码。



图 10 :在线模式下监控程序

正如您所看到的,操作数的结果是 #y = 0,期望值应为 1。这是为什么?



图 11 :程序结果与期望结果

以下是如何得出错误结果的。操作数 a 和 b 在计算的第一阶段相加。调整指数(对阶)后,两个操作数(a = 1.000000*10^8 和 b = 1.000000*10^0)的 Real 值如下:a = 1.000000*10^8和 b = 0.00000001*10^8。第二个数字(操作数 b)的最后两位数字被截断,因为其六位十进制数字的精度导致它们无法显示。结果,加 b 的操作变成加 0 而不是加 1。



图 12 :操作数 a 和 b 相加

在计算的第二阶段,从上一步计算的结果中减去操作数 c(中间结果:y = a + b – c = 1.000000*10^8 - 1.000000*10^8 = 0.000000e^0)。



图 13 :从之前的结果中减去操作数 c

在下一个计算步骤中,您在计算操作数 z 时,尝试将 1 除以 0,结果操作数 z 的值变成一个大数。



图 14 :计算操作数 z

有两种方法可以解决此问题。第一种解决方案:针对这种情况,您可以修改您的计算公式。不要在第一行计算中使用 y = a + b – c,而是将公式变成为 y = a – c + b。由于方程包括加法和减法,因此您可以更改操作数 b 和 c 的位置。因此,您应该首先通过单击顶部工具栏上的“离线”按钮将程序置于离线模式,然后开始在 SCL 编辑器窗口中编辑计算公式,如图15 所示。



图 15 :修改计算公式

您需要将修改后的程序下载到仿真器中才能查看结果。为此,请左键单击顶部工具栏上的“下载到设备”按钮以打开“下载预览”窗口,然后按“装载”按钮使程序进入在线模式。



图 16 :将修改后的程序下载到仿真器中

由于在这种情况下可以得到结果 0.000000e^0 ,因此在初始计算步骤(a – c = 1.000000*10^8 - 1.000000*10^8 = 0.000000*10^0)之后,将得到的 Real 数值(操作数 b)加到第二个计算步骤 (0.000000*10^0 + 1.000000*10^0 ) 得到期望的结果,即 1.000000*10^0。



图 17 :修改计算公式的结果

第二种解决方案是,如果您不想修改计算公式,可以将 Real 数据类型替换为 LReal 数据类型。LReal  数据类型以 15 位十进制数字的精度处理,之前的问题将几乎不会发生。

要应用此解决方案,请单击顶部工具栏中的“离线”按钮,使程序进入离线模式。然后双击左侧窗口中的数据块 DB_GlobalData,并使用之前的值创建三个名称分别为 a_LREAL、b_LREAL 和 c_LREAL 的新标签,每个标签的数据类型均为 LReal。



图 18 :在数据块中创建 LReal 标签

通过双击项目树中程序块文件夹下的函数 FC_Calculate,然后按块编辑器顶部的向下箭头,返回到 SCL 块接口。将名为 z_LREAL 和 y_LREAL 的两个新标签声明为 LReal 数据类型的临时变量。用新创建的 LReal 类型标签编辑程序代码。然后要查看结果,请左键单击顶部工具栏中的“下载到设备”按钮以打开“下载预览”窗口。



图 19 :创建 LReal 临时变量并修改程序代码

在“下载预览”对话框中,对于数据块,从“操作”下拉菜单中选择“重新初始化”,然后按“装载”按钮将程序下载到 PLC 仿真器中。



图 20 :将修改后的程序(LReal 类型)下载到仿真器

按 SCL 编辑器工具栏中的眼镜图标后,应用程序将以在线模式显示。正如您所看到的,没有再次遇到本教程开头讨论的问题,得到了操作数 y 和 z 的期望结果。



图 21 :修改计算公式的结果(LReal类型)

结论

本教程讨论了结构化控制语言 (SCL) 中的 Real 和 LReal 浮点数的计算。您了解到 Real 数据类型以六位十进制数字的精度进行处理,并且通常适用于 PLC 程序的每个计算步骤。此外,您还了解在处理浮点数值的加法或减法时,底数和指数是相等的(对阶)。

最后,您了解到有两种方法可以处理此问题。首先,您可以根据数学规则通过改变操作数的位置来修改您的计算公式。其次,您可以将 Real 数据类型替换为 LReal 数据类型,因为 LReal 数据类型以十五位十进制数字的精度进行处理。

对于浮点数大数加小数的应用场景,比如流量累加到一定值以后,会导致精度丢失,此时也可以选择第三种处理方法,即Kahan算法。关注后面文章会有讨论。



本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?注册哦

x
您需要登录后才可以回帖 登录 | 注册哦

本版积分规则