(def codetree (file)
(trav + 1 (readall (infile file))))
Anything that appears after two newlines and a blank space is treated as code, till there's a line that doesn't begin with a space. This is like the markdown convention, but you don't have to use four spaces; one will do.Incidentally, the code above tells me the number of nodes in the code tree of a file. Not just leaves, which would be
(len (flat (readall (infile file))))
but interior nodes as well. To me this is the best measure of how long a program is. I used to go by lines of code (def codelines (file)
(w/infile in file
(summing test
(whilet line (readline in)
(test (aand (find nonwhite line) (isnt it #\;)))))))
but I found this was encouraging me to do the wrong things.(This kind of test matters because I'm constantly trying to make news.yc shorter as a way of pushing functionality down into Arc.)
Here's trav, btw:
(def trav (f base tree)
(if (atom tree)
(base tree)
(f (trav f base (car tree)) (trav f base (cdr tree)))))
It traverses a tree, doing something at every node. So e.g. CL copy-tree would be (def copy-tree (tree) (trav cons (fn (x) x) tree))
If you're wondering how the second argument to trav in codetree could be 1, it's because a constant when called as a function simply returns itself. This turns out to be quite handy.The original writing(s) on Arc assumed a free lunch that would continue for decades (justifying a lack of emphasis on scalability and efficiency in implementation, I thought), which already seems kind of naive. You can already buy 8-core systems from Apple, mang. It's the future.
Just make sure that some concurrency package eventually becomes a de facto standard. Getting C libraries that use different threading implementations to interoperate is a nightmare, and I'd hate to see Arc go the same route.