ramsey2879 said:
I get a set write error, i.e. "And" in "Co > 0 && Temp" is protected. What am I doing wrong?
I apologize. I wrote that without testing it. I try to never do that.
That line needed a pair of () for precedence and it should have been:
While[Co>0 && (Temp=Mod[6 S1-S0-6, Caa])>=1,S0=S1; S1=Temp; Co--];
I just tested this and believe that is correct now.
Your code is very slow and spends almost all its time inside that inner while loop.
You might try to find a more efficient way of computing that. Or you could try using an external C program through MathLink. Or you could try using Mathematica's Compile[] function, which has nothing to do with compiling external programs and is one of the least well documented features I ever use. Every time I try to write a Compile[] I want to tear my hair out. But after three attempts I offer you this. Note that I reduced the range it was searching through because I couldn't wait as long as it would have taken your original code to finish.
In[1]:= Timing[
Caa=1049001;
Reap[
While[Caa<1049101,
Co=(Caa-3)/2;S0=2;S1=3;
While[Co>0&&(Temp=Mod[6 S1-S0-6,Caa])>=1,S0=S1;S1=Temp;Co--];
If[Co==1,Sow[Caa]];
Caa+=2
]
]
]
Out[1]= {336.904 Second,{Null,{{1049011,1049051,1049077}}}}
In[2]:= Timing[
f=Compile[{{Co,_Integer},{S0,_Integer},{S1,_Integer},{Caa,_Integer}},
Module[{xCo=Co,xS0=S0,xS1=S1,Temp},
While[Temp=Mod[6 xS1-xS0-6, Caa]; xCo>0 && Temp>=1;xS0=xS1;xS1=Temp;xCo--];
xCo
]
];
Caa=1049001;
Reap[
While[Caa<1049101,
Co=(Caa-3)/2;S0=2;S1=3;
If[f[Co,S0,S1,Caa]==1,Sow[Caa]];
Caa+=2
]
]
]
Out[2]= {22.983 Second, {Null, {{1049011, 1049051, 1049077}}}}
Using Compile[] is fraught with difficulties and limitations, but if you can live with these you see that you can have about 10x the speed and the same output. Probably the one limitation you should watch out for is that all the integer values within Compile should be within +/- 2^31.
If you just strip the Timing[] off this then you should have the same result as your original code.
Tiny changes in this can make big differences, I moved one statement and gained another 50% in speed.
Type declarations in Compile[] for Temp and Mod[_] might help, or hurt, but I've never figured out how to do that correctly.
But if you fiddle with this and break it then I probably won't be the one to fix it.
If anyone would write the world's greatest set of clear guidelines for writing a Compile[] that will correctly do what I want on the first try then I might buy that person a cake.
I hope this is correct. Please point out any errors.
If you scrape that off the screen and paste it into Mathematica then watch out for the space inserted by the forum software between the I and n in {Caa,_Integer} above. I don't know why it does that but I've seen that before.