Challenge: Make a data type for holding one of 8 directions allowing increment and overflow

Salih Dincer salihdb at hotmail.com
Wed Mar 13 05:45:01 UTC 2024


On Tuesday, 12 March 2024 at 05:38:03 UTC, Liam McGillivray wrote:
> Perhaps this would be a good programming challenge for someone 
> more experienced than me. Make a data type (probably a struct) 
> for holding one of 8 directional values using 3 bits. It should 
> accept the use of increment operators to change the angle.

D is such a perfect language that you can do the features you 
mentioned and more. I also implemented the following during my 
rookie years:

```d
alias Direction = enumSet;
union enumSet(T)
{
   T e;

   alias e this;
   struct
   {
     int i;

     auto opUnary(string op: "++")()
       => i = i < e.max ? ++i : e.min;

     auto opUnary(string op: "--")()
       => i = i > e.min ? --i : e.max;

     auto opOpAssign(string op: "+")(int val)
     {
       i += val;
       if(i > e.max) i -= e.max + 1;
     }

     auto opOpAssign(string op: "-")(int val)
     {
       i -= val;
       if(i < e.min) i += e.max + 1;
     }
   }

   string toString() const
     => e.to!string;
}

unittest
{
      auto direction = Direction!Directions(Directions.N);
      direction++;
      assert(direction == Directions.NE);
      direction+=3;
      assert(direction == Directions.S);
      direction--;
      assert(direction == Directions.SE);
      direction-=4;
      assert(direction == Directions.NW);
}

import std.stdio, std.conv;

void main()
{
   enum Directions
   {
     N , NE , E, SE, S, SW , W, NW
   }

   auto test = enumSet!Directions(Directions.W);
        test += 9; /*

        ++test; ++test; ++test;
        ++test; ++test; ++test;
        ++test; ++test; ++test;//*/

        test.writeln;

        test--; test--;
        test.writeln;
}
```

Here union was used with an extra template parameter. I also 
added 2 aliases to avoid confusion.

SDB at 79


More information about the Digitalmars-d-learn mailing list