Module:Limits: Difference between revisions
mNo edit summary |
m Refactoring |
||
Line 1: | Line 1: | ||
local rat = require('Module:Rational') | local rat = require('Module:Rational') | ||
local ET = require('Module:ET') | |||
local p = {} | local p = {} | ||
Line 41: | Line 42: | ||
-- `distinct`: whether distinct ratios are required to be mapped to distinct approximations | -- `distinct`: whether distinct ratios are required to be mapped to distinct approximations | ||
-- `previous`: already computed ratios for the previous iteraton | -- `previous`: already computed ratios for the previous iteraton | ||
function p.additively_consistent( | function p.additively_consistent(et, ratios, distinct, previous) | ||
distinct = distinct or false | distinct = distinct or false | ||
previous = previous or {} | previous = previous or {} | ||
if distinct then | if distinct then | ||
local approx_set = {} | local approx_set = {} | ||
for a_key, a in pairs(previous) do | for a_key, a in pairs(previous) do | ||
local a_approx = approximate(a) % size | local a_approx = ET.approximate(et, rat.as_float(a)) % et.size | ||
if approx_set[a_approx] then | if approx_set[a_approx] then | ||
return false | return false | ||
Line 57: | Line 55: | ||
end | end | ||
for a_key, a in pairs(ratios) do | for a_key, a in pairs(ratios) do | ||
local a_approx = approximate(a) % size | local a_approx = ET.approximate(et, rat.as_float(a)) % et.size | ||
if approx_set[a_approx] then | if approx_set[a_approx] then | ||
return false | return false | ||
Line 73: | Line 71: | ||
end | end | ||
for i, a in ipairs(ratios_ordered) do | for i, a in ipairs(ratios_ordered) do | ||
local a_approx = approximate(a) | local a_approx = ET.approximate(et, rat.as_float(a)) | ||
for j, b in ipairs(previous_ordered) do | for j, b in ipairs(previous_ordered) do | ||
local b_approx = approximate(b) | local b_approx = ET.approximate(et, rat.as_float(b)) | ||
local c = rat.mul(a, b) | local c = rat.mul(a, b) | ||
local c_approx = approximate(c) | local c_approx = ET.approximate(et, rat.as_float(c)) | ||
c = rat.modulo_mul(c, equave) | c = rat.modulo_mul(c, et.equave) | ||
local c_key = rat.as_ratio(c) | local c_key = rat.as_ratio(c) | ||
if previous[c_key] or ratios[c_key] then | if previous[c_key] or ratios[c_key] then | ||
Line 92: | Line 90: | ||
for j, b in ipairs(ratios_ordered) do | for j, b in ipairs(ratios_ordered) do | ||
if i <= j then | if i <= j then | ||
local b_approx = approximate(b) | local b_approx = ET.approximate(et, rat.as_float(b)) | ||
local c = rat.mul(a, b) | local c = rat.mul(a, b) | ||
local c_approx = approximate(c) | local c_approx = ET.approximate(et, rat.as_float(c)) | ||
c = rat.modulo_mul(c, equave) | c = rat.modulo_mul(c, et.equave) | ||
local c_key = rat.as_ratio(c) | local c_key = rat.as_ratio(c) | ||
if previous[c_key] or ratios[c_key] then | if previous[c_key] or ratios[c_key] then | ||
Line 115: | Line 113: | ||
-- returns nil when at least `max_n` | -- returns nil when at least `max_n` | ||
-- `distinct`: whether distinct ratios are required to be mapped to distinct approximations | -- `distinct`: whether distinct ratios are required to be mapped to distinct approximations | ||
function p.consistency_limit( | function p.consistency_limit(et, distinct, max_n) | ||
if size == 0 then | if et.size == 0 then | ||
-- the answer is known already | -- the answer is known already | ||
return '∞' | return '∞' | ||
end | end | ||
max_n = max_n or 1/0 | max_n = max_n or 1/0 | ||
distinct = distinct or false | distinct = distinct or false | ||
local n = 1 | local n = 1 | ||
Line 127: | Line 124: | ||
local previous = {} | local previous = {} | ||
while true do | while true do | ||
local ratios = p.limit_modulo_equave(n, equave, previous) | local ratios = p.limit_modulo_equave(n, et.equave, previous) | ||
for key, ratio in pairs(ratios) do | for key, ratio in pairs(ratios) do | ||
mw.log('step ' .. n .. ': ' .. key) | mw.log('step ' .. n .. ': ' .. key) | ||
end | end | ||
if next(ratios) ~= nil then | if next(ratios) ~= nil then | ||
local consistent = p.additively_consistent( | local consistent = p.additively_consistent(et, ratios, distinct, previous) | ||
if not consistent then | if not consistent then | ||
return last_n | return last_n |