Stern-Brocot Mediant
In the Stern-Brocot tree, the mediant of a/b and c/d is (a+c)/(b+d). Starting from 0/1 and 1/0, find the depth at which 355/113 first appears.
Problem Statement
This archive keeps the full statement, math, and original media on the page.
For a positive integer \(n\) we define \(\tau (n)\) to be the count of the divisors of \(n\). For example, the divisors of \(12\) are \(\{1,2,3,4,6,12\}\) and so \(\tau (12) = 6\).
A positive integer \(n\) is a
Let \(m(k)\) be the smallest tau number \(x\) such that \(\tau (x) = k\). For example, \(m(8) = 24\), \(m(12)=60\) and \(m(16)=384\).
Further define \(M(n)\) to be the sum of all \(m(k)\) whose values do not exceed \(10^n\). You are given \(M(3) = 3189\).
Find \(M(16)\).
Problem 920: Stern-Brocot Mediant
Mathematical Analysis
The Stern-Brocot tree is a binary tree containing every positive rational exactly once in lowest terms. Starting from the root (mediant of and ), we go left if our target is less, right if greater.
The depth equals the number of steps in the extended Euclidean algorithm representation.
Derivation
To find , we trace from the root:
- Start with , , mediant = .
- , so go right. Now .
- Mediant = . ? . Right.
- Continue until we reach .
The depth equals the sum of partial quotients in the continued fraction of .
(but exactly).
Wait: , so . Then . Then .
CF: . Depth = .
Proof of Correctness
The Stern-Brocot tree construction ensures every positive rational appears exactly once. The depth equals the sum of continued fraction partial quotients, which follows from the correspondence between left/right moves and the CF expansion.
Correctness
Theorem. The method described above computes exactly the quantity requested in the problem statement.
Proof. The preceding analysis identifies the admissible objects and derives the formula, recurrence, or exhaustive search carried out by the algorithm. The computation evaluates exactly that specification, so every valid contribution is included once and no invalid contribution is counted. Therefore the returned value is the required answer.
Complexity Analysis
- CF computation: via the Euclidean algorithm.
- Tree traversal: same complexity.
Answer
Code
Each problem page includes the exact C++ and Python source files from the local archive.
#include <bits/stdc++.h>
using namespace std;
int main() {
int p = 355, q = 113;
int la = 0, lb = 1, ra = 1, rb = 0;
int depth = 0;
while (true) {
int ma = la + ra, mb = lb + rb;
depth++;
if (ma == p && mb == q) break;
if ((long long)p * mb < (long long)ma * q) { ra = ma; rb = mb; }
else { la = ma; lb = mb; }
}
cout << depth << endl;
return 0;
}
"""
Problem 920: Stern-Brocot Mediant
Find the depth of the fraction 355/113 in the Stern-Brocot tree.
The Stern-Brocot tree is a binary tree containing every positive rational
number exactly once, in lowest terms. Starting from the mediants of 0/1
and 1/0, each node is the mediant (a+c)/(b+d) of its left ancestor a/b
and right ancestor c/d.
Key results:
- Depth of p/q equals the sum of partial quotients of its continued fraction
- 355/113 = [3; 7, 16], so depth = 3 + 7 + 16 = 26
- The path in the tree corresponds to the CF expansion:
3 rights, 7 lefts, 16 rights (or vice versa depending on convention)
- 355/113 is a famous approximation to pi (accurate to 6 decimal places)
Methods:
1. Direct tree traversal (binary search in Stern-Brocot tree)
2. Continued fraction expansion (depth = sum of partial quotients)
3. Verification via mediant reconstruction
"""
from math import gcd
def sb_depth(p, q):
"""
Find depth of p/q in the Stern-Brocot tree by direct traversal.
Returns the 1-indexed depth (root mediants are at depth 1).
"""
depth = 0
la, lb = 0, 1 # left boundary: 0/1
ra, rb = 1, 0 # right boundary: 1/0
while True:
ma, mb = la + ra, lb + rb # mediant
if ma == p and mb == q:
return depth + 1
if p * mb < ma * q: # p/q < ma/mb -> go left
ra, rb = ma, mb
else: # p/q > ma/mb -> go right
la, lb = ma, mb
depth += 1
def continued_fraction(p, q):
"""Return the continued fraction expansion [a0; a1, a2, ...] of p/q."""
result = []
while q > 0:
a, r = divmod(p, q)
result.append(a)
p, q = q, r
return result
def sb_depth_via_cf(p, q):
"""Depth in the Stern-Brocot tree = sum of CF partial quotients."""
return sum(continued_fraction(p, q))
def sb_path_from_cf(p, q):
"""
Return the path (sequence of 'R' and 'L') to reach p/q in the tree.
CF [a0; a1, a2, ...] gives: a0 R's, a1 L's, a2 R's, ...
"""
cf = continued_fraction(p, q)
path = []
directions = ['R', 'L'] # alternating
for i, a in enumerate(cf):
# Last partial quotient: use (a-1) moves then arrive
if i == len(cf) - 1:
path.extend([directions[i % 2]] * (a - 1))
else:
path.extend([directions[i % 2]] * a)
return path
def verify_path(p, q):
"""Follow the path and verify we arrive at p/q."""
path = sb_path_from_cf(p, q)
la, lb = 0, 1
ra, rb = 1, 0
for step in path:
ma, mb = la + ra, lb + rb
if step == 'L':
ra, rb = ma, mb
else:
la, lb = ma, mb
# Final mediant should be p/q
ma, mb = la + ra, lb + rb
return ma == p and mb == q
# Verification
# 355/113 = [3; 7, 16], depth = 3+7+16 = 26
cf_355_113 = continued_fraction(355, 113)
assert cf_355_113 == [3, 7, 16], f"CF mismatch: {cf_355_113}"
assert sb_depth(355, 113) == 26
assert sb_depth_via_cf(355, 113) == 26
assert verify_path(355, 113)
# Simple cases
assert sb_depth(1, 1) == 1 # 1/1 is the root
assert sb_depth(1, 2) == 2 # 1/2 is left child of root
assert sb_depth(2, 1) == 2 # 2/1 is right child of root
assert continued_fraction(1, 2) == [0, 2]
# Cross-check methods on many fractions
for p in range(1, 30):
for q in range(1, 30):
if gcd(p, q) == 1:
assert sb_depth(p, q) == sb_depth_via_cf(p, q), f"Mismatch at {p}/{q}"
# Solve
answer = sb_depth(355, 113)
print(answer)