三菱PLC高效编程:SUM、BON、DECO、ENCO、ZRST指令实战详解
1. 项目概述为什么这几个指令值得单独拿出来讲做三菱PLC项目时间久了你会发现真正难的不是起保停电路也不是模拟量换算而是那些“看起来很简单用起来却总差一口气”的指令。SUM、BON、DECO、ENCO、ZRST这五个指令很多人可能都见过但真正能在项目里熟练组合使用的人不多。我最初接触这几个指令是在一条8工位料盘检测设备上当时的痛点很直接8个传感器信号要统计数量、要判断某个位置的物料状态、要让不同工位的气缸按顺序动作还要在每批次结束后把几十个软元件全部清零。如果用传统写法程序冗长不说后期调试改起来也相当痛苦。最后我把这几个指令组合起来程序行数直接少了一半而且逻辑清晰了很多。这几条指令本质上解决的是三块问题第一位状态与数值之间的转换第二批量数据的快速处理第三程序初始化与批次收尾的批量复位。SU M负责统计一个字或双字里ON位的数量BON负责把某一位的状态提取出来DECO和ENCO是一对互逆的编码解码指令它们实现“数值”和“位位置”之间的映射ZRST则是区间复位指令一条指令把连续的一批软元件全部清零。我把它们放在一起讲是因为它们在真实项目中经常需要配合使用单独看每个指令都比较简单但组合起来能玩出很多花样。这套指令适合谁看我认为主要有三类人。第一类是刚学完基础指令、准备做实际项目的PLC初学者你会发现这几个指令能替你做很多“脏活累活”第二类是已经在做设备维护或改造的电气工程师当你接手别人程序时能快速看懂这几个指令能减少很多沟通成本第三类是准备参加技能竞赛或考取三菱PLC相关证书的人这几个指令在题目里出现频率相当高。下面我从原理到实操逐一拆解。2. 从整体上看这五个指令的设计思路2.1 数据与状态的转换关系PLC编程里有一个永恒的话题数据寄存器里存的数值怎么和设备现场的“状态”对应起来。八个传感器接在X0到X7上它们在PLC内部会组成一个字节的位状态但这个状态怎么变成我们可以做算术运算的数字反过来我们算出来一个数字5怎么让它变成某一台设备动作的信号这中间的桥梁就是DECO和ENCO这对指令。而SUM和BON则是在位状态和数值之间的另外两个方向SUM把一个字的位状态汇总成一个数量值BON则把一个字里的某一位单独提取出来变成一个位软元件。我举个例子你就明白了。一台设备有8个故障报警信号分别存在D100的bit0到bit7里。如果你想知道“当前有几个报警”用SUM一条指令完成如果你想知道“第3号报警有没有发生”用BON一条指令就能把bit2的状态拿出来如果HMI上要用一个数字表示“当前最先处理哪个报警”用ENCO就能把报警位里编号最大的那个转换成数字如果要在触摸屏上做一个“选中第几号配方”的操作把配方编号数字通过DECO变成选通位就可以一次性启用对应的配方数据块。这几个指令组合起来几乎覆盖了状态监控、故障诊断、配方管理、动作选通这些所有现场工程师都会遇到的场景。2.2 使用这些指令带来的实际收益从工程效率来说这几个指令是典型的“一条顶一屏”。例如统计ON数量如果不用SUM你就要写一个循环程序用ROR指令逐位移位再用CMP比较每一位是否为1程序写下来大概要二十多步。但如果用SUM一行指令就结束了扫描时间也短得多。同样ZRST对比多个MOV K0指令优势更加明显。程序步数减少不仅意味着扫描周期缩短更重要的是程序的可读性和可维护性大幅提升。当设备出了问题别人打开你的程序看到SUM、DECO这种语义明确的指令一眼就能明白你这段程序在做什么而不是在一堆比较指令里猜你的意图。2.3 这些指令的适用PLC平台我以三菱FX系列为主来讲解因为FX系列在中小型设备里用得最多。FX3U、FX3GA、FX5U都支持这些指令但要注意FX5U的编程软件是GX Works3它的指令格式和GX Works2有一些界面上的差异好在指令名称和操作数规则基本一致。Q系列和L系列也支持这些指令它们的软元件编号规则不同但指令功能是相同的。如果你用的是FX3G或者更老款的FX2N部分指令可能需要确认一下FX2N也支持SUM、BON、DECO、ENCO、ZRST属于应用指令区但要留意程序步容量。3. SUM与BON从事数据统计到位状态提取3.1 SUM指令的原理与用法SUM指令的功能是统计源操作数中ON位的总数并把结果存入目标操作数。它的指令格式是 SUM S D其中S是源操作数可以是数据寄存器D、文件寄存器R等字软元件D是目标操作数用来存放统计结果。16位指令SUM统计的是S中bit0到bit15共16个位的ON数量结果范围是0到1632位指令DSUM统计的是源操作数中32个位的ON数量结果范围是0到32。举个例子。D0里面存放的数值是二进制 0000 0000 0011 0101也就是bit0、bit2、bit4、bit5这4个位是ON那么执行 SUM D0 D10 后D10的值就是4。注意这里统计的是“有多少位是1”和D0的数值大小没有直接关系。D0等于60和D0等于15只要ON位的数量相同SUM的结果就一样。实际项目里我常用SUM做“多传感器状态汇总”。比如一台设备有12个安全门开关分别接到PLC的输入点上我需要知道当前关闭了几个门用于判断设备是否满足安全启动条件。用传统逻辑要写12个触点并联或串联而把12个输入状态通过BMOV批量移动到D20后一条 SUM D20 D30 就能知道关闭了几个门再配合比较指令判断是否达到要求程序非常简洁。3.2 SUM指令在项目中的典型应用应用场景一统计报警数量。很多设备会把报警信号统一映射到一个或多个数据寄存器里每个bit代表一类报警。用SUM统计出来“当前有几条报警”可以在HMI上显示报警总数也可以利用这个数值做分级处理0条正常1到2条预警3条以上停机。这比逐个比较报警位要高效得多。应用场景二检测数据位的合法性。某些通信协议中数据帧有奇偶校验或者校验字通过SUM可以快速统计某个数据字的1的个数用来判断是否符合预期的奇偶性。虽然三菱有专门的奇偶校验指令但在简单场合用SUM就够了。应用场景三模板匹配和位模式验证。在检测设备中经常需要判断相机检测出来的结果是否和标准模板一致。标准模板放在一个寄存器里检测结果放在另一个寄存器里两者做异或后通过SUM统计差异位数。如果差异位数在一个可接受范围内就判定为合格。这种做法可调整“容忍度”比单纯的相等比较灵活得多。3.3 BON指令的原理与用法BON指令全称Bit Test位测试指令。它的功能是判断源操作数中指定的某一位是ON还是OFF然后把判断结果输出到一个位软元件中。指令格式是 BON S D nS是源操作数D是结果存放的位软元件n是要测试的位的编号。这里有一个非常容易踩坑的点n的编号是从0开始的。也就是说要测试bit0n就写0要测试bit15n就写15。很多初学者第一次用BON时想测试第1位结果写成了K1实际上是测试了bit1也就是从低位往高位数第二个位自然会得到错误结果。我用一个现场案例来说明。某台设备的状态字D200中bit5是主轴运行信号bit8是主轴报警信号。我想在HMI上显示主轴状态最简单的方法不是把这个状态字传到HMI里再在画面里拆位而是用BON指令把这两个位提取出来转成M0和M1两个中间继电器HMI直接读这两个M点就行。程序就两行LD M8000 BON D200 M0 K5 BON D200 M1 K8这样不仅程序层面对操作员友好搞维修的同事也能快速定位到对应的M点而不需要对着状态字换算二进制位。3.4 16位与32位指令的选择FX系列里SUM和BON都有32位版本分别是DSUM和DBON。我一般的原则是看源操作数的数据类型。如果源数据本身就是32位的比如从高速计数器读取的当前值或者模拟量模块的32位数据那就用32位指令。如果是普通的16位状态字用16位指令就够。这里有一个需要特别注意的细节16位指令和32位指令占用的软元件数量不同。32位指令的源操作数是成对的比如 DSUM D0 D10它实际统计的是D0和D1组成的32位数中ON位的数量D1会被自动占用。所以编程时要注意后面不要再对D1单独赋值否则会覆盖32位数据的高16位导致统计结果错误。我见过一个比较隐蔽的问题有人在程序里用了DSUM D0 D10后面又单独写了一条 MOV K0 D1 用来做别的逻辑结果DSUM每次执行结果都不对排查了半天才发现是D1被重复使用了。这种问题在32位指令里特别容易出现因为指令面板上只显示第一个软元件编号后面的自然连续编号是隐性的很容易忽略。所以我的习惯是凡是32位指令用到的软元件都在程序注释里明确标注“D0-D1被DSUM占用”提醒自己和后续维护的人。3.5 SUM与BON的配合应用有时候我们需要同时对一组状态进行“统计”和“抽取”。比如设备有16个工位我想知道当前有几个工位有工件同时还想知道第7个工位有没有工件。这种场景下SUM和BON可以完美配合SUM统计总数用于产量计算BON提取第7位的状态用于单独的工位控制。更妙的是如果需要知道“某个特定位置是否也是工件”也能用SUM结果结合数学运算实现但不如BON直接。我在实际项目中的习惯是写程序时先问自己一个问题“我到底需要这个数据的哪个维度”。如果是数量考虑SUM如果是某个具体状态考虑BON如果是哪个位置考虑ENCO如果是要触发某个位置考虑DECO。这样思考下来程序的架构会清晰很多。4. DECO与ENCO编码与解码的互逆配合4.1 DECO解码指令的原理DECO指令是解码指令它的全称是Decode功能是把源操作数中指定的几位二进制数据解码成对应位置的位状态。指令格式是 DECO S D n其中S是源操作数D是目标位软元件或字软元件n是解码位数。n的取值范围在16位指令中是K1到K8它决定了参与解码的“位数量”1位解码成2个位置2位解码成4个位置3位解码成8个位置以此类推。具体来说DECO指令会读取源S的低n位二进制数值假设这个数值为X那么它会把目标D中编号为X的那一位置ON其他位置OFF。用简单的话说它把一个0到2^n-1的数值转换为一个“只有对应位为1”的位模式。举个例子LD X0 DECO D0 M10 K3这条程序执行时如果D0的低3位数值是5二进制101那么M15会被置ONM10到M17中除了M15之外的7个位全部置OFF。如果D0的低3位数值是0则M10置ON。这里M10是基准地址具体哪个M点被置ON取决于D0的值。4.2 DECO指令在设备选通中的应用DECO最常用的场景是“多路选通”。一条产线上有8个工位每个工位有一个气缸HMI或者上位机通过数值来选择哪个工位动作。以前我可能会写一堆比较指令D00时Y0动作D01时Y1动作程序写8行D0范围大一点就得写几十行。用DECO就非常优雅LD M8000 DECO D0 M20 K3 LD M20 OUT Y0 LD M21 OUT Y1 LD M22 OUT Y2这样可以无限扩展而且后续增加工位数量时只要修改K值和对应输出就行。要注意的是DECO解码出来的M20到M27一段时间内只有一个为ON这天然就是“互锁”的不会出现多个气缸同时动作的误操作。这一点在安全要求较高的场合尤其有价值因为你不用额外写互锁触点指令本身就保证了唯一性。4.3 ENCO编码指令的原理ENCO是DECO的逆运算编码指令。它的功能是在源操作数的所有位中找到编号最大的、状态为ON的那一位把这个位的编号转换成二进制数值存入目标操作数。指令格式是 ENCO S D nS是源操作数D是目标字软元件n是编码位数。16位指令的n范围是K1到K8。例如D0的内容是 0000 0000 1000 0001bit0和bit7都是ON执行 ENCO D0 D10 K3 后D10的值会是7。因为ENCO找的是“编号最大的ON位”也就是最高位的那个位置即使低位的bit0也是ON它也只会取bit7的编号7。这个特性在实际应用中非常重要我会在后面重点讲。4.4 ENCO指令在状态识别中的应用ENCO的一个典型案例是“多按钮输入识别”。有些设备面板上有一排按钮操作员按任意多个按钮后系统要优先响应“编号最靠后”的那个这种逻辑用ENCO一条指令就能实现。比如8个按钮的状态存在D0中执行 ENCO D0 D1 K3 后D1的值就是当前按下的按钮中编号最大的那个。还有一个场景是设备故障代码生成。设备有多个故障信号分别占用状态字的不同位。当多个故障同时发生时我们需要把“优先级最高”的故障提取出来显示在HMI上并做声光报警。传统做法是人为编写优先级比较逻辑故障多了程序很复杂。用ENCO取最高位相当于把“编号最大的位”视为最高优先级然后根据编码值查表跳转到对应的故障处理子程序。这个思路做出来的程序结构简单而且故障位顺序可以通过调整接线或状态字映射来灵活改变。4.5 DECO与ENCO的组合应用状态映射与回读DECO和ENCO在实际项目中经常联合使用。最典型的是“HMI选通操作”HMI输入一个编号DECO把编号变成选通位选中对应的配方数据块操作完成后系统告诉HMI当前选中的是哪个编号这时候就需要ENCO把选通位重新变回编号。我再举一个更具体的例子。某台自动化设备有16组工艺参数用D100到D115存放。操作员在HMI上选择一个编号3PLC通过DECO把编号3变成M103为ON然后程序根据M103把D100到D115中编号为3的那组数据移动到当前工艺参数区。在HMI回显“当前选中的配方号”时PLC通过ENCO语句把M100到M115中的ON位编码成编号3再传给HMI。整个过程数值和位状态之间的转换非常干净。我在实际调试中发现一个坑DECO和ENCO虽然互逆但如果源数据有多个ON位ENCO只按最高位编码而DECO产生的选通位永远只有一位ON所以它们组合使用时没有问题但如果直接用ENCO去编码一个“含多个ON位”的普通数据得到的并不是ON位的数量而是最高ON位的编号。这一点想清楚就不会把ENCO和SUM搞混了。4.6 DECO与ENCO的注意事项第一n的值不能随意设大。16位指令中n最大是K8因为2的8次方等于256而一个16位字只有16位超出范围结果没有意义。实际上n设置超过K4时要确保目标D的位范围足够否则会操作到相邻的其他软元件。同理ENCO的n也是K1到K8目标寄存器只会被写入低n位数据如果nK8目标寄存器的范围是0到255。第二源操作数全OFF时ENCO的结果需要特别小心。如果D0全部位都是OFF执行 ENCO D0 D10 K3D10的结果按照手册规定是0。这在逻辑上就产生了一个“歧义”D100既可能表示“没有输入”也可能表示“bit0有输入”。在实际程序中我通常会先用一条比较指令判断源操作数是否为0再决定是否执行ENCO避免把“无信号”误判成“1号信号”。第三DECO的目标D既可以是位软元件组比如M10到M17也可以是字软元件比如D20。如果目标是字软元件DECO会把对应位置ON其余位清OFF相当于生成了一个“独热码”格式的数据。这种数据在某些通信协议中很有用。5. ZRST区间复位批量清零的正确姿势5.1 ZRST指令语法与适用范围ZRST指令全称Zone Reset区间复位指令。它的功能是把从起始软元件到结束软元件之间的所有同类软元件统一复位为OFF或清零。指令格式是 ZRST S1 S2S1是起始软元件编号S2是结束软元件编号。这条指令一次操作可以覆盖多个连续编号的软元件省去了写大量复位指令的麻烦。ZRST可以用于位软元件比如 M0 M50 表示把M0到M50共51个中间继电器全部复位也可以用于字软元件比如 D0 D100 表示把D0到D100全部清零还可以用于定时器T、计数器C。但有一个重要的限定条件S1和S2必须是同一种类型的软元件。你不能写 ZRST M0 D100这样会报错因为M和D是不同类型的软元件。使用ZRST时还有一点需要切记S1的编号必须小于等于S2的编号。如果S1大于S2指令的执行结果是只有S1所指定的那一个软元件被复位而不是整个区间。这是手册里写得很清楚但我们调试时特别容易忽略的细节因为有时候计算起始地址和结束地址时算反了并不容易察觉。5.2 ZRST在设备初始化中的应用在设备开机初始化或者批次结束后的清场程序里ZRST是一个人见人爱的指令。一台设备动辄有几十个中间继电器、几十个数据寄存器如果用常规的方法写复位程序会又长又乱。用ZRST可以把所有需要复归的软元件集中在一段初始化程序里一次全部搞定。一个典型的初始化程序片段如下LD M8002 ZRST M0 M99 ZRST Y0 Y7 ZRST D0 D199 ZRST C0 C15M8002是FX系列的初始脉冲特殊辅助继电器PLC由STOP转为RUN时只接通一个扫描周期。在这个脉冲下执行ZRST可以保证设备每次上电开始时所有状态都是干净的。生产线设备调试时我最怕的就是“残留状态”——设备停机前某些M点还保持着1重新启动后设备莫名其妙乱动作。用ZRST做过完整的初始化之后这种问题基本就杜绝了。5.3 批次处理场景中的清零逻辑在批次处理模式下ZRST的价值更加明显。比如注塑机或者压铸机的生产流程每完成一个成型周期需要把工位状态、计数器当前值、故障临时标志等全部清零准备进入下一循环。这时候在周期结束段用ZRST把该轮使用的软元件区间一次性清零比用MOV K0逐个清零要快得多也便于检查是不是有遗漏。我在做一台自动化包装线时每个包装箱流入到位后系统会记录当前箱子的颜色、重量、贴标结果等20多个数据存放在D500到D519里。下个箱子来时必须把这些数据清掉否则新箱子的数据会和旧箱子的混在一起。在箱子交接点我用一条 ZRST D500 D519配合流转信号就实现了每批次数据的彻底刷新。刚开始我也觉得一条条清零更“保险”但后来发现维护人员更欢迎这种集中处理方式因为可以在程序里一眼看出“该批次使用了哪些数据区”。5.4 ZRST相对多条MOV的优劣分析有些工程师习惯用 MOV K0 D0、MOV K0 D1 这种方式逐个清零理由是“这样每一个软元件都看得见安心”。但从工程效率角度ZRST优势更明显第一程序步数少。清零200个D寄存器用MOV要200条指令用ZRST只要1条。第二扫描周期短。虽然初始化程序不经常执行但在批次循环清零时多出的扫描时间会影响节拍。ZRST是按系统内部机制批量处理的实际耗时远低于逐条MOV。第三遗漏风险低。写100多条MOV清零时总容易漏掉其中某几个寄存器。ZRST只要区间端点写对中间全部覆盖不会有遗漏。但ZRST也有它的不足之处它的复位方式是“一刀切”不区分区间内每个软元件的具体含义。如果你的程序里某个D寄存器需要保持断电记忆或者某几个M点需要在批次切换时保持状态就不能简单用一个ZRST区间把它们也清零了。我的习惯是在写初始化程序前先做一张“软元件地址分配表”把需要保持的数据和需要清零的数据分开规划让需要保持的数据落在一个独立地址区间不与清零区间交叉这样ZRST用起来才安全。5.5 使用ZRST的几个注意事项再强调几个实操层面的细节。第一ZRST虽然能复位定时器T和计数器C但对于定时器它复位的是当前值寄存器和触点状态。这个行为对模拟定时器和累计定时器是一样的。第二ZRST不能复位特殊辅助继电器M8000及以上的系统区操作无效。第三ZRST指令本身不能用32位指令形式它没有DZRST这种写法因为它本身就是成批操作不需要再用32位。我曾经遇到过一个问题现场设备偶尔出现“计数器没清零”的故障排查了很久最后发现原因是计数器C0到C10用了ZRST清零但程序里某个地方用FMOV或者MOV对C11单独赋值过而操作员的某次操作把编号算错把C11的值误写到了一个与C10连续的区域导致ZRST区间没有覆盖到。这种问题不是ZRST本身的锅而是软元件规划不严谨。所以用ZRST前一定要有一个全局的软元件分配表而不是边写程序边临时加地址。6. 综合案例五个指令在一套自动分拣设备中的完整落地6.1 设备动作流程与I/O分配讲完了原理我把这五个指令放到一个实际项目里完整串一遍。假设我们要做一台8工位料盘检测分拣设备有8个工位每个工位上方有一个光电传感器检测该工位是否有物料每个工位侧面有一个推料气缸当系统判定该工位需要剔除物料时气缸推出把物料推到剔除箱里。I/O分配如下X0到X78个工位的物料检测传感器1表示有料Y0到Y78个工位的推料气缸电磁阀1表示推出X10启动按钮X11复位按钮数据分配如下D0通过BMOV把X0到X7的输入状态打包成一个字bit0到bit7对应8个工位D1ENCO编码结果记录当前需要处理的工位编号D2SUM统计结果记录当前有料工位总数M0到M7当前选通的工位标志M20工位3的传感器状态提取结果用于特殊监控设备的工作流程是按下启动按钮后系统扫描所有工位统计有料数量如果总数大于0则优先处理编号最大的有料工位把该工位对应的气缸推出完成剔除后气缸缩回进行下一轮判断直到所有有料工位全部处理完毕。按下复位按钮所有标志和数据全部清零。6.2 关键控制逻辑的程序实现程序的关键段如下LD X10 SET M100 ; 启动处理标志 LD M100 BMOV X0 D0 K1 ; 把X0到X7的位状态复制到D0低8位 LD M100 SUM D0 D2 ; 统计D0中ON位的总数存入D2 LD M100 ENCO D0 D1 K3 ; 取D0中编号最大的ON位编码为0到7存入D1 LD M100 DECO D1 M0 K3 ; 根据D1的值把M0到M7中对应位置ON LD M100 BON D0 M20 K3 ; 提取D0的bit3状态用于工位3单独监控 LD M0 OUT Y0 LD M1 OUT Y1 LD M2 OUT Y2 LD M3 OUT Y3 LD M4 OUT Y4 LD M5 OUT Y5 LD M6 OUT Y6 LD M7 OUT Y7这里BMOV指令的作用是把X0到X7的位状态批量传送到D0的低8位保证后面SUM、ENCO能对同一份状态数据进行处理。执行时序上先SUM统计再ENCO编码再DECO选通最后输出到气缸逻辑链条很清晰。程序还包含一个关键的“剔除完成”判断当Y0到Y7任何一个气缸动作后延时500毫秒再复位当前工位对应的传感器状态。具体实现是当D10时复位D0.0D11时复位D0.1以此类推。这样每处理完一个工位D0中的ON位就会减少一个SUM和ENCO的结果也会自动更新直到D2变为0所有物料处理完毕。清零段LD X11 ZRST Y0 Y7 ZRST M0 M7 ZRST D0 D2 ZRST M100按下复位按钮后输出、选通标志、统计数据全部清零。整个逻辑中SUM、BON、DECO、ENCO、ZRST五个指令各司其职互相配合完成了一条完整的分拣逻辑而传统写法至少要比这个多写出两倍的程序步。6.3 编程思路复盘与优化方向这个案例最关键的一点是“数据流的组织”。X0到X7的输入状态先被集中到D0后续所有处理都围绕D0展开避免了直接对位软元件写大量分散逻辑。SUM提供总量判断ENCO决定处理优先级DECO把编号转化为位选通输出BON提供单独监控ZRST负责收尾清零。每一步的产物都是下一步的输入可读性非常强。如果设备工位数量增加比如从8个工位扩展到16个只需要修改K3为K4扩展D1的取值范围到0到15然后把DECO的目标从M0到M7改为M0到M15再增加对应的输出触点即可。这种扩展性是我特别喜欢这套指令组合的原因。当然如果输入点数超过了字软元件的16位限制就需要拆分为多个字分别处理。6.4 案例中体现的优先级逻辑我还想特别说明一下ENCO在案例中体现的“优先级”。这个程序用的是ENCO默认行为即优先处理编号最大的工位这在“从末端向前端取料”的场景中很自然。但有些场景需要优先处理编号最小的工位比如产线前进方向是从小号到大号那么物料应该按顺序从前到后处理。这种情况下单纯用ENCO就不够了我们需要对D0做一次“位反转”或者用循环扫描的方式实现。一个变通方法是利用DECO和ENCO的组合先用DECO把D0里的状态解码到M0到M7然后从M0开始按顺序查找第一个ON位找到后用ENCO把它的编号编码回来。但这样做程序较长。还有一个技巧是把D0的低8位数据通过查表方式反转bit顺序后再执行ENCO得到的结果做一次“7减”换算就能得到最小编号。这个方法在FX3U上可以用扩展指令实现虽然在老型号上会多几步但思路本身值得借鉴。7. 常见问题与排查技巧实录7.1 常见问题速查表我把这几个指令在实际使用中遇到的高频问题整理成一个表格方便大家快速定位。现象可能原因解决方法SUM结果总是不对统计值偏大或偏小源操作数被其他32位指令隐性占用了一部分或者源数据包含无效的高位数据检查源软元件是否有32位指令重叠使用确认统计范围是16位还是32位BON测试“第1位”结果错误n值从0开始编号K1对应的是bit1而不是第1位把n值调整为需要测试的位编号减1ENCO编码结果总是“最末位”混淆了ENC0的规则它找的是编号最大的ON位不是第一个ON位确认需求如果要求第一个ON位需要对源数据做位反转或改用循环扫描ENCO在源全OFF时输出0导致误动作源全OFF时目标值为0程序把0当作“bit0有效”处理了执行ENCO前先判断源操作数是否等于0DECO选通结果有两个位同时为ON目标位软元件区域被其他指令干扰或者n值过大导致目标区超出预期范围检查目标位软元件编号范围避免与程序中其他使用的M点重叠ZRST指定区间没有全部清零S1大于S2指令只复位S1单独一个软元件确认S1小于S2可通过监控指令的软元件编号检查ZRST把不该清零的软元件也清掉了起始和结束编号规划不严谨区间覆盖了需要保持的数据区制作软元件分配表把保持数据与清零数据分区分开32位DSUM执行后程序逻辑混乱32位指令占用两个连续D寄存器第二个被其他程序误写在注释中标注32位指令的占用区间避免重复使用7.2 排查技巧用监控视图验证指令执行结果在GX Works2或者GX Works3里调试这几个指令时有一个我极力推荐的技巧把“软元件批量监控”窗口打开同时监控源操作数和目标操作数观察指令执行前后的变化。比如调试SUM时同时监控D0和D10然后手动修改D0的数值看D10是否随之变化。这样可以快速验证指令的行为是否符合预期而不用一遍遍下载程序。调试ENCO和DECO这组指令时我习惯在“当前值监控”窗口里用二进制格式显示数据这样能直观地看到每一位的状态变化。GX Works2里可以在监控窗口右键选择显示格式为“位”GX Works3则在视图菜单中设置。看到位级别的变化你对指令的理解会立刻加深比只看十进制数值清楚得多。7.3 我踩过的几个坑第一个坑是关于DECO目标区的重叠。有一年我做一台16工位设备用了 DECO D10 M100 K4解码范围是M100到M115但我没有注意到程序里某个指示灯的中间继电器正好是M110导致设备运行中指示灯会跟着选通逻辑乱闪。后来我在程序里统一规划了M区的功能分区把选通区、报警区、状态区严格分开才彻底解决这个问题。这件事之后我养成了一个习惯任何需要扩展区域的指令都会先查一遍软元件注释表确认目标区间没有和其他逻辑共用。第二个坑是ENCO和SUM的混用。有一段时间我误以为ENCO能统计ON位的数量结果读出来的数值完全不是期望的。后来仔细翻手册才恍然大悟ENCO给的是最高ON位的“位置”不是“数量”。如果你需要的是数量请用SUM如果你需要的是位置才用ENCO。一句话就能说清但实际项目里压力大的时候人真的会把这俩搞混。第三个坑是ZRST区间过大。某次改造一台老设备我在初始化程序里写了一条 ZRST D0 D9999本意是“把所有用到的D区都清一遍”结果这条程序把D8000到D8511之间的特殊寄存器也清掉了导致一些系统参数被重置设备启动后通信异常。从那以后我清零D区再也不敢贪大都严格按软元件分配表来划定区间宁可多写两条ZRST也不允许一个超大区间覆盖未规划区域。7.4 软件版本和指令兼容性提醒最后提醒一点不同型号的PLC这几个指令的可用范围有细微差别。FX3U和FX5U全面支持SUM、BON、DECO、ENCO、ZRSTFX2N也有但要注意32位版本的DSUM、DBON在FX2N上是没有的。Q系列和L系列同样支持但L系列中部分特殊软元件区的访问规则不同使用前最好查看对应手册的应用指令列表。如果你从FX3U的程序移植到FX5U指令格式基本兼容但要注意GX Works3里梯形图输入方式变化较大输入指令时用指令列表插入即可不需要逐条画触点。我在实际项目里还会注意一点有些客户或者协作方使用的编程软件版本比较旧打开新版本软件保存的程序时这几个指令的帮助说明显示可能会有差异但执行逻辑不变。如果遇到程序下载后监控行为和预期不符先确认PLC的固件版本和编程软件版本是否匹配。毕竟这类指令的底层处理逻辑在固件里不同的固件版本偶尔会有行为差异虽然极少见但排查问题时不该忽略这个方向。
上一篇/下一篇内容由系统自动关联
返回资讯列表 →