|
|
Line 1: |
Line 1: |
− | Programming language: gforth (should work in other forths too)
| |
| | | |
− | Experience level with language: quite a bit. I only had to look up a few things
| |
− |
| |
− | Time spent: 102 minutes
| |
− |
| |
− | Notes:
| |
− |
| |
− | 1) I implemented this problem once before in ruby (Don't think that helped too much though. The two languages have little in common.)
| |
− |
| |
− | 2) I wrote this from scratch, including a number parser and array/list code. In the real world one would hopefully already have code for these things.
| |
− |
| |
− | 3) This program expects gspc.txt to come through on stdin, so run like so: gforth jasonwoof_gspc.fs < gspc.txt
| |
− |
| |
− | <pre>
| |
− |
| |
− | #! /usr/bin/gforth
| |
− |
| |
− | warnings off
| |
− |
| |
− | fvariable bank 10000e bank f!
| |
− | : p>f s>d d>f 100e f/ ; ( pennies -- float )
| |
− |
| |
− | \ make a FOR that makes sense, and can take 0 as count, and UNLOOP
| |
− | : for 0 postpone literal postpone ?do ; immediate
| |
− | : next postpone loop ; immediate
| |
− |
| |
− | : ++ 1 swap +! ; ( var -- )
| |
− | : -- -1 swap +! ; ( var -- )
| |
− |
| |
− | \ kill the header
| |
− | : dump-line key 10 = if exit then recurse ;
| |
− | dump-line
| |
− |
| |
− | : dump-word key 32 = if exit then recurse ;
| |
− | : dump-others 6 for dump-word next ;
| |
− |
| |
− | variable #fields
| |
− | variable last-field
| |
− |
| |
− | : field-pop last-field @ 4 - dup last-field ! @ ; ( -- field ) \ return the next field
| |
− |
| |
− |
| |
− | : -parse-close key dup 10 = if drop exit then dup [char] . = if drop recurse exit then 48 - swap 10 * + recurse ;
| |
− | : parse-close 0 -parse-close ; ( -- pennies ) \ parse digits until end of line (ignoring decimal point)
| |
− | : parse-field dump-others parse-close , #fields ++ ; ( -- )
| |
− | : parse-fields begin key -1 = if exit then parse-field again ;
| |
− | parse-fields
| |
− | here last-field !
| |
− |
| |
− | fvariable last-close
| |
− | fvariable close
| |
− | fvariable sell-thresh
| |
− |
| |
− | \ initialize close
| |
− | field-pop p>f close f!
| |
− | #fields @ 1 - #fields !
| |
− |
| |
− | variable #holds
| |
− | create holds 1000 floats allot
| |
− | : hold-close-a 2 * floats holds + ;
| |
− | : hold-last-a #holds @ hold-close-a ;
| |
− | : hold-last-close! hold-last-a f! ;
| |
− | : hold-last-shares! hold-last-a float+ f! ;
| |
− | : hold-close@ hold-close-a f@ ;
| |
− | : hold-shares@ hold-close-a float+ f@ ;
| |
− | : hold-push hold-last-shares! close f@ hold-last-close! #holds ++ ; ( #shares -- )
| |
− | : hold-cleanup #holds @ dup for 1 - dup hold-close@ f0= 0= if unloop drop exit then #holds -- next drop ;
| |
− |
| |
− | : get-close close f@ last-close f! field-pop p>f close f! ; ( -- )
| |
− | : change close f@ last-close f@ f- last-close f@ f/ ; ( -- % )
| |
− | : withdraw bank f@ 10e f/ bank f@ fover f- bank f! ; ( -- cash )
| |
− | : deposit bank f@ f+ bank f! ; ( money -- )
| |
− | : buy withdraw close f@ f/ hold-push ;
| |
− | : ?buy change -0.03e f< if buy then ;
| |
− | : hold-sell dup float+ f@ close f@ f* deposit >r 0e r> f! ; ( addr -- )
| |
− | : -?hold-sell dup f@ sell-thresh f@ f> if drop exit then hold-sell ; ( addr -- )
| |
− | : ?hold-sell dup f@ f0= if drop exit then -?hold-sell ; ( addr -- )
| |
− | : set-sell-thresh close f@ 1.06e f/ sell-thresh f! ;
| |
− | : -sell #holds @ for i hold-close-a ?hold-sell next ;
| |
− | : sell set-sell-thresh -sell hold-cleanup ;
| |
− | : trade #fields @ for get-close ?buy sell next ;
| |
− | : sell-all 100000e sell-thresh f! -sell ;
| |
− |
| |
− | trade
| |
− | sell-all
| |
− |
| |
− | bank f@ f. cr bye
| |
− |
| |
− | </pre>
| |