From: William James Date: 2007-09-25T20:25:04+09:00 Subject: Re: I am new to Ruby and I could use some expert advice as to how I can make this code run faster. On Sep 24, 6:50 pm, "Ilmari Heikkinen" wrote: > On 9/24/07, Ilmari Heikkinen wrote: > > > On 9/24/07, Joel VanderWerf wrote: > > > On 9/24/07, Ilmari Heikkinen wrote: > > > ... > > > > And here's a C version: > > > > To give C its fair due, you might try with > > > > unsigned long *buf; > > > > and > > > > buf[i] |= 0x80808080; > > > > (and the other necessary changes, of course). > > > And a version with 64-bit ints was even faster. But it had a bug too. > > > Anyone wish to contribute working versions :)? > > Guess not, so here's one: > > $ time ./scramble64 trace trace.scramblec > > real 0m0.022s > user 0m0.004s > sys 0m0.020s > > $ export RUBYOPT= # -rubygems takes ~40ms > $ time ruby -rscramble -e 'scramble_nobu("trace")' > > real 0m0.049s > user 0m0.016s > sys 0m0.032s > > $ diff trace.scramble* > $ > > $ cat scramble64.c > > #include > #include > #include > #include > #include > > #define BUF_SIZE 4096 > > int main(int argc, char** argv) { > int i, j, k, rsz, wsz; > FILE *in_f, *out_f; > unsigned long long isz; > struct stat st; > long long buf[BUF_SIZE]; > > if (argc != 3) { > printf("USAGE: %s INFILE OUTFILE\n", argv[0]); > return 1; > } > > isz = sizeof(long long); > > in_f = fopen(argv[1], "r"); > if (NULL == in_f) { > printf("Failed to open input file %s\n", argv[0]); > return 2; > } > > out_f = fopen(argv[2], "w"); > if (NULL == out_f) { > printf("Failed to open output file %s\n", argv[1]); > fclose(in_f); > return 4; > } > > fstat(fileno(in_f), &st); > for(i=0,j = st.st_size / (isz*BUF_SIZE); i rsz = fread(buf, isz, BUF_SIZE, in_f); > for(k=0; k buf[k] |= 0x8080808080808080; > wsz = fwrite(buf, isz, rsz, out_f); > if (wsz != rsz) { > printf("Failed to write to output file\n"); > break; > } > } > rsz = fread(buf, 1, isz*BUF_SIZE, in_f); > for(k=0; k ((char*)buf)[k] |= 0x80; > wsz = fwrite(buf, 1, rsz, out_f); > if (wsz != rsz) { > printf("Failed to write to output file\n"); > } > > fclose(in_f); > fclose(out_f); > return 0;} Here's my version in FreeBasic. #define BUF_SIZE 4096 function scramble( filename as string ) as double dim outname as string dim as integer in_handle, out_handle, i, size dim buffer( 0 to BUF_SIZE - 1 ) as byte dim p as longint ptr outname = filename & ".scrambled" in_handle = freefile if open( filename, for binary access read, as in_handle) then ? "Can't read "; filename end 2 end if out_handle = freefile if open( outname, for binary access write as out_handle) then ? "Can't write to "; outname close in_handle end 4 end if while not eof( in_handle ) size = seek( in_handle ) get #in_handle, , buffer() size = seek( in_handle ) - size p = @buffer(0) while p < @buffer( BUF_SIZE ) *p = *p or &h8080808080808080 p += 1 wend if put( #out_handle, , buffer(0), size ) then ? "Failed while writing to "; outname exit while end if wend close '-- Caution. Closes all open files. return 0.0 end function if command(1) = "" then ? "Give me a filename next time." end 1 end if print -timer + scramble( command(1) ) + timer