Heads up. The Windows API calls LoadIconWithScaleDown() and LoadIconMetric() fail when they try to load a 32×32 icon from an .ico file, when the current DPI is 96; that is, GetSystemMetrics(SM_CXICON) == 32. They work with resources and other image sizes.
Debugging the call LoadIconWithScaleDown(0, L"sample.ico", 32, 32, &hIcon) ends up in the following code path when run with a standard DPI screen:
This just cannot work, because of LoadIcon() only supports loading from resources, and not from .ico files.
This is simply a bug in Windows Vista through Windows 10. A suggested workaround is as follows:
if(!SUCCEEDED(LoadIconWithScaleDown(NULL, L"sample.ico", cx, cy, &hIcon)) {
hIcon = LoadImage(NULL, L"sample.ico", IMAGE_ICON, cx, cy, LR_LOADFROMFILE);
}
// you should do further error checking here
We just ran into a funny problem here, using a “tried and true” technique in SQL Server to concatenate strings. I use the quotes advisedly. This technique is often suggested on blogs and sites such as Stack Overflow, but we found out (by painful experience) that it is not to be relied on.
Update, 9 Mar 2016: Bruce Gordon from Webucator has turned this into a great little 5 minute video. Thanks Bruce! I don’t know anything much about Webucator, but they are doing some good stuff with creating well-attributed videos about blog posts such as this one and apparently they do SQL Server training.
The problem
So, given the following setup:
CREATE TABLE BadConcat (
BadConcatID INT NOT NULL,
Description NVARCHAR(100) NOT NULL,
SortIndex INT NOT NULL
CONSTRAINT PK_BadConcat PRIMARY KEY CLUSTERED (BadConcatID)
)
GO
INSERT BadConcat
SELECT 1, 'First Item', 1 union all
SELECT 2, 'Second Item', 2 union all
SELECT 3, 'Third Item', 3
GO
We need to concatenate those Descriptions. I have avoided fine tuning such as dropping the final comma or handling NULLs for the purpose of this example. This example shows one of the most commonly given answers to the problem:
DECLARE @Summary NVARCHAR(100) = ''
SELECT @Summary = @Summary + ec.Description + ', '
FROM BadConcat ec
ORDER BY ec.SortIndex
PRINT @Summary
And we get the following:
First Item, Second Item, Third Item,
And that works fine. However, if we want to include a WHERE clause, even if that clause still selects everything, then we suddenly get something weird:
SET @Summary = ''
SELECT @Summary = @Summary + ec.Description + ', '
FROM BadConcat ec
WHERE ec.BadConcatID in (1,2,3)
ORDER BY ec.SortIndex
PRINT @Summary
Now we get the following:
Third Item,
What? What has SQL Server done? What’s happened to the first two items?
You’ll probably do what we did, which is to go through and make sure that you are selecting everything properly, which we are, and eventually come to the conclusion that “there must be a bug in SQL Server”.
You may encounter unexpected results when you apply any operators or expressions to the ORDER BY clause of aggregate concatenation queries.
Now, at first glance that does not directly apply. But we can extrapolate from that, as Microsoft developer support have done, in response to a bug report on SQL Server, to learn that:
The variable assignment with SELECT statement is a proprietary syntax (T-SQL only) where the behavior is undefined or plan dependent if multiple rows are produced
Using assignment operations (concatenation in this example) in queries with ORDER BY clause has undefined behavior. This can change from release to release or even within a particular server version due to changes in the query plan. You cannot rely on this behavior even if there are workarounds.
Some alternative solutions are given, also, in that second report:
The ONLY guaranteed mechanism are the following:
1. Use cursor to loop through the rows in specific order and concatenate the values
2. Use for xml query with ORDER BY to generate the concatenated values
3. Use CLR aggregate (this will not work with ORDER BY clause)
And the article “Concatenating Row Values in Transact-SQL” by Anith Sen goes through some of those solutions in detail. Sadly, none of them are as clean or as easy to understand as that original example.
Another example is given on Stack Overflow, which details how to safely use XML PATH to concatenate, without breaking on the XML special characters &, < and >. Applying that example into my problem code given above, we should use the following:
SELECT @Summary = (
SELECT ec.Description + ', '
FROM BadConcat ec
WHERE ec.BadConcatID in (1,2,3)
ORDER BY ec.SortIndex
FOR XML PATH(''), TYPE
).value('.','varchar(max)')
PRINT @Summary
As I am taking on some new challenges at work, I realised I needed to clear the decks a bit with my side projects. So with some sadness, I’ve decided to close down or hand over the following cycling-related projects and activities to other people.
mesmeride.com
Mesmeride was a holiday project I put together to teach myself Ruby on Rails. Mesmeride renders the elevation profile from a Strava ride in a variety of ways, imitating the Giro d’Italia profiles among others. I did want to put some more time into this, having ideas for maps and more flexible profiles, but it isn’t going to happen.
The site will shut down in a couple of weeks — time to get your graphics off or to tell me you want to take over running it (currently costing $9/month for the Heroku instance).
The Hobart 10,000 is an annual ride over 3 days where a bunch of keen cyclists tackle 10,000 metres of climbing on some of Hobart’s iconic hills and mountains. Barry Jones and Mark Breen (@clunkersrule) are already doing a great job of running this event — I’m just handing over the digital reins.
The TassieCup Twitter account reports on the progress of Tasmanian cyclists in the major pro races. I’ve handed control of the account over to the inimitable Daniel Wood (@danielwood1).
The forecast was bleak — 10°C and rain showers. So we abandoned our original plans and decided to go bush instead. Last night, Hannah prepared an itinerary, including Mystery Creek Cave, Thermal Springs, Hastings Cave and Surprise Destination (at my suggestion). This morning, we executed that carefully shaped itinerary, nearly perfectly. Apart from wet clothes all day. That was a bit of a dampener.
On the way down, we stopped in Geeveston to buy some food. And happened to park right outside a huge lolly shop. What a huge lolly shop is doing in a tiny little place like Geeveston, I don’t know. Philosophical considerations were not top of my daughters’ minds. They happily accepted the existence of this incongruous edifice, and came away with — I’m sorry, Joey! — lollies.
Bellies charged, we made our way to our first objective: Almost Caving. I knew we were regrettably not adequately prepared for Real Caving, so instead we were aiming for Almost Caving. That is, looking into the cave, shining torches around the entrance and wondering what was around the next corner.
Almost was still an adventure. The track was muddy. Very muddy. Wind had brought many trees down. Climbing over wet branches and landing in big mud puddles was a great introduction to the day. Instantly soggy pants. The rain kept coming down, soaking from above, while the puddles soaked from below.
We found a midden of abandoned boots and bottles. Presumably collected and deposited there over time. Creepy, according to the girls.
Then we arrived at an obstacle.
Initially, I did not think we would be able to cross: the river was flowing fast and I was not keen on getting even more soaked than we already were. But then I found some exposed rocks and a fallen tree. So crossed we did! Apologies for the quality of the pictures and video. They were taken on SoggyiPhoneCam.
Shortly thereafter, we arrived triumphantly at a quarry. The rain decided to come down just a bit more heavily. That didn’t stop the girls from checking out what lay beyond the rock piles.
But on to the cave. A couple minutes more trekking through mud and puddles, and we spotted it. The river was not (yet) high. So we were able to approach the entrance of the cave, and look into what lay beyond. It was also dry, which was a nice change.
Lolly snakes all round, and back to the car. With the crossing of the raging torrent, now a little higher. But not more than any adventurous (nearly) 7 or 10 year old could handle.
Back at the dry and cosy car, there was unanimous agreement that we would head to the Thermal Springs for some additional warmth and recovery. With car heater on full bore, your merry correspondent and his soggy herd proceeded thence forthwith. And a fun time was had by all, steaming in front of open log fires, swimming, in the rain, in the thermal pools (much warmer than the rain), but cut short all too soon by the need for sustenance, and tourist cave booking.
Perhaps Newdegate Cave was just too tame, after the morning expedition. Or maybe we were too cold and tired. But the review of the cave, as expressed by Hannah, and not contested by the rest of us, was “it wasn’t as good as I expected”. Still, we “did” the tour, saw a solitary glowworm, many stalactites and -gmites, shawls and curtains and straws, holes and flowstone and more, and, then more than a little cold, made it back to the car.
Amazingly, just enough time for the final Surprise Destination. This Surprise Destination was augmented by a multi-dollar budget for each of the girls. A Gemstone Shop! The initial joy rapidly gave way to serious perturbation. This was difficult. So many pretty rocks. So much choice. Yet, finally, both girls came away satisfied, thanks to a friendly shopowner, who was willing to mix and match presorted bags to her appreciative and choosy customers’ satisfaction. Amethysts, moonstone, mookaite and more. And, from there we made our tired, soggy, smelly way home, stopping only once to buy drinks.
I expected the girls to collapse on arrival home, but they bounced in the door, greeted baby Peter, and exuberantly leapt into the bath. And while I was off preparing Peter for bed, they set the table for a fancy meal, including candles, wine glasses (no wine, more’s the pity) and neatly arranged place settings. Maybe lollies are good for them, after all?
Snow to 800 metres. 55km/h winds. Possible hail. That was the forecast that greeted us at 4:30am as we met at Tim’s house, all psyched up for our 200km Freedom Ride over the central plateau back to Hobart. As we drove up north in the bus, 11 testosterone fuelled blokes discussed whether or not we would be so soft that we would fall back on the “easy” bad weather backup route. Or whether we would be hard men and tough out the weather.
As each rider spoke up and agreed that they wanted to do the central plateau route, and then also said that it would probably be a bad idea, I recalled the Launceston – New Norfolk race a few years back, that took the same route, when only 7 pro riders finished in similarly atrocious weather.
Amazingly, we had almost unanimous agreement to go the soft option. Still 200km, still over 2000m climbing, but via the east coast, with its generally milder weather. I was relieved: the plateau route was sounding more and more like a really dangerous choice, with freezing cold, wet and gusty descents and general misery!
We were riding for the charity Live Free Tassie, which works to help young people break free from addictions. It’s not too late to donate — please do!
Preparing to leave Campbell Town. Weather looks great so far.
At just after 7am, we set out from Campbell Town towards the east coast, immediately hitting the largest climb of the whole ride, which we took gently while we warmed up. The strong winds were behind us at this point, and we were somewhat sheltered on most of the climb. Over the top of the range it was cold, but it was over surprisingly quickly and with little pain.
A tight well-organised bunch, rolling smoothly
The descent into Swansea was great fun and we rolled into the small seaside town well ahead of schedule. With no sense of urgency, and warm and pleasant weather, the brief toilet stop took somewhat longer than originally intended!
Swansea Stop
We rode the whole route in a tight, well organised bunch, with smooth roll-throughs and good communication through the group. No one got left behind and I really felt like we were all working well together. I’ve never been on a ride before where the bunch stayed organised for 50km, let alone 200km! Well done Tim (our organiser) for his success in motivating the fast boys to support the bunch!
Once we got to Triabunna, the traffic got a little heavier, and we had a couple of impatient drivers attempt to overtake on blind corners and similarly silly places. As we went through Orford, we had our one and only puncture of the day, and the local police stopped by to ask us to ride single file through the narrow gorge out of Orford to reduce the likelihood of more silly moves by drivers. The puncture meant that this became our lunch stop, and again, the beneficial winds meant we were still ahead of schedule. So again, we were in no rush…
Lunch stop at Orford, 125km in, everyone looks happy!
Then we turned our noses towards Hobart. And hit the cross-headwinds. 50km/h with lots of gusts thrown in for good measure. Our average speed plummeted, and we were riding at less than 20km/h most of the time now. A few of the riders in the group were starting to feel their legs, and we encouraged them to spend as little time on the front as they possible. As we rode single file through the gorge, a phalanx of probably 200-odd motorbikes roared past the other way, followed by a long line of classic cars. There was to be no overtaking anyway…
Mechanical — rear wheel change meant a bit of waiting for the group. Just before the rain!
We struggled against the wind, as the rain and a little bit of hail started to assault us. But we survived. The worst part, for me, was the steep descents in driving wind and rain. They were not much fun. At this point, Simon experienced a serious cramp that put him in the bus. But only for 5 minutes! He got out again, like a madman, in time for the sketchy descent. Not sure I could have done that…
The rain let up again after the hills and we just worked our way slowly back into Hobart against the winds. We finally and triumphantly arrived, the last group to finish for the day, all our early time gains destroyed by the ferocious winds and unexpected stops through to the finish.
Personally, I enjoyed the whole day, bar the sketchy descents and the handful of crazy drivers. I’ve never been as well prepared for a long ride as I was for this one, despite already having done 280km in the 5 days preceding the ride. Kudos must go out to Trev, Mark D and Mark P as the oldest in the bunch (by some margin, too), and to Tim who did a brilliant job of organising the ride. The whole bunch was great to ride with, and I’d do the ride again with the same guys without hesitation. Thanks for an awesome epic ride, Brendon, Dan, Simon, Ben, Tim, Michael, Ant, Trev, Mark, Mark and Mark! Updated: And massive thank you to Henry and Henry for driving and supporting on the ride. Sorry I forgot to mention you initially!
We saw a jack ant. We walked up a steep track. We saw some poisonous berries. We saw the fence again! We saw the signal station. We saw an old hook and a great view. We might have a sorbet if they have some here! The End
What does that dotted yellow straight line on the map mean? It’s just a fire trail, right?
But that is not what it means. Map designers like to lie about their dotted yellow lines. What is actually means is:
Marc will be…
…walking…
…his…
…fancy…
…mountain…
…bike.
That last hill has an average gradient of over 50%. It wasn’t so much walking as scrabbling to haul the bike up that.
The rest of the ride didn’t get much better. Very overgrown, but no where near as steep, only 13% average, rough — too rough for Marc’s mediocre abilities — and lots of fallen branches for variety. Don’t think I’ll try commuting that route again.
Recently Hobart Airport ‘upgraded’ their parking payment system with some fancy new machines. This new, modern, streamlined payment system allows the driver to pay before returning to their vehicle, or pay with credit card at the exit… Well, sorta.
I’ve been wanting to get pictures of these machines for a while but I’ve always been at the airport at night or in the rain. Finally today I managed to get a picture of the fantastic machines!
Ok, so you’ve decided to pay before you return to your vehicle, here’s the payment machine.
Wow. Instructions all over it. Let’s see, wait a moment, there’s a list of steps there.
Okey dokey, maybe it’s not so bad after all, where’s number 1 on the machine…?
Hey, there’s a long queue of grumpy travellers behind you, hurry up. There’s number 2, there’s number 3 … and number 3 again … and again … and step 4’s over there, but where’s step 1?!?
Oh. I guess they decided to do that one differently. Now where’s step 2 again? Maybe it’d be easier to do this graphically:
Maybe not.
Eventually you will get there but don’t forget to press the receipt button before the ticket pops back out again!
So which button is it? I think it is the middle button but I couldn’t give you any guarantees!
Step 5 curiously shows you walking to one of the four exits but I’m sure you’ll figure out that you are actually supposed to drive out of the car park…
Next time
Next time, you will probably decide that that machine is ridiculous and instead you will pay with a credit card at the exit gate. Let’s see how you go.
Seems easy enough. Put the ticket in, now where does your credit card go?
Wrong.
It goes here.
I learned that one by painful experience. Swiping my credit card 3 times in the marked slot before I gave up and pressed the Assistance button…