[Question]
  [
Arrr... Ahoy there, me maties! Unfurl tha' mainsail! Full to starboard! Ah, feel th' wind in yer hair!
Right, me hearties... I be needin' a bit of yer codin' skills! Me crew are a li'l more modernized than meself... I still be preferrin' th' points of th' compass (see [here](http://en.wikipedia.org/wiki/Points_of_the_compass) for more info, Arrr...) while me crew are always usin' a headin'... I be wantin' an easy way of convertin' this twaddle they call a headin' into what I be able to understand, Arrr!
What I be needin' is code tha' be takin' input of a number (decimals are okay) such tha' `0 <= the headin' < 360` and it be spittin' out th' answer as th' closest compass point! Arrr!
Here be some examples:
`> heading 0.1`
`North`
`> heading 11.25`
`North by East`
`> heading 22.7`
`North Northeast`
`> heading 44.99`
`Northeast`
`> heading 91`
`East`
Now, if'n th' headin' ye be givin' be such that it falls exactly in th' middle of two compass points, don' ye be frettin', me hearties... I be expectin' th' code to spit out `Between <point 1> and <point 2>`, e.g. `heading 5.625` will say `Between North and North by East`
This only be happenin' for a headin' tha' be satisfyin' the equation `H = 5.625 + 11.25(N)` where H be th' headin' and N be an integer between 0 and 31 inclusive...
Two restrictions tho'...
1) I not be wantin' ye to use arrays for storin' yer data for the points or th' headin's... Tha' be cheatin', sir, an' ye be gettin' a taste of me blunderbuss... This has t' be calculated, jus' like th' old days! Arrr!
2) Shortest code wins, or I'll be makin' ye walk th' plank... Arrr!
  
[Answer]
I be spendin' way too much time on this here treasure hunt, but here's a solution in **Java**:
```
public class Aaaaarrrr {
    public static void main(String[] aaarrrgs) {
        float heading = Float.parseFloat(aaarrrgs[0]);
        final List<String> points = Arrays.asList("North",
                "North by east", "North-northeast", "Northeast by north",
                "Northeast", "Northeast by east", "East-northeast",
                "East by north", "East", "East by south", "East-southeast",
                "Southeast by east", "Southeast", "Southeast by south",
                "South-southeast", "South by east", "South", "South by west",
                "South-southwest", "Southwest by south", "Southwest",
                "Southwest by west", "West-southwest", "West by south", "West",
                "West by north", "West-northwest", "Northwest by west",
                "Northwest", "Northwest by north", "North-northwest",
                "North by west");
        float cp = heading / 360.0f * 32.0f;
        if (cp % 1 == 0.5f)
             System.out.print("Between " + points.get((int)Math.floor(cp)) + " and ");
         System.out.println(points.get(Math.round(cp)));
    }
}
```
*edit* If I minimize the above code and make it real ugly it would become this:
## Java, 770 chars
```
import java.util.*;class A{public static void main(String[] r){List<String> l=Arrays.asList("North","North by east","North-northeast","Northeast by north","Northeast","Northeast by east","East-northeast","East by north","East","East by south","East-southeast","Southeast by east","Southeast","Southeast by south","South-southeast","South by east","South","South by west","South-southwest","Southwest by south","Southwest","Southwest by west","West-southwest","West by south", "West","West by north","West-northwest","Northwest by west","Northwest","Northwest by north","North-northwest","North by west");float c=Float.parseFloat(r[0])/360.0f*32.0f;if (c%1==0.5f) System.out.print("Between "+l.get((int)Math.floor(c))+" and ");System.out.println(l.get(Math.round(c)));}}
```
[Answer]
## Perl 5.10 using substitution, 231 228 226 224
```
@c=(north,east,south,west);
@q=qw(P PbR P-Q QbP Q QbR R-Q RbP);
sub p{$j=$_[0]>>3&3;$_=$q[7&pop];s/P/$c[$j]/;s/Q/$c[$j+1&2]$c[$j|1]/;s/R/$c[$j+1&3]/;s/b/ by /;ucfirst}
$a=<>/11.25+.5;
say$a==int$a&&'Between '.p($a-1).' and ',p$a
```
Four newlines added for readability.
**Edit:** Golfed 2 more bytes using `pop`. Thanks @Dom Hastings
**Edit:** 2 bytes less using `qw()`
[Answer]
## Python, 264
```
n='north'
e='east'
s='south'
w='west'
b=' by '
def f(H):x,y,z=(n,e,s,w,e,s,w,n,n+e,s+e,s+w,n+w)[int(H%360/90)::4];return(x,x+b+y,x+'-'+z,z+b+x,z,z+b+y,y+'-'+z,y+b+x)[int(H%90*4/45)].capitalize()
h=input()+5.625
print h%11.25and f(h)or'Between '+f(h-1)+' and '+f(h)
```
This uses capitalisation as per the wikipedia page and should work for any number.
[Answer]
### Arrr Python, 336
```
A,R,r=int,input()/360.*32,' by #South#north#West#East#south#North#west#east#-#/#Between#and'.split('#')
a=''.join(r[A(c,16)]for c in'6A608A6928A6802A68A6808A4928A402A4A405A4958A1808A18A1805A1958A108A1A107A1957A1705A17A1707A3957A305A3A302A3927A6707A67A6702A6927A607').split('/')
if R%1==.5:print r[11],a[A(R)],r[12],
print a[A(round(R))]
```
Thanks @Jeen
[Answer]
## Perl 5.10, 262 257 254
Somewhat similar to one of the Python solutions:
```
$n=north;$e=east;$s=south;$w=west;
@d=($n,$n.$e,$e,$s.$e,$s,$s.$w,$w,$n.$w,$n);
sub p{$j=pop;$i=$j>>2;ucfirst(($d[$i],"$d[$i] by $d[$i+2&~1]","$d[$i+1&~1]-$d[$i|1]","$d[$i+1] by $d[$i&~1]")[$j&3])}
$a=<>/11.25+.5;
say$a==int$a&&'Between '.p($a-1).' and ',p$a
```
Four newlines added for readability.
**Edit:** Three bytes less thanks to @Dom Hastings
]