Showing posts with label racketlang. Show all posts
Showing posts with label racketlang. Show all posts

Saturday, December 11, 2010

Cyclicals and defensive shares

Here's a very interesting quick experiment I just conducted. I wanted to compare an easily calculable Graham-like estimate of growth rate against a least squares regression fit. I also wanted to see if it was possible to "spot the cycles" based on least squares regression. The results I obtained were better than I expected - maybe suspiciously so.

One of Graham's test for a defensive stock is that it shows at least an improvement of 1/3 over 10 years. He suggests taking the average of the first 3 years and comparing it with the average of the last 3 years. I did my test a little differently, to hopefully smooth out some anomolies that may exist. I take the median of the first 3 years and compare it with the median of the last 3 years. You can go a little further than that, and actually work out a compounding rate - which is a little more human-sensible. In this case, you take the ratio of the numbers to the power of 1/7. Why 1/7? Well, if you assume the median of the first 3 years occurs on year 2, and similarly the median of the last 3 years occurs on year 9 (whether or not this actually happens), then the span is 7 years.

This number can then be compared with the compound rate obtained by using a computed rate on a least squares regression under an exponential model. I was quite impressed by how close the numbers were - usually within 1 or 2 percent, on occasions 3%.

Pulling some quck stats at random, RWD has a compound rate of 12% using both the Graham-esque method, and using the least squares fit. BLT had a rate of 32% using the model, and 33% using the Graham-esque model. There's very good agreement going on.

Using a least-squares fit lets you do one extra thing - it allows you to calculate R^2, the co-efficient of variation. This, in effect, allows you to see how much of the variation is "explained" by your model. Take AZN, for example, it has a compound rate of nearly 16%, and an R^2 of 0.94. This means that 94% of the EPS figures are "explained" by the model. Some companies have extremely high R2.

This is interesting, because it allows us to get a handle on defensive stocks versus cyclical stocks. A lot of the defensive stocks I did a quick scan of had rather high coeffs of variation. This is what you might expect: defensive stocks have steady and growing and "predictable" earnings.

I then looked at 2 cyclical stocks: BARC, and BWY. They had R2 values of 0.11 and 0.18. In other words, earnings were difficult to explain away by a growth model. This, too, is what you'd expect. Defensive models have slow predictable earnings, whilst cyclicals are prone to violent earnings swings.

Now, just because all this fancy maths says stuff, doesn't mean that the future will be like the past. In fact, most people will take it as a red flag that too much maths is being used.

However, it is suggestive. It helps you a little in cross-checking with a stock is a defensive stock, or a cyclical. For a defensive stock, what you want to look for is good growth rates, predictiable earnings, and you want to couple that with a good dividend, hopefully low PER, high ROE, and strong balance sheet. You try to get yourself a portfolio of about 10 of them in diversified sectors so as to smooth out any errors that you will invetably make. Note that in the case of defensives, high ROE is likely to correspond with high PBV. So low PER and high ROE are likely (but naturally not proven) to be good characteristics of defensive shares you want to own (along with the other factors I mentioned).

Now compare that with cyclicals, where you're more likely to look for low PBV and, paradoxically, high PER (and hence probably bad ROE). So how you characterise a company will have a profound impact on how you value it.

Defensive and cyclical is not the only categories that a company might fit in, of course. There are asset plays and turnarounds, too, and no doubt a few other that you can come up with. Companies might even fill an intermediate position between defensives and cyclicals. I'm not sure how you'd approach them, though.

If you use my scheme racket library, then you can compute growth rates and R2 (R-Squared) quite easily. Here's how I computed BATS.L:
(define (stats sym vals)
  (print sym)
  (print (exp-fit vals))
  (newline))

(stats 'bats  '(
           56.93    61.82    66.54    69.21    75.83    89.34    97.32    108.53    128.78    153.00
           ))
I obtained the results:
'bats'#hash((rate . 1.1130174848886074) (r2 . 0.9714435167133138))
This tells me that BATS is growing ar 11.3% pa, and the model "explains" 97.1% of the data. The data input is EPS, BTW.

Wednesday, October 13, 2010

A stateful web counter in Racket

The idea of using Racket as a stateful web server is really beginning to attract me interest. I present below a simple web counter. Each time you click on the ++ link, it increments the counter. If you start it in a new tab/window, then it begins at 0. So each tab has its own state.


#lang racket
;;;; a stateful web server

(require web-server/formlets
         web-server/servlet
         web-server/servlet-env)


(define (counter request (count 0))    
  (send/suspend/dispatch 
   (lambda (k-url)
     `(html (head (title "Counter"))
            (body
             (p "Computer says: " ,(number->string count))
             (a ([href 
                  ,(k-url (lambda (request)
                                (counter (redirect/get) (+ 1 count))))
                  ]) "++")
             (p "Enjoy!"))))))


(define log-file 
  (path->string 
   (build-path (find-system-path 'home-dir) ;(expand-user-path "~") 
               "racket-server-access.txt")))
; would this work better?:
; e.g. (list (build-path "js") (build-path "css"))


;;; Start the server
(serve/servlet counter 
               #:port 8080 
               #:listen-ip #f 
               #:log-file log-file 
               #:servlet-path "/counter.rkt")




Sunday, September 5, 2010

DrRacket: a dirt-simple exception handler

Exception-handling in Racket is very powerful - but a little overwhelming to me. Suppose you want to do some very very simple exception handling: try something, but if it fails, return an error-value. The way you do this is by using with-handlers:

(with-handlers ([exn:fail? (lambda (exn) 
put-specified-default-here)])
   try-something-here)

There's a lot of goo here, which can be tidied up with some macrology. I give this simple macro, and a couple of examples below:

(define-syntax catch-errors
  (syntax-rules ()
          ((_ error-value body ...)
           (with-handlers ([exn:fail? (lambda (exn) error-value)])
             body ...))))

(catch-errors "Oops" (/ 1 0)) ; "Oops"
(catch-errors "Oops" (/ 6 3)) ; 2
(catch-errors "Oops" (/ 6 3) (/ 16 2)) ; 8