Skip to content

Add KilometerPerSecond — the unit every orbital state vector is quoted in, and the one kilometre unit #240 left out #274

Description

@matt-edmondson

The Speed dimension carries five units and none of them is km/s:

FootPerSecond KilometerPerHour Knot MeterPerSecond MilePerHour KilometerPerSecond
Speed ✓ ✓ ✓ ✓ (base) ✓ missing
Velocity1D ✓ ✓ ✓ ✓ ✓ missing

So a library that can express a car's speed five ways cannot express a satellite's at all without arithmetic at the call site.

Why this is #240's loose end rather than a new request

#240 added GravitationalParameter with CubicKilometerPerSecondSquared, whose summary says it exists because "the unit published values of mu are quoted in" is km³/s². That reasoning is exactly right and it applies more strongly one dimension down. The library today has:

  • Kilometer for lengths ✓
  • CubicKilometerPerSecondSquared for μ ✓
  • nothing for speed ✗

Kilometres are there for the distance and for the gravitational parameter, but not for the velocity that sits between them in every state vector. An orbital state is quoted in km and km/s, together, in every source that publishes one — Vallado, the SGP4 verification set, CelesTrak, Space-Track, JPL Horizons.

What a consumer does today

From ktsu-dev/Osculator, converting an SGP4 residual (SGP4 emits km/s):

private static Velocity1D<T> PerSecond(T kilometersPerSecond) =>
    Velocity1D<T>.FromMeterPerSecond(kilometersPerSecond * T.CreateChecked(1000));

The multiplication is exact in every storage type, so this is not a precision complaint — it is that the one factor of a thousand the whole domain is written in has to be spelled by hand, in a library whose entire point is that units are not spelled by hand.

Design

One unit and one conversion constant. No new dimension, no new type name, no relationship, so nothing for SEM008 to check.

units.json — a KilometerPerSecond entry, added to the Speed dimension's availableUnits.

conversions.json — KilometerPerSecondToMeterPerSecond, value "1000". Exact by definition, comfortably inside double, and a plain decimal literal, so SEM009 has nothing to say about it.

Naming follows the existing neighbours exactly — KilometerPerHourToMeterPerSecond, FootPerSecondToMeterPerSecond, KnotToMeterPerSecond — and the factory name follows the singular-lemma rule (#49) mechanically: FromKilometerPerSecond, beside FromKilometerPerHour.

Scope, and one difference from #240 worth checking rather than assuming

The alias props should not change. #240's note about Generate-AliasProps.ps1 applied because it added type names. This does not: I checked ktsu.Semantics.Quantities.Double.props and all 220 aliases name generic quantity types (Acceleration1D<double>); not one names a unit, because units are non-generic types in ktsu.Semantics.Quantities.Units and need no alias. Worth re-running the script and confirming a clean diff anyway, since verify-generated will fail the PR either way.

The vector forms are unaffected. Velocity2D/3D/4D have no From* factories at all — they expose Cross, Dot, Length, Magnitude, Normalize, DistanceTo and are built from components. So this adds Speed.FromKilometerPerSecond and Velocity1D.FromKilometerPerSecond, and the vector forms benefit only through whatever builds their components.

Worth considering alongside, but not in this issue

Acceleration has the same shape: MeterPerSecondSquared is the base and KilometerPerSecondSquared is likewise absent, and that is the unit perturbation accelerations are quoted in. I have not checked whether anything needs it yet, so I am not asking for it here — noting it so the two can be decided together if that is cheaper.


Raised from ktsu-dev/Osculator, where a doc comment claimed this had been filed upstream before it actually had. Filing it makes that comment true.

🤖 Generated with Claude Code

https://claude.ai/code/session_01Dn4fyZp3kQhh2199arTU6p

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions