### Convert degrees to one of the 32 points of the compass

• The 32-point compass is... interesting, to say the least.

By Denelson83 (Own work) [GFDL or CC-BY-SA-3.0], via Wikimedia Commons

Your challenge is to take a degree measure, and convert it into a direction on the 32-point compass.

Each direction is 11.25 (360 / 32) degrees farther than the previous. For example, N (north) is 0 degrees, NbE (north by east) is 11.25 degrees, NNE (north-northeast) is 22.5 degrees, etc.

As for how you're supposed to get the directions,

• 0 degrees is N, 90 degrees is E, 180 degrees is S, and 270 degrees is W.

• These are called cardinal directions.

• The halfway points between the cardinal directions are simply the cardinal directions they're between concatenated. N or S always go first, and W or E always are second.

• These are called ordinal directions.

• The halfway points between the cardinal and ordinal directions are the directions they're between concatenated, again, with a "-" in between. Cardinal directions go first, ordinal second.

• These are called secondary-intercardinal directions.

• The halfway points between secondary-intercardinal directions and other directions are the other directions "by" the cardinal direction they're closest to (other than the one directly next to them, of course).

• I have no idea what these are called :P

If all this explanation hurts your brain as much as mine, you can refer to this chart:

``1   North               N2   North by east       NbE3   North-northeast     NNE4   Northeast by north  NEbN5   Northeast           NE6   Northeast by east   NEbE7   East-northeast      ENE8   East by north       EbN9   East                E10  East by south       EbS11  East-southeast      ESE12  Southeast by east   SEbE13  Southeast           SE14  Southeast by south  SEbS15  South-southeast     SSE16  South by east       SbE17  South               S18  South by west       SbW19  South-southwest     SSW20  Southwest by south  SWbS21  Southwest           SW22  Southwest by west   SWbW23  West-southwest      WSW24  West by south       WbS25  West                W26  West by north       WbN27  West-northwest      WNW28  Northwest by west   NWbW29  Northwest           NW30  Northwest by north  NWbN31  North-northwest     NNW32  North by west       NbW``

Here is a more detailed chart and possibly better explanation of the points of the compass.

Your challenge is to take input in degrees, and output the full name of the compass direction it corresponds to, along with its abbreviation.

Test cases:

``Input  Output0      North N23.97  North-northeast NNE33.7   Northeast by north NEbN73.12  East-northeast ENE73.13  East by north EbN219    Southwest by south SWbS275    West W276    West by north WbN287    West-northwest WNW``

All capitalization must be preserved, as in the test cases. Maximum number of decimal places is 2. All input numbers will be greater than or equal to 0, and less than 360. If a decimal point is present, there will be digits on both sides (you don't have to handle `.1` or `1.`).

This is , so the shortest code in bytes wins.

@WallyWest Hmm, this one allows arrays, has different capitalization, and has no "between," but I didn't notice that (possibly because of the... interesting title :P). I'll see what I can do to make it different enough...

@WallyWest There, now you have to output the abbreviation too. Along with all the other differences, that should be enough to make it a non-dup. (oh, also this one has dashes too)

@WallyWest There be no answers in "R" to your previous question (there weren't even any in "C"!) I hopes we'll see some this time, shipmates!

Would have been more fun if there were input from -360 to 360 degree (negative means anti-clockwise) and a bonus!.

For people not looking for a challenge, the easy solution is to find the possible output for which the distance is minimal from the input angle, using a lookup table angle <-> name.

• user2846289 Correct answer

7 years ago

## Perl, 250 236 231 188 187

Edit: Some bytes off exploiting symmetry (as I've seen in @bazzargh solution)

+Edit: And some evil tricks...

+Edit: Back to where I started (working with list, not string), and exploiting more symmetry = 1 byte off and a whole lot uglier.

``\$_=((@_=(1,@_=qw(1b3 1-13 13b1 13 13b3 3-13 3b1),3,map{y/1/2/r}[email protected]_)),map{y/312/421/r}@_)[int<>/11.25+.5];print ucfirst s/\w/(' by ',north,south,east,west)[\$&]/ger,' ',y/1-4-/NSEW/dr``

Pretty-printed:

``\$_=(    (@_=        (            1,            @_=qw(1b3 1-13 13b1 13 13b3 3-13 3b1),            3,            map{y/1/2/r}[email protected]_        )    ),map{y/312/421/r}@_)[int<>/11.25+.5];print ucfirst s/\w/(' by ',north,south,east,west)[\$&]/ger,' ',y/1-4-/NSEW/dr``

5.014 required because of `r` modifier.

You have a typo in your code: ***sourth*** should be ***south*** (2nd statement that starts with ***s/b/ by ...***

Those first 3 regexps can be replaced by y/NS/SN/; for 10 chars

@bazzargh, yes, and not only that ;-)