Physical Units (std.unit)
The std.unit module provides built-in, first-class support for physical units, quantities, and dimensional analysis directly within Flame.
Flame’s unit system allows you to create quantities that carry physical units (like meters, seconds, and kilograms). This ensures dimensional safety, meaning that the runtime automatically checks for incompatible operations (e.g. adding meters to seconds) and will throw an error to prevent logical bugs in calculations.
Standard Exported Units
Section titled “Standard Exported Units”Out of the box, std.unit provides the base SI units as constants:
unit.meter: The SI base unit for length (m).unit.second: The SI base unit for time (s).unit.kilogram: The SI base unit for mass (kg).
import std.unit
let length = 10 * unit.meterlet time = 5 * unit.secondArithmetic with Quantities
Section titled “Arithmetic with Quantities”You can use standard math operators (+, -, *, /) with quantities.
Addition and Subtraction
Section titled “Addition and Subtraction”When adding or subtracting, the units must match exactly. If you try to add quantities with different units, Flame will throw a runtime error.
import std.unit
let distance1 = 15 * unit.meterlet distance2 = 5 * unit.meter
let total_distance = distance1 + distance2println(total_distance) // 20 m
// This will throw a runtime error: "cannot add quantities with different units"// let error = distance1 + (5 * unit.second)Multiplication and Division
Section titled “Multiplication and Division”When multiplying or dividing, the units naturally combine or cancel out.
import std.unit
let distance = 100 * unit.meterlet time = 10 * unit.second
// Division results in a new unit: m * s^-1let speed = distance / timeprintln(speed) // 10 m * s^-1If the units cancel out completely, Flame will automatically downgrade the quantity back to a regular Float.
import std.unit
let length1 = 10 * unit.meterlet length2 = 2 * unit.meter
let ratio = length1 / length2println(ratio) // 5.0 (scalar float, no units)Creating Custom Units (Equations)
Section titled “Creating Custom Units (Equations)”If you need a compound unit or one that isn’t provided by default, you can construct custom unit equations using the unit.Equation(kg, m, s) function.
You pass the exponents for kilograms (kg), meters (m), and seconds (s) in that order.
import std.unit
// Speed: m/s -> kilograms^0, meters^1, seconds^-1let speed_unit = unit.Equation(0, 1, -1)
// Acceleration: m/s^2 -> kilograms^0, meters^1, seconds^-2let accel_unit = unit.Equation(0, 1, -2)
// Newton: kg * m/s^2 -> kilograms^1, meters^1, seconds^-2let newton = unit.Equation(1, 1, -2)
let my_speed = 50 * speed_unitExtracting Numeric Values
Section titled “Extracting Numeric Values”If you need to discard the dimensional information and work purely with the underlying magnitude of a quantity, you can use the built-in primitive conversion methods like toFloat(), tryFloat(), toInt(), and tryInt().
import std.unit
let distance = 10.5 * unit.meter
// Drops the "meter" unit and returns the raw float valuelet val = distance.toFloat()println(val) // 10.5Dimensional Analysis in std.math
Section titled “Dimensional Analysis in std.math”Flame’s math module (std.math) is unit-aware. When you pass units or quantities into mathematical functions and operators, Flame automatically calculates, scales, and validates their physical dimensions.
Exponentiation and Powers (^ and math.pow)
Section titled “Exponentiation and Powers (^ and math.pow)”You can raise units and quantities to integer powers using the ^ operator or math.pow(). The exponent scales both the underlying magnitude and the unit powers:
import std.unitimport std.math
// 1. Exponentiation on base unitslet s2 = unit.second^2 // seconds squared (s^2)let m3 = unit.meter^3 // cubic meters (m^3)
// 2. Exponentiation on quantities (scales magnitude and unit)let area = (4 * unit.meter)^2println(area) // 16 m^2
// 3. Using math.pow for dynamic or explicit powerslet volume = math.pow(3 * unit.meter, 3)println(volume) // 27 m^3Auto-propagating Roots (math.sqrt)
Section titled “Auto-propagating Roots (math.sqrt)”math.sqrt() evaluates the square root of numbers, quantities, and units with even dimensional powers. Each dimension’s exponent is safely halved:
import std.unitimport std.math
// Square root of a unit dimensionlet s = math.sqrt(unit.second^2)println(s) // 1 s
// Pendulum period calculation: T = 2 * pi * sqrt(L / g)let L = 2 * unit.meterlet g = 9.81 * unit.meter / unit.second^2
// L / g produces a quantity in s^2// math.sqrt(s^2) safely propagates the dimension and returns a quantity in seconds (s)let T = 2 * math.pi() * math.sqrt(L / g)println(T) // ~ 2.837 sAbsolute Values (math.abs)
Section titled “Absolute Values (math.abs)”math.abs() computes the absolute value while strictly preserving unit dimensions:
import std.unitimport std.math
let neg_speed = -25.5 * (unit.meter / unit.second)let speed = math.abs(neg_speed)
println(speed) // 25.5 m/sDimension Checking & Extremums (math.min and math.max)
Section titled “Dimension Checking & Extremums (math.min and math.max)”Functions like math.min() and math.max() compare quantities and units of matching physical dimension:
import std.unitimport std.math
let length1 = 15 * unit.meterlet length2 = 5 * unit.meterlet time = 10 * unit.second
// This works perfectly (same dimension: length)let longest = math.max(length1, length2)println(longest) // 15 m
let shortest = math.min(length1, 5 * unit.meter)println(shortest) // 5 m
// Comparing a quantity directly against a base unit (which has magnitude 1.0)let at_least_meter = math.max(0.5 * unit.meter, unit.meter)println(at_least_meter) // 1 m
// This throws a runtime error (cannot compare meters and seconds)// let error = math.max(length1, time)Trigonometric Functions (math.sin & math.cos)
Section titled “Trigonometric Functions (math.sin & math.cos)”Trigonometric functions like math.sin() and math.cos() strictly require a dimensionless input (e.g., an angle where all units have completely canceled out). If you supply a quantity with active units, the runtime will throw a dimensional error.
API Summary Table
Section titled “API Summary Table”| Method / Constant | Description |
|---|---|
unit.meter |
Constant representing the base unit for length (meters). |
unit.second |
Constant representing the base unit for time (seconds). |
unit.kilogram |
Constant representing the base unit for mass (kilograms). |
unit.Equation(kg, m, s) |
Returns a new custom unit composed of the exponents provided for kilograms, meters, and seconds. |
unit ^ n |
Raises a unit to the integer power n (e.g. unit.second^2). |
quantity ^ n |
Raises a quantity to power n, scaling magnitude and dimensional powers (e.g. (4 * unit.meter)^2). |
math.pow(base, exp) |
Raises a quantity or unit to an exponent while maintaining dimensional integrity. |
math.sqrt(q) |
Computes the square root, halving each even-powered unit dimension (e.g. math.sqrt(s^2) -> s). |
math.abs(q) |
Computes the magnitude of a quantity while preserving its unit. |
math.min(a, b) |
Returns the lesser of two quantities or units with identical physical dimensions. |
math.max(a, b) |
Returns the greater of two quantities or units with identical physical dimensions. |
