← Back to Guides

Math, String & Conversion Reference

GoPLC Math, String & Conversion Reference

James M. Belcher Founder, JMB Technical Services LLC April 2026 | GoPLC v1.0.535


1. Math & Trigonometry

Basic Math

FunctionSignatureReturnsDescription
ABS(x)REAL/INTAbsolute value
SIGN(x)INT-1, 0, or 1
SQRT(x)REALSquare root
POW(base, exp)REALPower (base^exp)
EXPT(base, exp)REALSame as POW
EXP(x)REALe^x
LN(x)REALNatural logarithm
LOG(x)REALBase-10 logarithm
FMOD(x, y)REALFloating-point modulus
distance := SQRT(POW(x2 - x1, 2) + POW(y2 - y1, 2));
gain_db := 20.0 * LOG(vout / vin);

Rounding

FunctionSignatureReturnsDescription
CEIL(x)REALRound up to integer
FLOOR(x)REALRound down to integer
ROUND(x)REALRound to nearest integer
TRUNC(x)REALTruncate toward zero
pages := CEIL(total_items / 10.0);      (* 25 items → 3 pages *)
whole := TRUNC(3.7);                     (* 3.0 *)

Trigonometry

All angles in radians.

FunctionSignatureReturnsDescription
SIN(rad)REALSine
COS(rad)REALCosine
TAN(rad)REALTangent
ASIN(x)REALArc sine (returns radians)
ACOS(x)REALArc cosine
ATAN(x)REALArc tangent
ATAN2(y, x)REALTwo-argument arc tangent
DEG_TO_RAD(deg)REALDegrees → radians
RAD_TO_DEG(rad)REALRadians → degrees
angle_rad := DEG_TO_RAD(45.0);
x := COS(angle_rad) * radius;
y := SIN(angle_rad) * radius;
heading := RAD_TO_DEG(ATAN2(dy, dx));

2. Selection & Comparison

FunctionSignatureReturnsDescription
MIN(a, b)ANYSmaller of two values
MAX(a, b)ANYLarger of two values
LIMIT(min, value, max)ANYClamp value to range
CLAMP(value, min, max)ANYSame as LIMIT (different arg order)
SEL(condition, false_val, true_val)ANYConditional select (like ternary)
MUX(index, val0, val1, val2, ...)ANYIndexed multiplexer
(* Clamp output to 0-100% *)
output := LIMIT(0.0, pid_output, 100.0);

(* Select based on condition *)
mode_name := SEL(auto_mode, 'MANUAL', 'AUTO');

(* Multiplexer — select by index *)
recipe_temp := MUX(recipe_id, 150.0, 180.0, 200.0, 220.0);

3. Statistics

FunctionSignatureReturnsDescription
MEAN(array)REALArithmetic mean
MEDIAN(array)REALMiddle value
VARIANCE(array)REALPopulation variance
STDDEV(array)REALStandard deviation
PERCENTILE(array, pct)REALNth percentile (0-100)
MOVING_AVG(handle, value, window)REALMoving average (handle-based)
SMA(handle, value, window)REALSimple moving average (alias)
EMA(handle, value, alpha)REALExponential moving average
temps := ARRAY_CREATE(68.2, 72.1, 71.5, 73.0, 69.8);
avg := MEAN(temps);                    (* 70.92 *)
med := MEDIAN(temps);                  (* 71.5 *)
sd := STDDEV(temps);                   (* ~1.8 *)
p95 := PERCENTILE(temps, 95);         (* ~72.8 *)

(* Running average over last 20 samples *)
smooth_temp := MOVING_AVG('temp_avg', raw_temp, 20);

(* Exponential smoothing — alpha 0.1 = heavy smoothing *)
filtered := EMA('pressure_ema', raw_pressure, 0.1);

4. Interpolation & Scaling

FunctionSignatureReturnsDescription
LERP(a, b, t)REALLinear interpolation (t=0→a, t=1→b)
SCALE(value, in_min, in_max, out_min, out_max)REALMap range to range
RANDOM()REALRandom 0.0–1.0
RAND()REALAlias for RANDOM
RANDOM_RANGE(min, max)REALRandom in range
(* Scale 0-4095 ADC to 0-100 PSI *)
pressure_psi := SCALE(adc_raw, 0, 4095, 0.0, 100.0);

(* Fade between two colors over 100 steps *)
brightness := LERP(0.0, 100.0, INT_TO_REAL(step) / 100.0);

(* Simulate sensor noise *)
noisy := actual_temp + (RANDOM_RANGE(-0.5, 0.5));

5. Unit Conversions

FunctionSignatureReturnsDescription
C_TO_F(celsius)REALCelsius → Fahrenheit
F_TO_C(fahrenheit)REALFahrenheit → Celsius
C_TO_K(celsius)REALCelsius → Kelvin
K_TO_C(kelvin)REALKelvin → Celsius
KMH_TO_MS(kmh)REALkm/h → m/s
MS_TO_KMH(ms)REALm/s → km/h
DEG_TO_RAD(degrees)REALDegrees → radians
RAD_TO_DEG(radians)REALRadians → degrees

6. String Functions

Length & Access

FunctionSignatureReturnsDescription
LEN(str)INTString length
LEFT(str, count)STRINGFirst N characters
RIGHT(str, count)STRINGLast N characters
MID(str, start, count)STRINGSubstring (1-based start)
CHR(code)STRINGASCII code → character
ORD(str)INTFirst character → ASCII code
name := 'GOPLC-Plant1';
prefix := LEFT(name, 5);              (* "GOPLC" *)
suffix := RIGHT(name, 6);             (* "Plant1" *)
mid := MID(name, 7, 6);               (* "Plant1" *)
newline := CHR(10);                    (* \n *)
FunctionSignatureReturnsDescription
FIND(str, search)INTPosition of substring (0 = not found)
CONTAINS(str, search)BOOLSubstring exists?
STARTS_WITH(str, prefix)BOOLStarts with prefix?
ENDS_WITH(str, suffix)BOOLEnds with suffix?
IF CONTAINS(alarm_text, 'HIGH') THEN
    severity := 3;
END_IF;

Modify

FunctionSignatureReturnsDescription
CONCAT(str1, str2, ...)STRINGJoin strings (variadic)
REPLACE(str, search, replacement)STRINGReplace all occurrences
INSERT(str, position, insert_str)STRINGInsert at position
DELETE(str, position, count)STRINGDelete characters
UPPER(str)STRINGUppercase
LOWER(str)STRINGLowercase
TRIM(str)STRINGStrip whitespace both ends
LTRIM(str)STRINGStrip leading whitespace
RTRIM(str)STRINGStrip trailing whitespace
REVERSE(str)STRINGReverse string
REPEAT(str, count)STRINGRepeat N times
PAD_LEFT(str, width, pad_char)STRINGLeft-pad to width
PAD_RIGHT(str, width, pad_char)STRINGRight-pad to width
SPLIT(str, delimiter)ARRAYSplit into array
FORMAT(template, args...)STRINGPrintf-style formatting
msg := CONCAT('Temperature: ', REAL_TO_STRING(temp), ' F');
csv := REPLACE(raw_data, ';', ',');
parts := SPLIT('10.0.0.50:502', ':');       (* ["10.0.0.50", "502"] *)
padded := PAD_LEFT(INT_TO_STRING(batch), 6, '0');  (* "000042" *)
line := FORMAT('%s,%d,%.2f', tag_name, count, value);

7. Type Conversions

Numeric

From \ ToINTDINTREALSTRINGBOOLBYTEWORDDWORD
INT—INT_TO_DINTINT_TO_REALINT_TO_STRINGINT_TO_BOOLINT_TO_BYTEINT_TO_WORDINT_TO_DWORD
DINTDINT_TO_INT—DINT_TO_REALDINT_TO_STRING—DINT_TO_BYTEDINT_TO_WORD—
REALREAL_TO_INTREAL_TO_DINT—REAL_TO_STRING—REAL_TO_BYTEREAL_TO_WORDREAL_TO_DWORD
STRINGSTRING_TO_INTSTRING_TO_DINTSTRING_TO_REAL—STRING_TO_BOOLSTRING_TO_BYTESTRING_TO_WORDSTRING_TO_DWORD
BOOLBOOL_TO_INTBOOL_TO_DINT—BOOL_TO_STRING—BOOL_TO_BYTEBOOL_TO_WORDBOOL_TO_DWORD
BYTEBYTE_TO_INT—BYTE_TO_REALBYTE_TO_STRING——BYTE_TO_WORDBYTE_TO_DWORD
WORDWORD_TO_INT—WORD_TO_REALWORD_TO_STRING—WORD_TO_BYTE—WORD_TO_DWORD
DWORDDWORD_TO_INTDWORD_TO_DINTDWORD_TO_REALDWORD_TO_STRING—DWORD_TO_BYTEDWORD_TO_WORD—

Extended Integer Types

FunctionDescription
UINT_TO_INT, INT_TO_UINTUnsigned ↔ signed 16-bit
UDINT_TO_DINT, DINT_TO_UDINTUnsigned ↔ signed 32-bit
LINT_TO_INT, INT_TO_LINT64-bit ↔ 32-bit
ULINT_TO_UINT, UINT_TO_ULINTUnsigned 64-bit ↔ 16-bit
SINT_TO_STRING, USINT_TO_STRINGShort int → string

Date & Time

FunctionDescription
TIME_TO_STRING, STRING_TO_TIMETIME ↔ STRING
TIME_TO_DINT, DINT_TO_TIMETIME ↔ milliseconds
TIME_TO_REAL, REAL_TO_TIMETIME ↔ seconds (float)
DATE_TO_STRING, STRING_TO_DATEDATE ↔ STRING
DT_TO_STRING, STRING_TO_DTDATE_TIME ↔ STRING
DT_TO_DATE, DATE_TO_DTExtract/build date portion
DT_TO_TOD, TOD_TO_TIMEExtract/build time-of-day
DATE_TO_DWORD, DWORD_TO_DATEDATE ↔ binary
DT_TO_DWORD, DWORD_TO_DTDATE_TIME ↔ binary
TOD_TO_DINT, DINT_TO_TODTime-of-day ↔ integer

Number Base

FunctionDescription
INT_TO_HEX, HEX_TO_INTInteger ↔ hex string
DINT_TO_HEX, HEX_TO_DINT32-bit ↔ hex string
INT_TO_BIN, BIN_TO_INTInteger ↔ binary string
DINT_TO_BIN, BIN_TO_DINT32-bit ↔ binary string
INT_TO_OCT, OCT_TO_INTInteger ↔ octal string
DINT_TO_OCT, OCT_TO_DINT32-bit ↔ octal string
BYTE_TO_GRAY, GRAY_TO_BYTEBinary ↔ Gray code
hex := DINT_TO_HEX(255);              (* "FF" *)
val := HEX_TO_INT('1A');               (* 26 *)
gray := BYTE_TO_GRAY(13);              (* Gray code encoding *)

8. Bitwise Operations

OperatorSyntaxDescription
ANDa AND bBitwise AND
ORa OR bBitwise OR
XORa XOR bBitwise XOR
NOTNOT aBitwise NOT
SHLSHL(value, bits)Shift left
SHRSHR(value, bits)Shift right
ROLROL(value, bits)Rotate left
RORROR(value, bits)Rotate right
SET_BITSET_BIT(value, bit)Set bit N
(* Extract bits from a status word *)
motor_running := (status_word AND 16#0001) > 0;     (* Bit 0 *)
fault_active := (status_word AND 16#0002) > 0;       (* Bit 1 *)

(* Build a command word *)
cmd := 0;
IF start THEN cmd := cmd OR 16#0001; END_IF;
IF forward THEN cmd := cmd OR 16#0004; END_IF;

9. Complete Example: Sensor Signal Processing

PROGRAM POU_SignalProcessing
VAR
    (* Raw inputs *)
    adc_raw : INT;                     (* 0-4095 from ADC *)
    pressure_raw : REAL;

    (* Processed outputs *)
    pressure_psi : REAL;
    temp_f : REAL;
    temp_c : REAL;
    filtered_pressure : REAL;
    alarm_active : BOOL;

    (* Statistics *)
    pressure_avg : REAL;
    pressure_sd : REAL;
    samples : STRING;                  (* ARRAY handle *)
    sample_count : INT := 0;
END_VAR

(* Scale ADC to engineering units *)
pressure_psi := SCALE(INT_TO_REAL(adc_raw), 0.0, 4095.0, 0.0, 100.0);

(* Temperature conversion *)
temp_c := 25.0;
temp_f := C_TO_F(temp_c);

(* Exponential moving average filter *)
filtered_pressure := EMA('press_filter', pressure_psi, 0.15);

(* Hysteresis on alarm — prevents chatter near threshold *)
alarm_active := HYSTERESIS(filtered_pressure, 85.0, 90.0, alarm_active);

(* Clamp output to valid range *)
pressure_psi := CLAMP(pressure_psi, 0.0, 100.0);

(* Collect samples for statistics *)
sample_count := sample_count + 1;
IF sample_count = 1 THEN
    samples := ARRAY_CREATE(filtered_pressure);
ELSE
    samples := ARRAY_APPEND(samples, filtered_pressure);
    IF ARRAY_LENGTH(samples) > 100 THEN
        samples := ARRAY_SLICE(samples, 1, 100);    (* Keep last 100 *)
    END_IF;
END_IF;

IF ARRAY_LENGTH(samples) >= 10 THEN
    pressure_avg := MEAN(samples);
    pressure_sd := STDDEV(samples);
END_IF;

(* Format for display *)
display_text := FORMAT('Pressure: %.1f PSI (avg: %.1f, sd: %.2f)',
                       filtered_pressure, pressure_avg, pressure_sd);

END_PROGRAM

GoPLC v1.0.535 | Math, String & Type Conversion Reference | IEC 61131-3 + Extensions

© 2026 JMB Technical Services LLC. All rights reserved.