login
A328883
Denominators of the best rational approximations of log(6/5)/log(2).
0
1, 2, 3, 4, 11, 15, 19, 232, 251, 270, 289, 308, 327, 346, 365, 384, 403, 422, 1285, 1707, 2129, 3836, 28981, 32817, 36653, 40489, 44325, 48161, 51997, 3591629, 3643626, 3695623, 3747620, 3799617, 3851614, 3903611, 3955608, 4007605, 4059602, 4111599, 4163596, 4215593
OFFSET
1,2
COMMENTS
A list of equal temperaments (equal divisions of the octave) whose nearest scale steps are closer and closer approximations to the ratios of two tones of musical harmony: the minor third, 6/5 and its complement the major sixth, 5/3.
The numerical value of each term represents a musical scale based on an equal division of the octave. 19, for example, signifies the scale which is formed by dividing the octave into 19 equal parts.
The 19 equal temperament, first proposed and used by Guillaume Costeley in the 16th century, uses 19 equally spaced tones, offering better major thirds and far better minor thirds than normal 12-semitone equal temperament at the cost of a flatter fifth.
PROG
(Python 3)
import decimal
from math import floor
from decimal import Decimal as D
from collections import namedtuple
def continued_fraction(x, k):
cf = []
q = floor(x)
cf.append(q)
x = x - q
i = 0
while x != 0 and i < k:
q = floor(1 / x)
if q > k:
break
cf.append(q)
x = 1 / x - q
i += 1
return cf
def best_rational_approximation(clist, app):
hn0, kn0 = 0, 1
hn1, kn1 = 1, 0
ran, rad = 0, 0
conlist, finallist = [], []
fraction = namedtuple("fraction", "ratio, denom")
for n in clist:
for i in range(1, n + 1):
ran = hn0 + (i * hn1)
rad = kn0 + (i * kn1)
try:
if D.copy_abs(app-D(ran)/D(rad)) < D.copy_abs(app-D(hn1)/D(kn1)):
conlist.append(fraction(f'{ran}/{rad}', rad))
except:
pass
hn2 = (n * hn1) + hn0
kn2 = (n * kn1) + kn0
conlist.append(fraction(f'{hn2}/{kn2}', kn2))
hn0, kn0 = hn1, kn1
hn1, kn1 = hn2, kn2
#Change x.denom to x.ratio for the full ratio as a string
finallist = [ x.denom for x in sorted(conlist, key=lambda i: i.denom) ]
return list(dict.fromkeys(finallist))
if __name__ == "__main__":
prec = 200
decimal.getcontext().prec = prec
value = D(6/5).ln()/D(2).ln()
vc = continued_fraction(value, prec)
print(', '.join([str(x) for x in best_rational_approximation(vc, value)]))
KEYWORD
nonn,frac
AUTHOR
Daniel Hoyt, Oct 29 2019
STATUS
approved