17 June, 2013

Bike Ride 41 - To Trichardt and back - Bike ride

Monday the 17th June was a public holiday and the kids had made plans with their uncle to go go-carting. This left Trish and myself free to do whatever we liked. And it ended up being a bike ride to Trichardt and back.

The BMW club we belong to have an alphabet challenge. The challenge is there to get you out riding and experience South Africa. The idea is to visit a specified amount of towns, passes, light houses, and harbours. All of them are outside of Gauteng. Ever since we became members of the club 4 months ago I wanted to go and do a few towns. The "right" day just never happened. But on Monday the 17th June 2013 that all changed.

We left home at 06H50, so we could be at the Bapsfontein garage before 07H30 incase there were any other club members that wanted to join us on the days outing. We got there and waited till 07H35 and then left for Delmas. The ride there was blooming cold. It dipped to -3 deg Celsius at times. At Delmas we stopped for some petrol, and a hot beverage at Winmpy, which thankfully was open. We also stopped at a Delmas sign to take a photo for our towns visited album (Not a BMW challenge town).

Once we were warmed up, we left Delmas at 08H45, and attemped a geocache close to a dam. Since it looked like we night have to drive through a farmers land we opted to leave it and headed towards Leandra.

We left Leandra at 9H35, and rode via Kinross to Trichardt where we took our second BMW town photo before stopping at Marne Guest house (and bar) [S26 29.387 E29 13.807] for some lunch. We waited over 30 minutes for our burgers to arrive, but boy was it worth it. They were HUGE. And all for R45.00 each. We tried to order the "Large" burgers but since it was a public holiday they did not have the bigger rolls. Good thing, as we would not have been able to finish the larger ones.


We left Trichardt at 11H40 and headed towards 2 geocaches in Secunda. The one was at some type of time capsule, but the entrance was closed, so we attempted another one by the air field. Luckily we found that one. We also saw 2 aeroplanes taking off and landing. Nice smoke break we had there. We also rode past "Graceland" which seems to be a casino and golf club just outside Secunda town.

We had meant to go to Charl Cilliers town, but somehow I got mixed up in the next waypoint and we missed it. We had a quick stop at Evander before heading back to Leandra.

At 13H20 we took our BMW photo in front of the NG kerk in Eendracht, and then headed off to Eloff via Devon and Delmas.


Just before Devon we stopped at the sign which said "Devon Correctional services". The stupid guard told us we were not allowed to take photos without getting permission of the supervisor. I said Ok I'll chat to the supervisor but there was no phone in the hut, and we would have to sign in ride to the offices get permission and then take the photo. All to much trouble. So in the end I said we would leave it. Strange thing though I have it all on video. She (the guard) did not even notice it on my helmet.

In Devon itself we got a nice photo (not a BMW club challenge) in front of the "Boere vereniging sall". Nice little building, and well looked after in this small town. We left Devon at 14H45 heading Delmas to take our last photo at Eloff.

BMW Photo 4
As we met up on the main road just before Delmas we had two people pass us on BMW bikes. One was on a 1200 and an the other on a orange 650 twin. I wondered at the time if they were perhaps club members.

At Eloff we found a big pumpkin and decided to take our photo there, and then a quick stop at the local (shitty) garage for a toilet break, As we left town we saw a huge numberplate against a fence and thought it would make for an interesting photo, so it was a quick stop before heading home.

We were home at 15H15, having ridden a total of 324km.

After today our stats are as follows:
1) Towns visited: 21
2) BMW Tar Towns visited: 4


 Lessons learnt:
1) We will try and take a BMW challenge photo at the local church of each town.
2) A break every 40 odd minutes of riding suits both of us well.
3) Easy riding and lots of stops is an easy and interesting way to experience the towns of South Africa.
4) We are not yet bike fit.

Note: The photos where Trish and I are in have been "photo shopped" to show us both in the same photo. Can you see who was added and who is in the original photo?

11 May, 2013

Bike Ride 38 - Pretoria BMW Club at ADA, S & GS Slow skills, 11 May 2013

The BMW club had a Slow Skill day out at ADA at Hartebeespoort dam. This was the first time I went, and I asked my son Jerome and his friend Don with. Later on I learnt that it was meant for BMW Paid up members only (I mis-read the email).
All in all, another great day, and I learnt lots. I also learnt I need to better my balancing big time.

05 May, 2013

Bike Ride 37 - BMW Club - Easy GS ride to Que Sera - 5 May 2013

We have joind the BMW Club in Pretoria, for various reasons. But one reason is to go out riding in a group once a month. And we are loving these outings. I have decided to create short videos of the rides and upload to youtube. Hopefully with time I will see how I have progressed and got better at the off road riding.

This video was of the outing on the 5th of May 2013. We rode from Centurion via the train track lines, and sand highway all the way to Que Sera. From there we opted for the train tracks home. All in all a lekker  outing.



25 January, 2013

Solving a (formula based) Sudoku puzzle using LINQ

Last weekend (the 19th January 2012) we went to a geocaching event in Heidelburg here in South Africa. While at the event a new cache was published, and it consisted of a Sudoku puzzle with a twist. No numbers were given.

The puzzle looks like this:
We were about 5 people who solved the puzzle in about 30 minutes, and once back at work I showed a work collogue (lets call him Bob) the puzzle and we started chatting if it would be possible to write a LINQ query to solve this puzzle.

Bob showed me the MSDN Blog artice Using LINQ to solve puzzles and we used this as a basis to solve this Sudoku puzzle.

But first I wanted to understand how this LINQ query worked by simplifying the problem.

So I did the following:
I drew a small 3 by 3 grid and entered some numbers.
I entered "random" numbers from 1 to 9 into each cell. At this stage I am simulating one section of the Sudoku puzzle, so that when I write the LINQ query I can understand it better. It is much simpler to work with a 3x 3 grid and understand what is going on then working with a 9x9 grid.



Once I had the numbers then I made up some of my own formulas as follows:


As it happened I did enter 3 circular references. This helped me understand how the "from" and "joins" work later on. (See further below).









I started with the brute force method as per the MSDN blog, and the code looked like this:

         var solveForNumbers =
          from a1 in Enumerable.Range(1, 9)
          from a2 in Enumerable.Range(1, 9)
          from a3 in Enumerable.Range(1, 9)
          from b1 in Enumerable.Range(1, 9)
          from b2 in Enumerable.Range(1, 9)
          from b3 in Enumerable.Range(1, 9)
          from c1 in Enumerable.Range(1, 9)
          from c2 in Enumerable.Range(1, 9)
          from c3 in Enumerable.Range(1, 9)
          where (a1 == b3 - 4)
              && (a2 == a3 - b2)
              && (a3 == b2 * c3)
              && (b1 == a3 + a1)
              && (b2 == c2 - a3)
              && (b3 == a1 + a2)
              && (c1 == a3 + c3)
              && (c2 == a2 * b2)
              && (c3 == b3 - b2)
          select new
          { a1, a2, a3, b1, b2, b3, c1, c2, c3};

Solving the puzzle this way took around 110 seconds on my laptop. For the big puzzle to be solved would take exponentially longer.

I then started as per the MSDN blog post to move the "where" clause into a "joins". I wanted to see the speed improvements along the way.

I moved the 1st entry "c3" into a join as follows:
         var solveForNumbers1 =
          from a1 in Enumerable.Range(1, 9)
          from a2 in Enumerable.Range(1, 9)
          from a3 in Enumerable.Range(1, 9)
          from b1 in Enumerable.Range(1, 9)
          from b2 in Enumerable.Range(1, 9)
          from b3 in Enumerable.Range(1, 9)
          from c1 in Enumerable.Range(1, 9)
          from c2 in Enumerable.Range(1, 9)
          join c3 in Enumerable.Range(1, 9) on b3 - b2 equals c3
          where (a1 == b3 - 4)
              && (a2 == a3 - b2)
              && (a3 == b2 * c3)
              && (b1 == a3 + a1)
              && (b2 == c2 - a3)
              && (b3 == a1 + a2)
              && (c1 == a3 + c3)
              && (c2 == a2 * b2)
          select new
          { a1, a2, a3, b1, b2, b3, c1, c2, c3};

 I reran the test and now it took only 12 seconds.

With some help from Rankadu I moved them all across and ended up with this code:
        var solveForNumbers1 =
          from b2 in Enumerable.Range(1, 9)
          from a3 in Enumerable.Range(1, 9)
          from a1 in Enumerable.Range(1, 9)
          join a2 in Enumerable.Range(1, 9) on a3 - b2 equals a2
          join b3 in Enumerable.Range(1, 9) on a1 + a2 equals b3
          join c3 in Enumerable.Range(1, 9) on b3 - b2 equals c3
          join c2 in Enumerable.Range(1, 9) on a2 * b2 equals c2
          join b1 in Enumerable.Range(1, 9) on a3 + a1 equals b1
          join c1 in Enumerable.Range(1, 9) on a3 + c3 equals c1
          where (b2 == c2 - a3)
              && (a3 == b2 * c3)
              && (a1 == b3 - 4)
          select new
          { a1, a2, a3, b1, b2, b3, c1, c2, c3};


Some explanation is required here:
The reason b3, a3, and a1 are left in the "from" portion is that there is a circular reference to that value.

b2 == c2 - a3
and c2 == a2 * b2
and a2 == a3 - b2
(b2 depends on c2, and c2 depends on b2)
(b2 depends on c2, and c2 has a2, and a2 depends on b2)
 
So there is no reliable way for the "join" to know what the value is therefore it must be left in the from section of the code.





The ordering of the joins.
When a join is added the values of the formula must already be known at the time (previously defined).
Since c3 == b3 - b2, the value b3 and b2 must be defined before the c3 join.

This proved to be a 4 hour re-factoring job once I got to the 9x9 grid.







Once I had this in place and the tests running, I now knew how to solve the 9x9 grid.

While I was testing the proof of concept on the 3x3 grid Bob got going with the 9x9 grid brute force (or "where clause" method).

This is the result:
        var solveForNumbers =
            from a1 in Enumerable.Range(1, 9)
            from a2 in Enumerable.Range(1, 9)
            from a3 in Enumerable.Range(1, 9)
            from a4 in Enumerable.Range(1, 9)
            from a5 in Enumerable.Range(1, 9)
            from a6 in Enumerable.Range(1, 9)
            from a7 in Enumerable.Range(1, 9)
            from a8 in Enumerable.Range(1, 9)
            from a9 in Enumerable.Range(1, 9)
            from b1 in Enumerable.Range(1, 9)
            from b2 in Enumerable.Range(1, 9)
            from b3 in Enumerable.Range(1, 9)
            from b4 in Enumerable.Range(1, 9)
            from b5 in Enumerable.Range(1, 9)
            from b6 in Enumerable.Range(1, 9)
            from b7 in Enumerable.Range(1, 9)
            from b8 in Enumerable.Range(1, 9)
            from b9 in Enumerable.Range(1, 9)
            from c1 in Enumerable.Range(1, 9)
            from c2 in Enumerable.Range(1, 9)
            from c3 in Enumerable.Range(1, 9)
            from c4 in Enumerable.Range(1, 9)
            from c5 in Enumerable.Range(1, 9)
            from c6 in Enumerable.Range(1, 9)
            from c7 in Enumerable.Range(1, 9)
            from c8 in Enumerable.Range(1, 9)
            from c9 in Enumerable.Range(1, 9)
            from d1 in Enumerable.Range(1, 9)
            from d2 in Enumerable.Range(1, 9)
            from d3 in Enumerable.Range(1, 9)
            from d4 in Enumerable.Range(1, 9)
            from d5 in Enumerable.Range(1, 9)
            from d6 in Enumerable.Range(1, 9)
            from d7 in Enumerable.Range(1, 9)
            from d8 in Enumerable.Range(1, 9)
            from d9 in Enumerable.Range(1, 9)
            from e1 in Enumerable.Range(1, 9)
            from e2 in Enumerable.Range(1, 9)
            from e3 in Enumerable.Range(1, 9)
            from e4 in Enumerable.Range(1, 9)
            from e5 in Enumerable.Range(1, 9)
            from e6 in Enumerable.Range(1, 9)
            from e7 in Enumerable.Range(1, 9)
            from e8 in Enumerable.Range(1, 9)
            from e9 in Enumerable.Range(1, 9)
            from f1 in Enumerable.Range(1, 9)
            from f2 in Enumerable.Range(1, 9)
            from f3 in Enumerable.Range(1, 9)
            from f4 in Enumerable.Range(1, 9)
            from f5 in Enumerable.Range(1, 9)
            from f6 in Enumerable.Range(1, 9)
            from f7 in Enumerable.Range(1, 9)
            from f8 in Enumerable.Range(1, 9)
            from f9 in Enumerable.Range(1, 9)
            from g1 in Enumerable.Range(1, 9)
            from g2 in Enumerable.Range(1, 9)
            from g3 in Enumerable.Range(1, 9)
            from g4 in Enumerable.Range(1, 9)
            from g5 in Enumerable.Range(1, 9)
            from g6 in Enumerable.Range(1, 9)
            from g7 in Enumerable.Range(1, 9)
            from g8 in Enumerable.Range(1, 9)
            from g9 in Enumerable.Range(1, 9)
            from h1 in Enumerable.Range(1, 9)
            from h2 in Enumerable.Range(1, 9)
            from h3 in Enumerable.Range(1, 9)
            from h4 in Enumerable.Range(1, 9)
            from h5 in Enumerable.Range(1, 9)
            from h6 in Enumerable.Range(1, 9)
            from h7 in Enumerable.Range(1, 9)
            from h8 in Enumerable.Range(1, 9)
            from h9 in Enumerable.Range(1, 9)
            from i1 in Enumerable.Range(1, 9)
            from i2 in Enumerable.Range(1, 9)
            from i3 in Enumerable.Range(1, 9)
            from i4 in Enumerable.Range(1, 9)
            from i5 in Enumerable.Range(1, 9)
            from i6 in Enumerable.Range(1, 9)
            from i7 in Enumerable.Range(1, 9)
            from i8 in Enumerable.Range(1, 9)
            from i9 in Enumerable.Range(1, 9)
            where (a1 == e5 * e8)
                && (a2 == h1 - 2)
                && (a3 == c5 * e8)
                && (a4 == h9 - 1)
                && (a5 == d7 - e2)
                && (a6 == f1 + g7)
                && (a7 == e3 - h2)
                && (a8 == h6 + a9)
                && (a9 == g3 / g6)
                && (b1 == d1 - a9)
                && (b2 == g2 - h1)
                && (b3 == e5 - 4)
                && (b4 == c7 + 1)
                && (b5 == d7 - 7)
                && (b6 == i5 + d6)
                && (b7 == f8 + 1)
                && (b8 == a1 / i5)
                && (b9 == g3 + 3)
                && (c1 == i2 * a7)
                && (c2 == b4 * a7)
                && (c3 == c6 + 6)
                && (c4 == a2 * f5)
                && (c5 == c6 + 7)
                && (c6 == f8 - i3)
                && (c7 == d6 - 1)
                && (c8 == h8 + 1)
                && (c9 == g4 / c1)
                && (d1 == a7 * 3)
                && (d2 == i3 + a7)
                && (d3 == c2 - e2)
                && (d4 == f4 * i2)
                && (d5 == c4 + 2)
                && (d6 == h9 * e8)
                && (d7 == c4 * a2)
                && (d8 == d1 - a7)
                && (d9 == c1 * d4)
                && (e1 == i1 - e3)
                && (e2 == e3 + 3)
                && (e3 == d1 - g9)
                && (e4 == f1 + d1)
                && (e5 == d1 * 3)
                && (e6 == a5 + 4)
                && (e7 == g6 * h7)
                && (e8 == d9 - 7)
                && (e9 == i3 / e3)
                && (f1 == a3 / i2)
                && (f2 == b7 * e8)
                && (f3 == b6 * d3)
                && (f4 == h2 + 1)
                && (f5 == d1 - 2)
                && (f6 == g5 / b5)
                && (f7 == e3 * h3)
                && (f8 == h2 + h9)
                && (f9 == i1 - 3)
                && (g1 == c5 - f5)
                && (g2 == a6 + 2)
                && (g3 == e6 / a9)
                && (g4 == e8 + 7)
                && (g5 == d6 * a7)
                && (g6 == b1 + 1)
                && (g7 == h1 - 2)
                && (g8 == h5 - f4)
                && (g9 == a8 - a4)
                && (h1 == d2 - i2)
                && (h2 == h4 / i9)
                && (h3 == c7 - 2)
                && (h4 == f9 + 4)
                && (h5 == h2 + 6)
                && (h6 == d8 * 2)
                && (h7 == h1 - e9)
                && (h8 == f5 + 7)
                && (h9 == a1 - b8)
                && (i1 == f3 - b1)
                && (i2 == c9 / h7)
                && (i3 == i1 - c1)
                && (i4 == a6 - 6)
                && (i5 == d5 - d8)
                && (i6 == f6 + 2)
                && (i7 == c7 + 2)
                && (i8 == e3 + i2)
                && (i9 == f6 * g7)
            select new
            {
                a1,a2,a3,a4,a5,a6,a7,a8,a9,
                b1,b2,b3,b4,b5,b6,b7,b8,b9,
                c1,c2,c3,c4,c5,c6,c7,c8,c9,
                d1,d2,d3,d4,d5,d6,d7,d8,d9,
                e1,e2,e3,e4,e5,e6,e7,e8,e9,
                f1,f2,f3,f4,f5,f6,f7,f8,f9,
                g1,g2,g3,g4,g5,g6,g7,g8,g9,
                h1,h2,h3,h4,h5,h6,h7,h8,h9,
                i1,i2,i3,i4,i5,i6,i7,i8,i9
            };

This brute force method will take a hell of a long time to get the answer.

I ran it for an hour and the results at that point was only:
a1 to h9 all 1s and
i1=1, i3=1, i2=1, i4=1, i5=5, i6=1, i7=5, i8=5, i9=7
That is just over 33 000 iterations.

I took this code home and then over 4 hours of re-factoring the "where clauses" into "joins", and then re-ordering the joins I got to this code:
        var solveForNumbers =
            from i2 in Enumerable.Range(1, 9)
            from i5 in Enumerable.Range(1, 9)
            from h2 in Enumerable.Range(1, 9)
            from e3 in Enumerable.Range(1, 9)
            from a9 in Enumerable.Range(1, 9)
            join a7 in Enumerable.Range(1, 9) on e3 - h2 equals a7
            join d1 in Enumerable.Range(1, 9) on a7 * 3 equals d1
            join b1 in Enumerable.Range(1, 9) on d1 - a9 equals b1
            join g6 in Enumerable.Range(1, 9) on b1 + 1 equals g6
            join d8 in Enumerable.Range(1, 9) on d1 - a7 equals d8
            join h6 in Enumerable.Range(1, 9) on d8 * 2 equals h6
            join a8 in Enumerable.Range(1, 9) on h6 + a9 equals a8
            join e5 in Enumerable.Range(1, 9) on d1 * 3 equals e5
            join b3 in Enumerable.Range(1, 9) on e5 - 4 equals b3
            join f5 in Enumerable.Range(1, 9) on d1 - 2 equals f5
            join h8 in Enumerable.Range(1, 9) on f5 + 7 equals h8
            join c8 in Enumerable.Range(1, 9) on h8 + 1 equals c8
            join c1 in Enumerable.Range(1, 9) on i2 * a7 equals c1
            join e2 in Enumerable.Range(1, 9) on e3 + 3 equals e2
            join i8 in Enumerable.Range(1, 9) on e3 + i2 equals i8
            join h5 in Enumerable.Range(1, 9) on h2 + 6 equals h5
            join f4 in Enumerable.Range(1, 9) on h2 + 1 equals f4
            join d4 in Enumerable.Range(1, 9) on f4 * i2 equals d4
            join d9 in Enumerable.Range(1, 9) on c1 * d4 equals d9
            join e8 in Enumerable.Range(1, 9) on d9 - 7 equals e8
            join a1 in Enumerable.Range(1, 9) on e5 * e8 equals a1
            join b8 in Enumerable.Range(1, 9) on a1 / i5 equals b8
            join h9 in Enumerable.Range(1, 9) on a1 - b8 equals h9
            join a4 in Enumerable.Range(1, 9) on h9 - 1 equals a4
            join g9 in Enumerable.Range(1, 9) on a8 - a4 equals g9
            join f8 in Enumerable.Range(1, 9) on h2 + h9 equals f8
            join b7 in Enumerable.Range(1, 9) on f8 + 1 equals b7
            join d6 in Enumerable.Range(1, 9) on h9 * e8 equals d6
            join b6 in Enumerable.Range(1, 9) on i5 + d6 equals b6
            join c7 in Enumerable.Range(1, 9) on d6 - 1 equals c7
            join b4 in Enumerable.Range(1, 9) on c7 + 1 equals b4
            join c2 in Enumerable.Range(1, 9) on b4 * a7 equals c2
            join d3 in Enumerable.Range(1, 9) on c2 - e2 equals d3
            join f3 in Enumerable.Range(1, 9) on b6 * d3 equals f3
            join i1 in Enumerable.Range(1, 9) on f3 - b1 equals i1
            join e1 in Enumerable.Range(1, 9) on i1 - e3 equals e1
            join f9 in Enumerable.Range(1, 9) on i1 - 3 equals f9
            join h4 in Enumerable.Range(1, 9) on f9 + 4 equals h4
            join i3 in Enumerable.Range(1, 9) on i1 - c1 equals i3
            join c6 in Enumerable.Range(1, 9) on f8 - i3 equals c6
            join c3 in Enumerable.Range(1, 9) on c6 + 6 equals c3
            join c5 in Enumerable.Range(1, 9) on c6 + 7 equals c5
            join g1 in Enumerable.Range(1, 9) on c5 - f5 equals g1
            join a3 in Enumerable.Range(1, 9) on c5 * e8 equals a3
            join f1 in Enumerable.Range(1, 9) on a3 / i2 equals f1
            join e4 in Enumerable.Range(1, 9) on f1 + d1 equals e4
            join d2 in Enumerable.Range(1, 9) on i3 + a7 equals d2
            join h1 in Enumerable.Range(1, 9) on d2 - i2 equals h1
            join g7 in Enumerable.Range(1, 9) on h1 - 2 equals g7
            join a6 in Enumerable.Range(1, 9) on f1 + g7 equals a6
            join a2 in Enumerable.Range(1, 9) on h1 - 2 equals a2
            join c4 in Enumerable.Range(1, 9) on a2 * f5 equals c4
            join d5 in Enumerable.Range(1, 9) on c4 + 2 equals d5
            join d7 in Enumerable.Range(1, 9) on c4 * a2 equals d7
            join a5 in Enumerable.Range(1, 9) on d7 - e2 equals a5
            join i4 in Enumerable.Range(1, 9) on a6 - 6 equals i4
            join g2 in Enumerable.Range(1, 9) on a6 + 2 equals g2
            join b2 in Enumerable.Range(1, 9) on g2 - h1 equals b2
            join e6 in Enumerable.Range(1, 9) on a5 + 4 equals e6
            join g3 in Enumerable.Range(1, 9) on e6 / a9 equals g3
            join b9 in Enumerable.Range(1, 9) on g3 + 3 equals b9
            join b5 in Enumerable.Range(1, 9) on d7 - 7 equals b5
            join e9 in Enumerable.Range(1, 9) on i3 / e3 equals e9
            join h7 in Enumerable.Range(1, 9) on h1 - e9 equals h7
            join e7 in Enumerable.Range(1, 9) on g6 * h7 equals e7
            join i7 in Enumerable.Range(1, 9) on c7 + 2 equals i7
            join g5 in Enumerable.Range(1, 9) on d6 * a7 equals g5
            join f6 in Enumerable.Range(1, 9) on g5 / b5 equals f6
            join i9 in Enumerable.Range(1, 9) on f6 * g7 equals i9
            join i6 in Enumerable.Range(1, 9) on f6 + 2 equals i6
            join h3 in Enumerable.Range(1, 9) on c7 - 2 equals h3
            join f7 in Enumerable.Range(1, 9) on e3 * h3 equals f7
            join f2 in Enumerable.Range(1, 9) on b7 * e8 equals f2
            join g4 in Enumerable.Range(1, 9) on e8 + 7 equals g4
            join c9 in Enumerable.Range(1, 9) on g4 / c1 equals c9
            join g8 in Enumerable.Range(1, 9) on h5 - f4 equals g8
            where
                (e3 == d1 - g9) &&
                (a9 == g3 / g6) &&
                (h2 == h4 / i9) &&
                (i2 == c9 / h7) &&
                (i5 == d5 - d8)
            select new
                {
                    a1, a2, a3, a4, a5, a6, a7, a8, a9,
                    b1, b2, b3, b4, b5, b6, b7, b8, b9,
                    c1, c2, c3, c4, c5, c6, c7, c8, c9,
                    d1, d2, d3, d4, d5, d6, d7, d8, d9,
                    e1, e2, e3, e4, e5, e6, e7, e8, e9,
                    f1, f2, f3, f4, f5, f6, f7, f8, f9,
                    g1, g2, g3, g4, g5, g6, g7, g8, g9,
                    h1, h2, h3, h4, h5, h6, h7, h8, h9,
                    i1, i2, i3, i4, i5, i6, i7, i8, i9
                };
I ran the code and then the answer was calculated in a mere 8 seconds.

Conclusion:
1) LINQ can be used to solve different types of puzzles.
2) Using joins greatly reduces the time spent to find the answer.
3) Formulas in the sheet which refer back to themselves cannot be added to a join, and can only be used in the "from" section. This means the LINQ query must *guess* these values. The less guesses there are the faster the answer will be calculated.

Todo:
1) The LINQ query above only solves this one single Sudoku puzzle. It would be interesting to come up with a generic solutions that would work for any Sudoku puzzle of this type.
2) It would be interesting to see if I can get to a general Sudoku LINQ solver for a normal Sudoku puzzle.
3) Better understand *how* the joins speed up the calculation.

26 January, 2012

Bike Ride 9 - To Dullstroom via Loskop dam by sand road, and back to Johannesburg via tar backroads, a good weekend outing

The weekend of the 21st and 22nd January 2012 was my first truly long distance ride. And it was an AWESOME weekend.

Background
I had joined up on the Think Bike forum, and browsing around saw that there was a trip planned from Bapsfontein, using mostly sand roads to Dullstroom via Loskop dam. This looked like lots of fun. So I signed up for the ride, and couldn't wait for the weekend to arrive. It would have been nice if Trish came along, but with hindsight it was maybe better, as I think some of the sand roads would have been to rough with two of us on the bike.

The originator of the ride was a guy with the nick name "iamgigglz", (each time I see his nick I think of a geocache we did close to Bapsfontein [Biggels will like it here]) and the idea was make a non technical ride from Bapsfontein, all the way to Dullstroom via Loskop dam, using as much sand road as possible. In the Garmin track log below, the purple sections are the sand roads we took, and the red ones are tar.

Que Sera to Bronkhorstspruit 
Sand road: 8 km
Tar road: 34 km

Photo taken by "Fox"
I arrived at Que Serra at about 7H30, and saw only one bunch of guys in the whole parking lot. It must be the guys leaving for Dullstroom, so I parked my bike close by and introduced myself. I got to hear a lot of names, but honestly couldn't remember many. Some guys asked me where the 69 of my forum name came from (my forum name is AntonD69). "It's the year I am born in" was my reply. They all laughed, as they thought otherwise.
After a hearty breakfast of bacon, eggs, pap, and tea (or coffee) all for R55.00 we left for our first route stop in Bronkhorstspruit. This is also where I got my first proper taste of sand road. I was about the 3rd bike of 12 to go onto the sand road, but as I felt very uneasy on the dirt, lots of the bikes started to pass me. A few times the front tyre was sliding along the gravel and I panicked a few times. Luckily I did not drop the bike, and slowed down grammatically. At the end of the sand ride the others were patiently waiting for me. Shjoe ... I made it.
I was later to learn this is the way it is done. The mavericks (fast guys) go on ahead, having their speedy fun, but once one arrives at a intersection or tar road, where the group could possibly be split up, all wait till everyone has regrouped. Lots of times either Brendon or luv2ride was behind me making sure that even the slow ones make it all the way (thanks guys).
We all filled up with petrol, as the next fuel stop would only be Loskop dam. My tank made it all the way to Dullstroom, with still lots of fuel to spare.


Bronkhorstspruit to Loskop dam
Sand road: 73 km
Tar road: 37 km
taken by "iamgigglz"
After we all filled up with fuel, and met at the other end of town we set off for Loskop dam. We hit some more dirt road, which wasn't as bad as the 1st patch, and I was able to keep up (mostly) with the group. I decided to stay at the back, then there would be nothing for me to proof, nor the need to worry about anybody passing me. I saw some guys stand up on their foot pegs and ride at around 60 to 70 km per house over the sand. I initially thought it was their way to get above the dust, but at the smoke break stop after the 1st patch of sand road I was to learn from luv2ride that its a better way to get across the sand. He always stands on his pegs whenever he crosses sand. As the day progressed I slowly started to stand more and more. First I started at slow speeds and higher gears, but by the end of the day was pretty good. I just sat down on the seat when we got to corners. I still wasn't confident enough to stand and lean with them. 

As I felt a little more relaxed now riding on sand I was starting to enjoy the scenery a little more, but still had to concentrate a heck of  lot on the road. We entered some beautiful hills and valleys. Amazing greenery all the way around. Its such a pity that I could only take photos at our stops. At one point coming down a hill, we passed a small rural village, and from afar one could see two rusted tins standing in the middle of the road. WTH (or F)? AS I got closer and closer, I saw the tyre marks go past the right of the tins, and started to follow, and then saw a donga of about .5 metres deep and maybe a meter across where the tins where. So now I know what 'rural' traffic cones look like.
At Loskop we stopped for lunch at the Bospot Restaurant. I had a Cheese hamburger, which had a nice thick patty, and a sprite. Total cost I think was R56.00. I cleaned my visor with a tisshe, and then from Gryshond was able to use a slightly wet shamy which made it nice and clean. (Note to self: Get one for sand roads). We stopped over at the dam wall for some photos.
While at the dam wall I decided to go and attempt the cache 1.4 km away, but on arrival saw I had to climb a small hill. In full bike gear, a full stomach and the midday heat, I decided to rather leave it.
After returning to the others at the dam wall, and taking some more photos we left for Dullstroom.


Loskop dam to Dullstroom / Elandskloof
Sand road: 72 km
Tar road: 60 km


The first part of the ride down into the valley was on tar, but soon enough we turned off onto a dirt road, with a game fence on the one side. Beautiful greenery all the way around. It was on this stretch of road with a long open, compacted sand that I took the bike up to 100 kmph. Only for a short bit though then it was down to 70-80 again. At the end they were all waiting for me again, and we decided to go to a small pub which came highly recommended.
On entering the small village of Laersdrif, we passed a small grey stone church, and then onto a farm or something where the pub was to be. The last section was on gravel, where the front wheel was sliding a bit, and now with much more experience I didn't find it that bad.
The pub was closed but we were greeted by two dogs. The big one seemed very happy to see us. After a rest, and some cold water, we took the road again, which was to be the last sand section before we get to Dullstroom.
Just by the Police station we turned back onto the sand road, and drove past farms and small rural villages. It amazes me that one can ride for 5 to 10 minutes, with no settlements in sight, and then a huge house is found, with no clear means of income. I would have thought one would see sheep, or cattle.
We entered a small pass, and rapidly, within 2.5 km, climbed from 1700 m asl to about 1900 m asl. Most of the way up the pass I rode in 1st and 2nd gear, and lots of times I stood up as well. Just when it got a little to technical, I opted to sit down. 
At a T-junction we regrouped, and on this stretch was another geocache, but as we got to it, I opted to rather leave it, as I did not want to keep the group up, and it was nearing 17H00, and we still had to get meat and drinks for the evening.
Once in Dullstroom, some people filled up their bikes, I phoned Trish to say we had arrived, and then drew some money at the ATM, and bought a lekker T-Bone steak, a piece of wors, and 6 rolls, as well as 2 beers, and some milk for tea. All in all it came to just over R100.00.
Once we all had our stuff, we set of for the last stop of the day; Elandskloof.

Elandskloof

The last bit of road to Elandskloof was quite bumpy after all the rain and tyre tracks made in soft mud (which were mostly dry by now). A normal sedan would make it if it rode slowly.
After sorting every thing out at reception we rode the last 4 km down to the chalets and
Lovely little place. I had to pay R125.00 towards my share of the chalet, which was more then reasonable and slept 6 people. I stayed with Brendon and his family, and luv2ride. 
Before dinner we had a quick dip in the indoor swimming pool and jacuzzi.We had quite some trouble getting the fire to start as we had no fire-lighters, but my small pointy knife which I always carry with me, saved the day when I split up some small logs, Bear Grylls style.
The T-Bone, pap made by Speedy Vee, and buttered roll, with some rooster koekies went down well. I don't remember much after my head hit the pillow.
I awoke the next morning, and got up just after 7  and decided to go and take some early morning photos. Some people were up already, and others were still sound asleep.
The morning went quite quick. Speedy Vee made us breakfast with only 4 eggs, but with the bacon and left of boerewors from last night, it fed us chalet dwellers, and about another 4 campers. 


Once we were all packed, we took one final group photo of us all with our bikes by the water's edge, and then set of for a final visit to Dullstroom, where we had breakfast "pudding" at Harrie's Pancakes. I joined the group after completing a geocache. I am glad that I got it, as I needed a "green block" for today.

Elandskloof all the way home.
Tar road: 280 km (took 5H30m including the stops)

After breakfast "pudding", we split up as a group. Some riders wanted the fast way home, over the N4 toll road. It was iamgigglz, bikerMom, The pink Duck and me who opted for the more scenic route home, by using tar road, but avoiding the toll road and sand roads.




A pretty uneventful trip from Dullstroom to Belfast. We got onto the N4 for a few kilometres, and then back onto the R104 to Middleburg.
Somewhere on this road we had a bakkie in front of us, and all of a sudden he left the road, and rode next to the mielie fields. "He must be a farmer going into the fields" I thought. I had not even completed the thought and he was motioning to us to slow down. With this the pot holes started and it got so bad that we also left to "tar" road and joined the bakkie next to the mielie fields. This happened to us another 3 or 4 times till we got to Witbank.
In Witbank I wanted to do an earth cache. It was about the burning coal fields which is the longest burning fire in South Africa. It was also the chance to show group members what "earch caching" was all about. But alas, it was visually a very boring earth cache. I took some photos, and read out aloud the basics of the earth cache, but I think it was all lost on them. Pity. 
From Witbank the plan was to take the N12 home via Benoni, but the GPSr took us home via the N4. This was very confusing to me, as I did not recognise the road, and I had travelled the N12 many times. Three off ramps later I realised what was going on and we took the rural road toward Kendal and Ogies, and got onto the N12. We stopped one last time at the Delmas off ramp. My bum was getting seriously numb / sore by now. My water was still ice cold though, and lekker to drink after the hot ride.
Once at the R21 crossing, I waved the rest of my group goodbye and rode the last little bit in rain home. At least I wasn't soaked when I got home. With hindsight I should have invited the rest of the group over to wait for the rain to pass.


Home
Once home, Trish took all my dirty bike gear and washed it with NikWax, and I added it to the dry rack so it would be ready for Monday morning's ride to work. I also degreased and cleaned my chain, as well as the rest of the bike, and after it was dry, added special wax to the chain again.
I didn't make the Sunday night movie, and was in bed just after 8PM.

08 January, 2012

Bike ride 5 - Pretoria, Magalies, Home (350 km)

What a weekend it was.

My folks wanted to go camping with our kids for a few days not to far away. They choose Mountain Sanctuary Park just outside Rustenburg.

Trish and I decided we would go and visit them on the bike. But the 150 odd kilometres one way seemed a little much for both of us, and since we had never driven from Pretoria to Hartebeespoort dam opted to go and stay with some friends in Pretoria.
I also knew that there was a very old geocache on the Magalies mountains, and when checking up on it found that it was a mere 5 km from the resort we were going to. We made all our arrangements which included an overnight stay for Peanut at Marius and Anneke, and then waited for the weekend to arrive.

Friday arrived, and we dropped of Peanut, gave Bobbie enough food for the day, and left for Pretoria on the bike just after 6 PM. 

All went well until we got to the fountains circle. There the road was somewhat wet, which caused us to slow down and it looked like rain was immanent. We looked for a place to stop by couldn't find any suitable spot, so just rode on. Luckily it did not start raining. We briefly stopped for a geocache on the south side of the mountain, and then got to Oliver and Gloria's place just after 19H10.
We spent the evening chatting on their stoep, and later on watched a Jeff Danham video. I fell asleep half way through it, and missed the best part. Oh well, will just have to get the video ourselves now.

The next morning we left at 7H20. A little later then I had wanted too. It was a very enjoyable ride from there to Brits. We stopped of for a Tonteldoos geocache, on the way to the Chameleon village close to Hartebeespoort dam. We had a brief walk through the curio shops and got a new wallet for Trish at a "discount" of R150.00. Then we had breakfast at Woodies. Trish had a hamburger, and I had some type of breakfast. It was to much for me, and couldn't finish it.

The next stop was the Maanhaarrand geocache. It is one of the oldest 25 in the country. I have been wanting to do it for a long time now, but either the detour would have been to far, or we were to late in the day to do it. However.... now doing some research on the cache, I see the road to the cache is only accessible by 4x4s. So even if we had the time previously to do the cache we would not have succeeded. 

We took to by-road from Hartebeespoortdam, which was a much more pleasent bike ride then the highway. Once I had to break very quickly, as I had almost missed seeing the speedbump in the road. We turned off the R104, and rode past Buffelspoort dam.

Soon we were on the sand road, and going up the mountain. From my GPS track I see it took us 20 minutes to get the 5 km up the mountain. The bike is new, and I don't want it to fall over, so I took it really slow.

Once we got to the top, there in front of us was a small front wheel car. How the hell it had gotten up there I have no idea. Either the person had lots of patience, or it was a hired car.
We were told that approaching the geocache form the South Side was much more difficult then from the North side. So its beyond me how this little car got up there.

Trish opted to stay with the bike, and I scrambled up the koppie, after taking a few sips of the refreshing ice cold water we had with us. I expected to search for quite a while, but located the geocache in no time. I signed the log sheet, and did not trade anything, as I left all my "swag" in my bike jacket with Trish and the bike.

Took some photos, and a 180 degree panorama, before returning to the bike.

Back at the bike, Trish said 3 4x4s had passed. I had only seen two. After suiting up again we slowly returned to the bottom of the hill from where we came. Almost at the bottom we were overtaken by 3 mountain bikes. I got quite a fright, as it was very unexpected. This also made me realise how slow I was going, and soon picked up a little more speed. A little further on I got my own back, by passing them on an uphill.

We turned right at the corner shop, and now knew we were on our last few kilometres from our final destination. A few times we went through very soft sand, and as this was also very unexpected and the front wheel did tart to slide on the soft sand. Slowing down seemed to be a lot better.

At the camp side we paid our R50.00 per person and R20.00 for the "car", and then parked the bike under s shady tree right next to my parent's camp site (no 21).

The afternoon went very quick. I went for a quick swim with Anya. Then we had a lekker potjie lunch, and afterwards Pappa, Calra, Anya and myself took a walk up to the "Sliding pools". There we found a pool, and jumped in. It was nice and relaxing. After we had our fun, we walked down to the actual sliding pool, and Anya showed Carla and me how it worked. As I had already my walking shoes on, I did not join her. Then it was the 1.2 km hike back to the tents.

Jerome and Alex got sunburnt the previous day, and had enough of all of the camping. They opted to leave with Carla, a day early, and go home. So it was only Anya who stayed behind with Ouma and Oupa for the full camping trip (Well done girl!).

The ride back was 150 kilometers, and felt much longer. At Mooinooi we got onto the highway, and then off again at Hartebeespoortdam. We stopped in the little town for a smoke break. Must say the ride on the highway was very boring, taking the R104 was much more exciting.

We stopped on more time for another smoke break just before the Olifantsfontein on ramp to give our bums another rest, and then took the N1 South, N3 South, R24 all the way home.


All in all a very enjoyable weekend, but it was a very long ride for both of us.