← 所有文章

PLC 型別轉換的小數 截斷與超範圍處理

· 站長

從正負小數到16位上下界,建立轉換前的有效性檢查,分清截斷、取整與位元解讀。

轉換前先決定哪些資訊可以丟掉

溫度 2.9 轉成整數,應該得到 2 還是 3?兩種答案都可能符合某種需求,卻不能在同一個控制程式裡隨意交換。先寫出要截斷、取最近整數,或保留一位小數,再選指令。這篇以 CODESYS 文件中的 REAL_TO_INT 與 TRUNC_INT 為對照,帶你把型別、範圍、有效旗標一起設計。

我們的虛擬來源是 REAL 量測值,目的欄位是 16 位有號 INT,範圍 −32768~32767。轉換後還要輸出 Valid 與 Error,讓下一段程式知道這次數字可不可用。案例不連接輸出,也不把這些函式名稱當成三菱 Q 系列可直接使用的指令。

需求 做法 會失去什麼
只要整數部分 向零截斷 正負小數部分
取最接近的整數 按明訂規則取整 小數細節,中點另有規則
保留0.1單位 先定義倍率與整數存法 低於0.1的解析度
解碼原始位元 依原型別重新解讀 不能用數值轉換代替解碼

例如 IEEE 754 單精度 1.0 的位元圖樣是 16#3F800000。把這些位元當成無號整數,會得到 1065353216;真正做 1.0 的數值轉換則得到整數 1。兩者不是精度差,而是你問了不同的問題。通訊讀到兩個暫存器時,先確認資料型態與字組排列,再決定如何解碼。

用正負小數看懂兩種轉換

CODESYS 官方 TRUNC_INT 說明只取整數部分,正負值都向零。例如 −2.9 截斷後是 −2,不是 −3。REAL_TO_INT 依其文件進行取整;本表選用不在中點的值,避免把中點策略和一般取整混為一談。

輸入 TRUNC_INT REAL_TO_INT文件預期 要學會的判斷
2.9 2 3 截斷與取整不同
−2.9 −2 −3 負數截斷往零靠近
2.1 2 2 部分值看不出差異
−2.1 −2 −2 不能只測一組正數
0.9 0 1 小值轉換可能變成零
−0.9 0 −1 正負都要驗收

先在紙上填完兩欄,再在目標工程軟體中建立來源與結果監看。如果只測 2.1,兩種函式都得到 2,你可能誤以為它們一樣。一定要包含 2.9、−2.9 與接近零的數,才會看到資訊怎麼消失。若平台提供不同名稱,照同一組測試輸入驗收,不靠函式名字猜。

參考:CODESYS TRUNC_INT 整數部分與負數示例

參考:CODESYS REAL LREAL Conversion 與 Rounding

先做範圍檢查 再允許轉換

本例採保守接受規則:來源必須有效、有限,而且位於 −32768~32767,才執行轉換。32767.9 即使截斷有機會落回範圍,本例仍拒絕,讓兩種轉換共用清楚的輸入契約。若你的規格需要接受這種邊界,必須另外定義取整後檢查的安全方法。

  1. 先檢查來源品質,通訊失敗或感測器無效時,不執行正常數值轉換。

  2. 確認來源是有限數,處理 NaN 與正負無限大;使用目標平台有文件支持的檢查方式。

  3. 依本例先比對上下界,超出便令 Valid=0、Error=RANGE,不更新結果。

  4. 範圍通過後才呼叫選定的轉換,令 Valid=1,清除本次錯誤。

  5. 後續程式同時使用結果與 Valid;若保留上一筆數值,畫面應明示那是舊值。

測試輸入 本例接受 預期處理
32767 可轉成32767
−32768 可轉成−32768
32767.9 先拒絕,不呼叫轉換
40000 RANGE錯誤
NaN/無限大 INVALID錯誤
來源品質無效 保留原因,不把舊值冒充新值

不要先把 REAL 轉成 INT,再用 INT 看有沒有大於 32767:超範圍的資訊可能已經消失。官方文件指出超出目標範圍可能產生未定義或目標系統相關結果,因此不能把某次觀察到的負數當成可靠的溢位通知。

讓錯誤值不再偷偷參與計算

設計結果介面時,把 Converted、Valid、Error 與原始值保留在同一個可觀察區域。假設上一筆 12.8 成功轉為13,下一筆收到40000,這次Converted可以仍是13,但Valid必須為0。使用者看到「13 目前無效」和看到正常13,意思完全不同。

次序 原始值 Converted Valid 說明
1 12.8 13 1 使用最近整數策略
2 40000 13 保留 0 拒絕新值,禁止當作新量測
3 −2.9 −3 1 來源恢復且在範圍內

若把結果寫成0當作錯誤替代,也必須保留無效旗標;因為正常的0.1截斷也會變成0,單靠數字無法分辨。控制策略要另定義無效時停止、保持或降級,本篇不替任何機械指定安全動作。這裡只要求錯誤與正常資料不能混在一起。

失敗時先查運算型別和選用函式,再查來源是否已被前一段縮放、截斷或字組交換。監看上顯示2.9不一定代表儲存值剛好2.9;需要看足夠有效位數與原始型別。尤其是多次放大縮小後的數,應回到最初來源逐段核對,不要再加一個常數修正結果。

動手建立轉換驗收紀錄

先建立一張測試紀錄,左側依序放來源值、來源型別、來源有效性,中間放所選策略,右側放結果、結果有效性與錯誤原因。不要只留一個轉換後的數字。假如改用截斷,表格標題也應同步改成截斷,避免下一位維護人員拿取最近整數的答案來判斷程式。

第一輪只使用範圍內資料。先輸入正的小數,再輸入其負值,最後輸入零附近的正負小數。每次都先在紙上寫答案,再觀察目標系統結果。若答案不同,先確認實際呼叫的是哪一個函式,以及來源是否在進入函式之前就被別的運算轉成整數。

第二輪測試有效性切換。先送入正常資料,再送入超界資料,最後恢復正常。觀察的重點是錯誤當下有效旗標是否立即清除,以及恢復後錯誤是否依本次結果更新。保留的舊值應帶時間或序號,讓畫面能說明它不是剛收到的新值,不能只靠顏色讓操作員猜。

第三輪才測上下界。邊界測試應從已知有效值走向邊界,再跨出邊界,記錄是哪一個條件拒絕資料。本文採原始值先檢查的保守規則,因此某些轉換後看似可容納的輸入也會被拒絕。這是介面契約的選擇,不是轉換指令故障;驗收表要清楚註明。

若來源是一個十六位無號通訊欄位,不能直接套用本例的有號上下界。先查資料字典,再決定要接成無號整數、有號整數或固定小數。相同位元在不同型別下可以有不同意思;例如全一位元在無號解讀下是最大正值,在十六位二補數解讀下則是負一。

最後把轉換規則放進欄位說明:來源單位、來源型別、目標型別、取整規則、允許範圍與無效時的處理都要齊全。這份說明能讓通訊、畫面與控制程式使用相同定義。日後量程改大,先重新計算範圍與解析度,再修改程式,不要只把錯誤旗標關掉。

完成驗收與適用限制

完成後應得到表中的六組正負小數結果,所有超界和無效輸入都被拒絕,且下游不使用Valid=0的結果。測試記錄至少包含CPU、Runtime與編譯器版本、來源型別、轉換函式、原值與結果;只有手算表完成,不等於PLC驗證已完成。

常見問題

TRUNC 是往下取整嗎?本篇的 TRUNC_INT 是向零取整;−2.9變−2。若需求是數學上的floor,必須另選正確方法。

轉成較大整數就能保留小數嗎?不能。較大位寬增加的是整數範圍,小數仍要靠浮點或明訂倍率保存。

把顯示小數位改成0算轉換嗎?不算。畫面可能只改格式,PLC內儲存值仍含小數。請檢查真正送到下一個運算的資料。

適用型號與限制:具體函式依據為 CODESYS Development System 線上文件,查閱2026-09-17;Q06UDVCPU/GX Works2、其他PLC或Runtime的函式與例外行為須另核對。本例只教轉換設計與離線驗收,未指定任何設備暫存器或已編譯程式。

延伸閱讀


使用 PLC 工具箱 →