A compact Julia implementation of the NKTg law (varying inertia)

Hi everyone,

I’m sharing a small Julia module that encodes the core quantities of the NKTg law for varying inertia systems. The law considers:

  • position x
  • velocity v
  • mass m
  • momentum p = m * v

and two “tendencies”:

  • NKTg₁ = x · p (dot product for vectors)
  • NKTg₂ (related to mass change), provided in two forms:
    • scalar form: dm/dt * ||p||
    • vector form: dm/dt * p

Sign convention (interpretation):

  • If NKTg₁ > 0, the system tends to move away from a stable state.
  • If NKTg₁ < 0, the system tends to approach stability.
  • If NKTg₂ > 0, mass variation supports motion.
  • If NKTg₂ < 0, mass variation hinders motion.

Below is the Julia implementation as a self-contained module.


:backhand_index_pointing_right: On Julia Discourse you can also use inline math with LaTeX if you want it to render nicely:

NKTg₁ = $x \cdot p$  
NKTg₂ = $\dot m \,\|p\|$ or $\dot m p$

That way it will render clean, like NKTg1=x⋅pNKTg_1 = x \cdot pNKTg1​=x⋅p.

Do you want me to rewrite the whole post (intro + code + example) in Markdown

Below is the Julia implementation as a self-contained module.

module NKTgLaw

export momentum, nktg1, nktg2_scalar, nktg2_vector, tendency_signs

"""
    momentum(m, v)

Return momentum `p = m * v`.

- `m::Real`: mass (instantaneous).
- `v::Union{Real,AbstractVector}`: velocity (scalar or vector).
"""
function momentum(m::Real, v::Union{Real,AbstractVector})
    return m * v
end

"""
    nktg1(x, p; dot_product::Bool = true)

Compute NKTg₁ = x × p. For vectors, the default is the dot product (x ⋅ p)
to yield a scalar sign-friendly metric. If `dot_product=false` and `x,p`
are vectors of the same length, returns elementwise product.

- `x, p`: scalar or vector.
"""
function nktg1(x, p; dot_product::Bool = true)
    if isa(x, AbstractVector) && isa(p, AbstractVector)
        return dot_product ? dot(x, p) : x .* p
    else
        return x * p
    end
end

"""
    nktg2_scalar(dm_dt::Real, p)

Scalar form of NKTg₂ = (dm/dt) * ||p||.
Useful as a magnitude-only measure of mass-variation influence.

- `dm_dt`: mass time-derivative.
- `p`: momentum (scalar or vector).
"""
function nktg2_scalar(dm_dt::Real, p)
    pnorm = isa(p, AbstractVector) ? sqrt(sum(abs2, p)) : abs(p)
    return dm_dt * pnorm
end

"""
    nktg2_vector(dm_dt::Real, p)

Vector form of NKTg₂ = (dm/dt) * p.
Keeps the direction of the influence aligned with momentum.
"""
nktg2_vector(dm_dt::Real, p) = dm_dt * p

"""
    tendency_signs(n1, n2)

Sign-based interpretation:
- n1 > 0: tendency to move away from stability;
  n1 < 0: tendency to move toward stability.
- n2 > 0: mass variation supports motion;
  n2 < 0: mass variation hinders motion.

Returns a NamedTuple of textual hints.
"""
function tendency_signs(n1::Real, n2::Real)
    msg1 = n1 > 0 ? "NKTg₁ > 0 → tendency away from stability" :
           n1 < 0 ? "NKTg₁ < 0 → tendency toward stability" :
                    "NKTg₁ = 0 → neutral per x·p"
    msg2 = n2 > 0 ? "NKTg₂ > 0 → mass variation supports motion" :
           n2 < 0 ? "NKTg₂ < 0 → mass variation hinders motion" :
                    "NKTg₂ = 0 → no instantaneous influence from dm/dt"
    return (nktg1=msg1, nktg2=msg2)
end

end # module

Quick example

using .NKTgLaw

# Example state (units arbitrary)
x = [1.0, -2.0, 0.5]    # position relative to a reference
v = [3.0,  0.5, -1.0]   # velocity
m = 2.0                 # mass
dm_dt = -0.1            # losing mass (e.g., rocket-like)

p  = momentum(m, v)           # p = m * v
n1 = nktg1(x, p)              # scalar: x · p
n2 = nktg2_scalar(dm_dt, p)   # scalar: (dm/dt) * ||p||

println("p      = ", p)
println("NKTg₁  = ", n1)
println("NKTg₂  = ", n2)
println(tendency_signs(n1, n2))

Notes & rationale

  • I use the dot product for x and p to obtain a single signed scalar for NKTg_1; an elementwise option is also provided when needed.
  • Two NKTg_2 variants are included: scalar dm/dt * ||p|| for sign/magnitude reasoning and vector dm/dt * p for direction-aware analyses.

Feedback requested

  • Are there Julia API idioms or type signatures you’d suggest to make this more Julian?
  • Would you prefer only one canonical form for NKTg_2 in practice?

Thanks for any review or suggestions!