The deployed STACK (2026-08-19): geography + ArtaModel IV — public leaderboard 0.64303

The model that leads the public board of artamatch-genderless is not ArtaModel alone but a stack of three members with non-negative weights on their ranks, fitted per availability group on forward-chained train OOF:

member what it reads held out alone
GEO — plain + geography older/younger age at the start, their gap, the start year, the two birthplaces, their great-circle distance, order-free lat/lon extremes, same-place flag; three small LightGBMs averaged (geo_lgbm_{0,1,2}.txt, JSON dumps beside them) 0.6406
AM-G — ArtaModel IV greedy the phase model above, boosted over split single-phasor fields 0.6071
AM-F — ArtaModel IV fixed cycle the same phasors in a fixed cycle (the stable twin) 0.6184
group GEO AM-G AM-F bias
0 — wedding-sky clocks exist (t1/t2 Uranus) 2.055 0.355 0.335 +0.066
1 — synastry only (a Uranus) 1.467 0.390 0.000 -0.529
2 — wedding sky only 1.750 0.000 0.335 +0.260

logit = Σ wᵢ·(rankᵢ − 0.5) + b per group (a member that cannot speak for a pair casts no vote); ranks are read off the quantile grids stored in stack_iv_deployed.json; both orders of the pair are scored and averaged. Members are refitted on train + test for deployment; the weights are the fitted ones. Held out 0.6448 (7,631 pairs) · public board 0.64303 · the plain ages alone 0.6155. The gain is geography — where the two were born — not the sky; every other tradition tried (21 tropical traditions incl. numerology, 14 Jyotiṣa/Zǐ Wēi families) added nothing.

import sweshim, stack_iv_predictor as P                 # pure Python + numpy; the same files run in the browser
P.init(open("ephem4.bin","rb").read(), open("tables.json").read(), open("stack_iv_deployed.json").read(),
       [open(f"geo_lgbm_{k}.json").read() for k in range(3)], sweshim_module=sweshim)
r = P.predict("1936-08-04", 37.943, 23.647, "1924-05-14", 37.727, 26.909, "1968-06-15")
r["probability"], r["breakdown"]                          # 0.333 here; identical with the partners swapped

The match finder. best_matches(dob, lat, lon, start=None, top=20, min_age=18, max_age=100) scores the stack over every birthday of people alive at the start × the capital of every country (capitals.json, 197 — Wikidata P36 + P625): ~5.9 M candidates in about a second, by the model's structure (geography by year × capital, vectorised; ArtaModel by day from weekly-interpolated outer planets), one best day per (year, capital). Live on the prod page.

P._CAPS = json.load(open("capitals.json")); r = P.best_matches("1994-02-15", 35.6892, 51.389)   # Tehran, start = today
r["matches"][:3]   # [{dob, capital, country, lat, lon, probability, geo_probability, am_greedy_logit, am_fixed_logit}, ...]

The best start day. best_start_days(dob_1, lat_1, lon_1, dob_2, lat_2, lon_2, from_date=None, years=5, top=20) scores every day of the horizon for a pair (ages, weekday/month, the day's outer planets against each chart; 1 January skipped as the dataset's year-only placeholder) and returns the top days plus the best day of each month. Live on the prod page.

It is served live on the prod page: https://artaquest.github.io/artamatch/artamodel.html (Pyodide, nothing leaves the page). artamodel_iv_stack_deploy.py builds it; artamodel_iv_ensemble.py is the study it came out of.


ArtaModel IV — genderless

A genderless sidereal phase model of a long-term relationship, the fourth edition of ArtaModel (Arash Ashrafnejad, ArtaQuest Foundation, 2026-08-19: "I want a genderless model from now on"). Two births and birthplaces — in no order — and the date the relationship began, one probability out: did it last thirty years?

y = | b + Σᵢ  aᵢ ·e^{i|θ1ᵢ − θ2ᵢ|}     the absolute synastry angle          (even under the swap)
             + t1ᵢ·e^{i|θtᵢ − θ1ᵢ|}     the wedding sky to partner 1's chart
             + t2ᵢ·e^{i|θtᵢ − θ2ᵢ|}     the wedding sky to partner 2's chart
             + n1ᵢ·e^{i θ1ᵢ}            partner 1's own natal longitude
             + n2ᵢ·e^{i θ2ᵢ}            partner 2's own natal longitude
             + tnᵢ·e^{i θtᵢ} |²         the wedding sky itself

for each of fourteen bodies i (Sun, Moon, Mercury, Venus, Mars, Jupiter, Saturn, Uranus, Neptune, Pluto, Rāhu, Ketu, Chiron, Lilith). θ are sidereal longitudes (Lahiri) from Kerykeion (Swiss Ephemeris): births cast at 09:00 local time at the birthplace (nobody's birth time is recorded — the dataset's convention), the start at 12:00 UT. Genderless, three ways: no sex is read; every phase difference enters as its wrapped absolute value |Δθ| ∈ [0°, 180°], so each term is an even function of the swap; the training data carries every pair in both orders; and the scorer averages the two orders, so the answer is identical whichever way the partners are given. Every long-term relationship in Wikidata is in the data — marriages of every kind (same-sex included), unmarried partnerships, business and sporting partnerships, "significant person" pairs with family excluded. A term exists only when both of its phases exist: an unknown start day drops the wedding-sky terms, an unknown birth drops that partner's terms; a missing phase contributes exactly zero.

The deployed model, term by term

Gradient boosting over split single-sum fields: each stage is one field |bₖ + wₖ·e^{iφ}|² on one phasor, chosen greedily as the phasor that best explains the current residual (all 84 phasors of all six terms compete at every stage), added to the logit as stepₖ·(αₖ·u + cₖ). Fitted on all the data — train and test rows with both natal charts, 35,894 rows (every pair in both orders) — for 8 stages (the number the train-only fit chose on its inner temporal split). Of the 84 phasors offered it chose 3:

phasor body term stages contribution to the logit swing phase at which the field peaks
a_uranus Uranus a 4 0.151 176°
t2_neptune Neptune t2 2 0.099 195°
t1_neptune Neptune t1 2 0.081 331°

Never chosen, at any stage:

  • a (a·e^{i|θ1−θ2|}): 13 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, neptune, pluto, true_node, true_south_node, chiron, mean_lilith
  • t1 (t1·e^{i|θt−θ1|}): 13 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, pluto, true_node, true_south_node, chiron, mean_lilith
  • t2 (t2·e^{i|θt−θ2|}): 13 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, pluto, true_node, true_south_node, chiron, mean_lilith
  • n1 (n1·e^{iθ1}): 14 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, neptune, pluto, true_node, true_south_node, chiron, mean_lilith
  • n2 (n2·e^{iθ2}): 14 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, neptune, pluto, true_node, true_south_node, chiron, mean_lilith
  • tn (tn·e^{iθt}): 14 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, neptune, pluto, true_node, true_south_node, chiron, mean_lilith

Read plainly: a_uranus is the absolute gap between the two births measured by Uranus (4.3°/yr); t1_neptune and t2_neptune are each partner's age at the start measured by Neptune (2.2°/yr) — chosen as a pair, as a genderless model should. No natal phase, no wedding-sky phase, no fast body.

What it scores, honestly

on pairs born after 1900 (temporal hold-out; 7,631 pairs, both orders, symmetrised) AUC
ArtaModel IV, fitted on train alone (inner split 0.6326, 8 stages) 0.6252 (public board 0.6101)
the plain columns — the two ages at the start, the absolute gap, the start year (LightGBM) 0.6114 (public board 0.6000)
equal-weight rank average of the two 0.6289 (public board 0.6144)
ArtaModel IV with the two ages held flat (AUC within 3-year age cells) 0.5659

What the model reads is the two partners' ages at the start and the absolute gap between their births, through the outer planets as clocks — the same finding as every edition before it, now without a sex anywhere in the model. It is exactly invariant to the ayanāṁśa, the birth hour and the birthplace; the age-cell-matched row is what is left once the ages are held flat. See ARTAMODEL.md for the study (editions III and IV).

Use

from artamodel_score_iv import predict       # needs: numpy, kerykeion, timezonefinder
r = predict("1936-08-04", 37.943, 23.647,     # partner 1: dob, lat, lon
            "1924-05-14", 37.727, 26.909,     # partner 2 — the order does not matter
            "1968-06-15")                     # start date (YYYY-01-01 = year only -> wedding-sky terms dropped)
r["probability"], r["terms"], r["terms_swapped"]

artamodel_iv_deployed.json holds every stage's weights; artamodel_iv.py is the fit (with artamodel.py, artamodel_deploy.py, kerykeion_phases.py); artamodel_iv.json the leaderboard numbers. Data: artaquest-foundation/artamatch-genderless; competition: artamatch-genderless. CC0.


Edition III (superseded 2026-08-19): the gendered model, kept for the record

ArtaModel (third edition)

A sidereal phase model of a marriage, named by Arash Ashrafnejad (ArtaQuest Foundation, 2026-08-18). Three dates and two places in — his birth and birthplace, hers, and the wedding date — one probability out: did the marriage last thirty years?

y = | b + Σᵢ  aᵢ ·e^{i(θmᵢ − θdᵢ)}     mom's longitude minus dad's            (synastry)
             + mᵢ ·e^{i(θtᵢ − θmᵢ)}     the wedding sky minus mom's chart      (transit to mom)
             + dᵢ ·e^{i(θtᵢ − θdᵢ)}     the wedding sky minus dad's chart      (transit to dad)
             + mnᵢ·e^{i θmᵢ}            mom's own natal longitude
             + dnᵢ·e^{i θdᵢ}            dad's own natal longitude
             + tnᵢ·e^{i θtᵢ} |²         the wedding sky itself

for each of fourteen bodies i (Sun, Moon, Mercury, Venus, Mars, Jupiter, Saturn, Uranus, Neptune, Pluto, Rāhu, Ketu, Chiron, Lilith). θ are sidereal longitudes (Lahiri) from Kerykeion (Swiss Ephemeris): the births cast at 09:00 local time at the birthplace (nobody's birth time is recorded — this is the dataset's convention), the wedding at 12:00 UT. A term exists only when both of its phases exist: an unknown wedding day drops the wedding terms, an unknown birth drops that partner's terms; a missing phase contributes exactly zero.

The deployed model, term by term

The deployed model is gradient boosting over split single-sum fields: each stage is one field |bₖ + wₖ·e^{iφ}|² on one phasor φ, chosen greedily at that stage as the phasor that best explains the current residual (so all 84 phasors of all six terms compete at every stage), and added to the logit as stepₖ·(αₖ·u + cₖ). Fitted on all the data — train and test rows with both natal charts, 16,802 couples — for 31 stages (the number the train-only fit chose on its inner temporal split).

Of the 84 phasors offered, the boosting chose 6. Every one of them is an outer-planet clock:

phasor body term stages contribution to the logit swing phase at which the field peaks
a_uranus Uranus a 12 0.221 193°
d_pluto Pluto d 5 0.170 295°
d_neptune Neptune d 3 0.096 200°
d_uranus Uranus d 4 0.056 88°
m_pluto Pluto m 3 0.019 134°
m_saturn Saturn m 4 0.001 103°

Never chosen, at any stage:

  • a (a·e^{i(θm−θd)}): 13 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, neptune, pluto, true_node, true_south_node, chiron, mean_lilith
  • m (m·e^{i(θt−θm)}): 12 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, uranus, neptune, true_node, true_south_node, chiron, mean_lilith
  • d (d·e^{i(θt−θd)}): 11 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, true_node, true_south_node, chiron, mean_lilith
  • mn (mn·e^{iθm}): 14 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, neptune, pluto, true_node, true_south_node, chiron, mean_lilith
  • dn (dn·e^{iθd}): 14 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, neptune, pluto, true_node, true_south_node, chiron, mean_lilith
  • tn (tn·e^{iθt}): 14 bodies never chosen — sun, moon, mercury, venus, mars, jupiter, saturn, uranus, neptune, pluto, true_node, true_south_node, chiron, mean_lilith

Read plainly: a_uranus is the age gap between the two births measured by Uranus (4.3°/yr); d_pluto, d_neptune, d_uranus are the groom's age at the wedding measured by Pluto, Neptune and Uranus; m_pluto, m_saturn are the bride's. The model uses no natal phase, no wedding-sky phase, and no fast body — the study (ARTAMODEL.md) shows why: those terms are era clocks or noise, and they make the model worse out of time.

What it scores, honestly

on couples born after 1900 (temporal hold-out) AUC
this construction, fitted on train alone (its inner temporal split chose 31 stages) inner 0.6320 · held-out ≈ 0.62–0.64
the plain columns — two ages at the wedding, the gap, the start year (LightGBM) 0.6189–0.6371 depending on the row population
the same model with the two ages held flat (AUC within 3-year age cells) ≈ 0.50

The held-out AUC of ArtaModel is real, and every point of it is the two partners' ages at the wedding and the gap between their births, read through the outer planets as clocks. It is exactly invariant to the ayanāṁśa (a constant offset cancels in a phase difference), to the birth hour and to the birthplace; Uranus alone equals the whole model; the Sun alone scores 0.47; and it adds nothing to a plain model of the ages. This card says so because the study measured it, from every angle, on fixed populations — see ARTAMODEL.md and artamodel_study.json.

Use

from artamodel_score import predict          # needs: numpy, kerykeion, timezonefinder
r = predict("1936-08-04", 37.943, 23.647,     # dad: dob, lat, lon
            "1924-05-14", 37.727, 26.909,     # mom
            "1968-06-15")                     # wedding date (YYYY-01-01 = year only -> wedding terms dropped)
r["probability"], r["terms"]                  # the probability, and the stage-by-stage account

artamodel_deployed.json holds every stage's weights; artamodel.py / artamodel_ensemble.py / artamodel_deploy.py are the fit; kerykeion_phases.py the phase extraction. Data: artaquest-foundation/artamatch-sidereal; competition: artamatch-sidereal. CC0.

Downloads last month

-

Downloads are not tracked for this model. How to track
Inference Providers NEW
This model isn't deployed by any Inference Provider. 🙋 Ask for provider support