Tuesday, 5 November 2013

SQL to produce 1..100 as a comma separated string

WITH t AS (SELECT 1 id UNION ALL SELECT id + 1 FROM t WHERE id < 100)
SELECT STUFF((
         SELECT ', ' + CAST(id AS nvarchar(max))
         FROM (SELECT id FROM t) y
         FOR XML PATH(''), TYPE).value('.', 'NVARCHAR(MAX)'), 1, 1, '')

Thursday, 12 September 2013

Problems with static_assert(sizeof(X)) upgrading to VS 2013

While upgrading to VS 2013 I encountered several changes to sizeof classes which stopped me from compiling:

static_assert(sizeof(QESQLSelect) == 188, "You probably have more cloning to do?");

Presumably stl has changed it's implementation so the sizes are different between versions.

The link below shows how to change compile options to show the sizeof to use.
http://blogs.msdn.com/b/vcblog/archive/2007/05/17/diagnosing-hidden-odr-violations-in-visual-c-and-fixing-lnk2022.aspx

Summary:
Add the following option and compile your cpp.  (Remember to remove the option afterwards)
I also used this option in the past to reduce the memory usage of my application.

This produces the following in the output window:

class QESQLSelect size(164):
+---
| +--- (base class QESQLSelectBase)
0 | | {vfptr}
| +---
4 | m_bCheckDistinctColumns
| <alignment member> (size=3)
8 | m_nDBType
12 | m_bDistinct
| <alignment member> (size=3)
16 | m_nTopN
20 | m_bHasImplicitOrdering
21 | m_bCount
| <alignment member> (size=2)
24 | QESQLColumnList m_selectedColumns
40 | ?$CStringT@_WV?$StrTraitMFC_DLL@_WV?$ChTraitsCRT@_W@ATL@@@@ m_strTableOrAliasName
44 | m_pAlternativeSQLSuffix
48 | m_pOptionalSubQuery
52 | ?$auto_vector@PAVQESQLJoinCondition@@ m_joinConditions
68 | ?$auto_vector@PAVQESQLCrossApplyCondition@@ m_crossApplyConditions
84 | ?$auto_vector@PAVQESQLWhereCondition@@ m_whereConditions
100 | ?$auto_vector@PAVQESQLHavingCondition@@ m_havingConditions
116 | m_pGroupBy
120 | DimensionalRollupType m_RollupType
124 | m_pOrderBy
128 | m_pWithSelect
132 | m_pConnectPrior
136 | ?$vector@V?$CStringT@_WV?$StrTraitMFC_DLL@_WV?$ChTraitsCRT@_W@ATL@@@@@ATL@@V?$allocator@V?$CStringT@_WV?StrTraitMFC_DLL@_WV?$ChTraitsCRT@_W@ATL@@@@@ATL@@@std@@ m_vecOracleHints
152 | m_pVecSQLServerHints
156 | ?$CStringT@_WV?$StrTraitMFC_DLL@_WV?$ChTraitsCRT@_W@ATL@@@@ m_strComment
160 | ?$CStringT@_WV?$StrTraitMFC_DLL@_WV?$ChTraitsCRT@_W@ATL@@@@ m_strSimpleTableAlias
+---

 
So I know to change the code to:
static_assert(sizeof(QESQLSelect) == 164, "You probably have more cloning to do?"); 

Note as of VS 2017 the flag seems to have been removed however d1ReportAllClassLayout still works.
Note again - it's a capitalisation problem.. use /d1reportSingleClassLayout

Wednesday, 31 July 2013

Navigating code which uses IoC

Recently I've been navigating around lots of code which uses interfaces to implement Inversion of Control.  The problem is that every time you use F12 to 'Go To Definition' you are taken to the interface, not any of the available implementations.  Most of the time there is only one real implementation, the other(s) are for unit tests.
 
Here are your quick navigation options:

 

Put interface and implementation in the same file

A low-tech option is just to put the main implementation of the interface in the same file as the interface itself.  In reality this is often not an option.

 

Call Hierarchy

You can use the built in 'Call Hierarchy' (Ctrl+k, Ctrl-t) to show implementations of the given function.
 

 

Productivity Power Tools

Productivity Power Tools (see here) allow you to click on the interface name and see 'Implemented By'.  You can then open the list of functions to get to the function you need.

 

Code Rush

There's a plugin for CodeRush here but I couldn't get it to work (even after I remembered to Unblock the downloaded DLL).  Also I found that CodeRush made my IDE grind to a halt (the solution is VERY large)

 

Visual Assist X

Visual Assist doesn't help (but also doesn't hinder any of the other options)

 

ReSharper

Apparently if you have ReSharper then ALT+END will find all implementors.
 
Note these hints are a summary of this post.
Visual Studio user voice suggestion that the functionality is added (here)

Wednesday, 24 April 2013

How to assess user experience

Thu 7th March Tobias Komischke
Aims:
  • Suitability for task (e.g. Amazon = 15 tabs to get to the input box!)
  • Self-descriptive
  • Controllability
  • Conform to user expectations
  • Error tolerance
  • Suitability for individualisation
  • Suitability for learning
Example of proving UI was improved using a radar chart:

Avoid:
  • Non-standard UI controls
  • Inconsistency
  • No perceived affordance
  • No feedback
  • Bad error messages
  • No default values and bad cursor focus
  • Dumping users right in (completely empty OR really full)
  • No workflow support
Other UI considerations
 
Screen clutterAesthetics / human factors - clutter limits the brains ability to process info
Text legibilityCharacter sizes - well known optimum + minimum text sizes for handhelds / monitors / projection walls.
Hard to do for different form factors
Text orientationDon't use Marquee
Rotated right slightly better than left.
Horizontal is best
Colour contrastTools available on the web
Colour blind = 8% of men, 0.43% of women.  Mostly red/green
RAGs: Use both colour / shape and icon
Text alignment in menusLeft align is best (for English)
In forms: align text next to the control (proved using eye tracking)
top align is also ok (benefit is language translation when the text size will vary)
Bad = bottom right or in the input box (info has gone once input + watermarked text is hard to read + presume it's already been input)
Visual structure and flowGrid structure and flow
Improve readability, quicker learning
Standardisation reduces design
Add grid lines to measure conformance
OrientationWhere am IWhere have I come from
What's next
Icon qualityConcreteness = resemblance to real world counterpart
Complexity = Richness of details depicted (want low)
Semantic Distance (want low)
Data visualisationBar charts are best
Volume control worst (humans can't spot area changes)
Visual attentionWhere do people look?
Eye tracking is costly
OR Saliency modelling - use website "Feng GUI" to simulate where people will look first.  1 free heat map per day.
Usability testingReal users
Real tasks
Prototypes + real products
Thinking aloud
Qualitative + quantative data
7/8 people will find 80% of usability problems.  Diminishing returns.
Trend towards remote UI testing - easier + better tooling these days

Design for testing

Thu 7th March Kevin Jones
Our goal is to produce flexible, maintainable, defect free code.
 
Code:
  • Automate the build and deploy process
  • Don't leak UI in to domain layers
  • Don't leak DB access across layers
  • Define new types for each concept even if they are small
    • e.g. Money type rather than using a double.
  • Build facades
    • Amalgamate behaviour in to a new type
    • Hide complexity of underlying objects
  • Single responsibility principle
  • Using concrete types is often a bad idea
    • Code to interfaces
    • Can replace real objects with test objects
    • Can use Dependency Injection
    • Use of 'new' means we are tied to an implementation
Test:
  • Tests should be isolated
  • Unit tests shouldn't use system (file / DB etc.)
  • Test names should be descriptive (use the BDD style)
    • Given_When_Than()
    • e.g. GivenAUserService_WhenIAskForAllUsers_ThenAllUsersAreReturned()
  • Arrange -> Act -> Assert
Dependency Injection
  • Parameter injection
  • Setter injection
  • Constructor injection
  • Use an IoC container (e.g. Unity / Castle / Ninject / AutoFac for MVC)
  • IoC (Inversion of Control) is a principal, Dependency Injection is a consequence of IoC

Tuesday, 2 April 2013

Living happily with the GC

Wed 6th March Richard Blewett

This lecture was one of the more practical ones and mainly focused on using PerfMon to show how the GC works when various bits of code are run.  I'm not going to give a description of how the GC works, instead I'll concentrate on coding changes we can/should be making.

The main goal is to collect as much memory in Generation 0 as possible since Generations 1/2 are around 10 and 100 times slower respectively.

It's worth noting that as of .net 4 you can choose Asynchronous garbage collections for Generation 2.

There is a stage in garbage collection called Finalization which happens in case Dispose wasn't called on an object.  This is run using the Finalizer thread which is slow and its timing is unpredictable.  Simply by adding a destructor to a C# object the number of objects allocated per second drops by about a factor of 15.  If you need to remove references to unmanaged objects (e.g. icon/filestream/sqlconnections) consider using SafeHandle instead.

This example looks strange but helps if a GC happens half way through the Load function:
    
    void LoadData(string s)
    {
        this.data = null;
        this.data = XDocument.Load(s);
    }

Actions:

  • Run load tests with PerfMon garbage collections switched on.
  • Look at our use of destructors
  • Consider using SafeHandle instead of IDisposable
  • Profile to see what the current state of play is w.r.t memory usage / GC time.

Tuesday, 19 March 2013

DevWeek 2013: Overview


You can use this post either as an index of upcoming posts or an incredibly brief summary of the things I found interesting over the week.

For my colleagues, my full notes are in TFS in: "M:\TFS\C++\MooD\Docs\Misc\DevWeek 2013"

There's also a memory stick with all the slides on if anyone is really interested.

Monday

SharePoint 2013

  • Code runs under full trust.
  • 50% faster than predecessor (with 24Gb of RAM)
  • Farm / App / Sandbox solutions.  Should try and use Apps
  • Powershell is worth learning and useful for SharePoint development

Tuesday

Welcome to DevWeek

  • A question of craftsmanship (funny lecture + some links to interesting material)
  • Advances in the cloud computing platform (an advert for Azure)

Design patterns in the real world

  • Various patterns demonstrated using "Game of Life" example
  • Each class can contribute to many design patterns, not just one.

From the user to the unit test - how to start using tests

  • A description of SCRUM
  • Using Gherkin to specify scenarios
  • Arrange -> Act -> Assert
  • Selenium to test web

Light-weight architectures for everyone with the ASPNET WebAPI

  • WebAPI allows HTTP protocols without needing IIS / ASP.NET

Wednesday

Modern JavaScript

  • Encapsulation via Closures
  • Self invoking functions
  • Module pattern / revealing module pattern.
  • Confirmed that Sam's later work was using the right pattern.

Living happily with the GC

  • Using PerfMon to keep track of Gen0/1/2 collections
  • How to reduce frequency of slow collections
  • Why destructors are evil in C#

Evolution of the Entity Framework

  • Can auto migrate databases up/down versions
  • Code first POCO style development (plain old C# object)

Writing code that others can read.  A survival guide (for others)

  • Use Resharper
  • Commenting / consistency / clarity
  • Single responsibility principal
  • Function bigger than a screen is an alert to refactor

Thursday

Design for testing

  • Red, green refactoring
  • Use IoC / Dependency Injection
  • Confirmation that we're kind of doing it right (in some bits of the code base!)

How to asses user experience

  • Checklists of things to look for
  • "Feng GUI" is a good website which simulates eye tracking
  • Overlay a grid on your dialog to see how messy it is.

Emergent Design

  • Justifications for using TDD
  • Do things at the "Last Responsive Moment"
  • Try not to over engineer.  Rather respond to change as it happens.

Applied NoSQL in .net

  • MongoDB allows JSON objects stored against a primary key
  • Means that less JOINs happen
  • Very fast, depending on your data requirements.

Thursday, 14 March 2013

Code snippets in Blogger

Use the following link
http://www.manoli.net/csharpformat/format.aspx
And add custom CSS to your site (as the link advises)

A class which implements 'for each' in unmanaged C++

This is a way to make just about any class implement a C++ 'for each'.  In this example the existing way of iterating round a list is as follows:

CTypedPtrList<CPtrList,int*> myList;
POSITION pos = myList.GetHeadPosition();
while(pos)
{
    int* p = myList.GetNext(pos);
}

You need to implement a begin() and end() function which return an iterator class.
The iterator class must implement:
    void operator++();
    T operator*() const;
    bool operator!=(const iterator& other)

Once you have done this then the compiler will automatically allow you to write your iterator like this:
for each(int* p in myList)
{
}

Note that if your variable is const you may need to implement a version of everything which is const.

See below for a full implementation example built on CTypedPtrList:

template <class T> class PList : public CTypedPtrList<CPtrList> 
{
public:

    // Support for iterators.
    class iterator
    {
    public:
        iterator( PList<T>* p, POSITION pos ) 
            : m_pList(p), m_pos(pos), m_pointer(NULL) 
        {
            if( m_pList )
            {
                m_pos = m_pList->GetHeadPosition();
                if( m_pos )
                    m_pointer = m_pList->GetNext(m_pos);
            }
        }

        void operator++(int) 
        {
            if( m_pos==NULL ) m_pointer = NULL;
            else    m_pointer = m_pList->GetNext(m_pos);
        };

        void operator++()
        {
            this->operator++(0);
        };

        T* operator*() const { return m_pointer; }

        bool operator!=(const iterator& other) const 
        {
            return m_pointer!=other.m_pointer;
        }
    protected:
        PList<T>* m_pList;
        POSITION  m_pos;
        T*        m_pointer;
    };
    //
    iterator begin() { return iterator(this, GetHeadPosition()); }
    iterator end()   { return iterator(NULL,NULL); }
};

A word of caution about the unmanaged C++ 'for each' and 'auto' keywords

Recently I had the following code:

 
std::map<CString, std::vector<CString>> mapIdToChildren;
for(std::map<CString,std::vector<CString>>::iterator it = mapIdToChildren.begin();it!=mapIdToChildren.end();++it)
 std::sort( (*it).second.begin(), (*it).second.end() );
 

And tried replacing it with the 'for each' keyword:
for eachauto it in mapIdToChildren )
 std::sort( it.second.begin(), it.second.end() );
 

But found that the result is unsorted..
What is really happening is that the 'auto' is expanded to the following which means the vector is copied, so the original object remains unsorted:
for each( std::pair<CString,std::vector<CString>> it in mapIdToChildren )
 std::sort( it.second.begin(), it.second.end() );
 

Unfortunately the following code doesn't compile..
for each( std::pair<CString,std::vector<CString>>& it in mapIdToChildren )
 std::sort( it.second.begin(), it.second.end() );
 

Another failure:
for each( std::map<CString,std::vector<CString>>::iterator it in mapIdToChildren )
 std::sort( (*it).second.begin(), (*it).second.end() );
 

In conclusion you should be careful when using the 'auto' keyword in conjunction with 'for each' because you may not be getting what you think.

Tuesday, 12 March 2013

DevWeek 2013: Intro

Last week Steve Cooper and I visited London Village in order to learn more about what's cutting edge in Software Engineering.  Thankfully we both returned unscathed from the big smoke and learned a thing or two.  I shall attempt to jot down these pearls of wisdom in the following posts.  Oh and here are couple of nice pictures of the impressive main hall and lots and lots and lots of techie men.


A note on DevWeek itself:  The location is very nice, we had one lunch break basking in glorious sunshine while we dangled our feet over the edge of a fountain and watched the world go by.  Oh dear, now I've made it sound like a date.

I would advise people choosing lectures to pick very specifically titled ones.  An hour and a half isn't very long so the more general titles to do with design or testing or architecture seem to barely scratch the surface where as the specific ones can get down to the meat of the problem.