atolf lftoa
Using SuperCollider I reverse-engineered two old MaxMSPJitter externals from Cycling'74. They came as part of the pluggo installer and were compiled in the cfm binary format. This format is since long-defunct and cfm externals can't be loaded into MaxMSPJitter running under Windows or newer Intel macs (afaik). Luckily I could still run the externals and help files under Max4.6 on my old PPC mac.
And as far as I could tell, the source code for these binaries was never released. So I took the trial&error route and managed to figure out how they work internally by using simple input strings like 'aa', 'ab', 'ac', 'ba', 'bb', 'aba', 'abc' etc. Then I just observed the output arrays of floating-point numbers and tried to mimic that in SuperCollider code. It was fairly quick to come up with the algorithms that encode (atolf
) and decode (lftoa
) shown below.
Also a note on MaxMSPJitter vs SuperCollider: no way I could have solved this using MaxMSPJitter only. Algorithms like these are horrendous to implement with patchcords. See the mess in the screenshots below. Also, MaxMSPJitter's floating-point number boxes, as well as the [print] object, does not show the whole 32bit float values! They round off to 6 digits after the decimal point. Why? So MaxMSPJitter can calculate just fine using 32bit floats as long as you don't try to print or output them in any way.
Anyway, I first wrote RedALF
for SuperCollider (it is now in the redSys quark) and from that, I then patched f0.atolf and f0.lftoa (now part of my f0.abs MaxMSPJitter abstractions).
(
~atolf= {|str|
var res= [1/2**5];
var tre= [2**12, 2**20, 2**28];
str.do{|chr, i|
var j= i.div(3);
if(i%3==2, {
res= res++(1/2**5);
});
res.put(j, res[j]+(chr.ascii/tre[i%3]));
};
res;
};
~lftoa= {|arr|
var res= "";
arr.do{|val|
var a, b, c;
val= val-(1/2**5)*(2**12);
a= val.asInteger;
val= val-a*(2**8);
b= val.asInteger;
val= val-b*(2**8);
c= val.asInteger;
res= res++a.asAscii++b.asAscii++c.asAscii;
};
res;
};
)
a= ~atolf.value("aber") //--> [0.055025476962328, 0.05908203125]
~lftoa.value(a) //--> "aber"