Ambrus wrote:
> I wonder how fast a straightforward translation
> of this to J with control words would run.
Below is a translation as straightforward and mechanical as I could make it.
It's actually almost line-for-line. The only difference stems from the fact
that J lacks C's for(init;test;update) construct, so I had to replace that
one line for-loop with 3 lines (init, test, update) and a while-loop.
Note that the verb has a bug. The results it gives are wrong. I haven't
investigated this because I wanted to avoid "reading" the C code, lest it
bias my translation. One difference that may account for the error is that
the C consumes an integer and a char array, whereas J would balk at doing
arithmetic on characters, so the inputs are an integer and an integer array.
Performance is godawful:
ts=:6!:2 , 7!:2@:]
10 ts '(gij~ #&_9) 100'
0.0955389 11648
Note that's an average of a /tenth of a second/ to generate the first 100
terms of the series. This may improve when the bug is fixed, but I don't
imagine by much.
-Dan
NB. // OEIS A090822 Gijswijt's sequence
NB. void gij(int nm, char *a) {
gij =: dyad define
a =.x NB. args x=a, y=nm
nm=.y
NB. for(int n = 0; n < nm; n++) {
for_n. i. nm do.
NB. int r = 1;
r =. 1
NB. for (int l = 1; l <= n/2; l++) {
for_l. 1 +i.<.-:n do.
NB. int s = 0;
s =. 0
NB. int q = 0;
q =. 0
NB. while (! q) {
while. -.q do.
NB. s++;
s=.>:s
NB. if (l * (1+s) <= n)
if.(l * (1+s)) <: n do.
NB. for (int u = 1; !q && u <= l; u++)
u=.1
while. (-.q)*.(u <= l) do.
NB. q = a[ n - l * (s - 1) -
u] != a[ n - l * s - u];
q =.(a{~ n - (l * (s - 1)) -
u) ~: a{~ (n -(l * s)- u)
u =. >: u
end.
NB. else
else.
NB. q = 1;
q =. 1
end.
NB. }
end.
NB. if (r < s)
if. r < s do.
NB. r = s;
r =. s
end.
NB. }
end.
NB. a[n] = r;
a =. r n} a
NB. }
end.
NB.}
)
----------------------------------------------------------------------
For information about J forums see http://www.jsoftware.com/forums.htm