<?xml version="1.0"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Tommy’s stuff: Blog</title>
    <description>Tommy Carlier’s blog</description>
    <link>https://www.tcx.be</link>
    <language>en-US</language>
    <copyright>© 2004–2026 Tommy Carlier</copyright>
    <atom:link href="https://www.tcx.be/feed.xml" rel="self" type="application/rss+xml" />
    
    <item>
      <title>Remove all children of an element in JavaScript</title>
      <description>&lt;p&gt;The &lt;a href=&quot;https://developer.mozilla.org/en-US/docs/Web/API/Document_Object_Model&quot;&gt;&lt;abbr title=&quot;Document Object Model&quot;&gt;DOM&lt;/abbr&gt; &lt;abbr title=&quot;Application Programming Interface&quot;&gt;API&lt;/abbr&gt;&lt;/a&gt; does not provide a function to remove all children of an element. A straightforward way to do this is to remove each child element: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;function removeAllChildren(e) {
  while(e.firstChild) {
    e.removeChild(e.firstChild);
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This works, but there is a faster alternative: select all children using the &lt;a href=&quot;https://developer.mozilla.org/en-US/docs/Web/API/Range&quot;&gt;DOM Range API&lt;/a&gt; and delete the contents of the range. This is &lt;a href=&quot;https://caniuse.com/#feat=dom-range&quot;&gt;supported in all modern browsers&lt;/a&gt; (in Internet Explorer since version 9). 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;function removeAllChildren(e) {
  var r = document.createRange();
  r.selectNodeContents(e);
  r.deleteContents();
  r.detach();
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;If you need &lt;a href=&quot;https://en.wikipedia.org/wiki/Backward_compatibility&quot; title=&quot;Backward compatibility&quot;&gt;backward compatibility&lt;/a&gt; with older browsers, you can check whether the range API is supported and use the old method otherwise: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;var removeAllChildren = document.createRange
  ? function(e) {
    var r = document.createRange();
    r.selectNodeContents(e);
    r.deleteContents();
    r.detach();
  } : function(e) {
    while(e.firstChild) {
      e.removeChild(e.firstChild);
    }
  };&lt;/code&gt;&lt;/pre&gt;&lt;/p&gt;</description>
      <pubDate>Mon, 22 Jan 2018 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2018/remove-children-js/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2018/remove-children-js/</guid>
    </item>
    
    <item>
      <title>Shuffle an array in JavaScript</title>
      <description>&lt;p&gt;If you have an array, and you want to randomly shuffle its elements, you can use the &lt;a href=&quot;https://en.wikipedia.org/wiki/Fisher%E2%80%93Yates_shuffle&quot;&gt;Fisher–Yates shuffle&lt;/a&gt; algorithm. In JavaScript, it looks like this:  

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;function shuffle(xs) {
  var i = xs.length, x, rnd;
  while(i) {
    rnd = Math.floor(Math.random() * i);
    i -= 1;
    x = xs[i];
    xs[i] = xs[rnd];
    xs[rnd] = x;
  }
}&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Thu, 18 Jan 2018 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2018/shuffle-array-js/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2018/shuffle-array-js/</guid>
    </item>
    
    <item>
      <title>Update SysInternals Suite via PowerShell</title>
      <description>&lt;p&gt;&lt;a href=&quot;https://technet.microsoft.com/en-us/sysinternals/bb842062.aspx&quot;&gt;SysInternals Suite&lt;/a&gt; is a collection of troubleshooting tools for Windows, developed by Microsoft. You can download the tools as a ZIP-file, that you can extract into a directory, and run the individual applications without having to install them.
&lt;p&gt;When I find out there’s a new version of the SysInternals Suite, I have to click the link to the website, click the download link, save the ZIP-file, open the ZIP-file and select the destination folder to extract to. After having done this for the umpteenth time, I wrote the following PowerShell-script to automate the process: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;$url = &amp;apos;https://download.sysinternals.com/files/SysinternalsSuite.zip&amp;apos;
$zipPath = &amp;apos;d:\dev\tools\SysinternalsSuite.zip&amp;apos;
$tempFolder = &amp;apos;d:\dev\tools\temp-sys-internals&amp;apos;
$folder = &amp;apos;d:\dev\tools\sys-internals&amp;apos;

Write-Host &amp;apos;Downloading&amp;apos; $url &amp;apos;to&amp;apos; $zipPath
$web = New-Object System.Net.WebClient
$web.DownloadFile($url, $zipPath)

Write-Host &amp;apos;Extracting&amp;apos; $zipPath &amp;apos;to&amp;apos; $tempFolder
Add-Type -assembly &amp;apos;System.IO.Compression.FileSystem&amp;apos;
[System.IO.Compression.ZipFile]::ExtractToDirectory($zipPath, $tempFolder)

Write-Host &amp;apos;Copying files from&amp;apos; $tempFolder &amp;apos;to&amp;apos; $folder
Copy-Item (Join-Path $tempFolder &amp;apos;*&amp;apos;) $folder

Write-Host &amp;apos;Removing temporary files&amp;apos;
Remove-Item $zipPath
Remove-Item $tempFolder -Recurse&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;The above script installs the SysInternals Suite in the directory &lt;code&gt;d:\dev\tools\sys-internals&lt;/code&gt;. Please change the variables for your specific installation, before running the script. </description>
      <pubDate>Mon, 05 Sep 2016 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2016/powershell-update-sysinternals/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2016/powershell-update-sysinternals/</guid>
    </item>
    
    <item>
      <title>Synchronize KeePass via Amazon S3</title>
      <description>&lt;p&gt;I use &lt;a href=&quot;http://keepass.info/&quot;&gt;KeePass&lt;/a&gt; to manage my passwords, but I need to access these passwords from my PC at home, and my PC at work. To keep these databases synchronized, I put a copy on Amazon’s cloud storage service &lt;a href=&quot;https://aws.amazon.com/s3/&quot;&gt;S3&lt;/a&gt;. Until recently, I synchronized manually: whenever I add a new password entry on 1 PC, I upload it to S3 (using &lt;a href=&quot;https://cyberduck.io/&quot;&gt;Cyberduck&lt;/a&gt;), and when I’m on the other PC I download it from S3 (unless I forget).

&lt;p&gt;This week, I discovered there are plugins for KeePass that enable you to open/save/synchronize your passwords with cloud storage systems like Dropbox, Google Drive, or Amazon S3. For my system, I use the &lt;a href=&quot;https://bitbucket.org/devinmartin/keecloud/wiki/Home&quot;&gt;KeeCloud&lt;/a&gt; plugin. Because I don’t want to give the KeeCloud plugin full access to my Amazon S3 account, I figured out how to create an AWS user with the minimal permissions necessary for accessing only my password database. Here’s a description of the full process. This example uses the bucket name &lt;i&gt;passwords&lt;/i&gt; and the password database name &lt;i&gt;passwords.kdbx&lt;/i&gt;.

&lt;h2&gt;Configure Amazon S3&lt;/h2&gt;
&lt;p&gt;Skip this step if you already have a bucket where you want to store your password database.
&lt;ol&gt;
&lt;li&gt;Log in to the &lt;a href=&quot;https://console.aws.amazon.com/&quot;&gt;AWS Management Console&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;Navigate to &lt;a href=&quot;https://console.aws.amazon.com/s3/&quot;&gt;S3&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;Create a bucket for your password database (e.g. &lt;i&gt;passwords&lt;/i&gt;)&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;Create AWS user&lt;/h2&gt;
&lt;p&gt;To have maximum security, it’s important to create a dedicated AWS user that has limited access to only your password database (and nothing else on AWS).&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Navigate to &lt;a href=&quot;https://console.aws.amazon.com/iam/&quot;&gt;Identity and Access Management&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;Navigate to the &lt;i&gt;Users&lt;/i&gt;-screen&lt;/li&gt;
&lt;li&gt;Create a new user, give it a name&lt;/li&gt;
&lt;li&gt;Copy the &lt;i&gt;Security Credentials&lt;/i&gt; of the user (&lt;i&gt;Access Key ID&lt;/i&gt; and &lt;i&gt;Secret Access Key&lt;/i&gt;): you will need these later to sign in&lt;/li&gt;
&lt;li&gt;Navigate to the created user, to the &lt;i&gt;Permissions&lt;/i&gt;-tab&lt;/li&gt;
&lt;li&gt;Open the &lt;i&gt;Inline Policies&lt;/i&gt;-view, and press &lt;i&gt;Create User Policy&lt;/i&gt;&lt;/li&gt;
&lt;li&gt;Select &lt;i&gt;Custom Policy&lt;/i&gt;, and press &lt;i&gt;Select&lt;/i&gt;&lt;/li&gt;
&lt;li&gt;Give the policy a name, and enter the following &lt;i&gt;Policy Document&lt;/i&gt;: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;{
  &amp;quot;Version&amp;quot;: &amp;quot;2012-10-17&amp;quot;,
  &amp;quot;Statement&amp;quot;: [
    {
      &amp;quot;Effect&amp;quot;: &amp;quot;Allow&amp;quot;,
      &amp;quot;Action&amp;quot;: [
        &amp;quot;s3:DeleteObject&amp;quot;,
        &amp;quot;s3:GetObject&amp;quot;,
        &amp;quot;s3:PutObject&amp;quot;
      ],
      &amp;quot;Resource&amp;quot;: [
        &amp;quot;arn:aws:s3:::passwords/passwords.kdbx&amp;quot;,
        &amp;quot;arn:aws:s3:::passwords/passwords.kdbx.tmp&amp;quot;
      ]
    }
  ]
}&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt; 
&lt;/ol&gt;

&lt;h2&gt;Install and configure KeeCloud&lt;/h2&gt;
&lt;ol&gt;
&lt;li&gt;Download the latest version of KeeCloud from the &lt;a href=&quot;https://bitbucket.org/devinmartin/keecloud/downloads&quot;&gt;Downloads&lt;/a&gt;-page (download the PLGX-file)&lt;/li&gt;
&lt;li&gt;Put the PLGX-file in the KeePass installation directory:&lt;ul&gt;
  &lt;li&gt;32-bit Windows: &lt;i&gt;C:\Program Files\KeePass Password Safe 2&lt;/i&gt;&lt;/li&gt;
  &lt;li&gt;64-bit Windows: &lt;i&gt;C:\Program Files (x86)\KeePass Password Safe 2&lt;/i&gt;&lt;/li&gt;
&lt;/ul&gt;&lt;/li&gt;
&lt;li&gt;Start (or restart) KeePass&lt;/li&gt;
&lt;li&gt;Open the database you want to synchronize&lt;/li&gt;
&lt;li&gt;Navigate to the menu &lt;i&gt;File &amp;gt; Synchronize &amp;gt; Synchronize with URL…&lt;/i&gt;&lt;/li&gt;
&lt;li&gt;Enter the following information:&lt;table&gt;
  &lt;tr&gt;&lt;th&gt;URL&lt;td&gt;&lt;code&gt;s3://passwords/passwords.kdbx&lt;/code&gt;&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;User name&lt;td&gt;The &lt;i&gt;Access Key ID&lt;/i&gt; of your AWS user&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;Password&lt;td&gt;The &lt;i&gt;Secret Access Key&lt;/i&gt; of your AWS user&lt;/tr&gt;
&lt;/table&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Instead of synchronizing a local file with S3, you can also just open the database directly from S3, using the menu &lt;i&gt;File &amp;gt; Open &amp;gt; Open URL…&lt;/i&gt;
</description>
      <pubDate>Fri, 13 May 2016 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2016/sync-keepass-s3/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2016/sync-keepass-s3/</guid>
    </item>
    
    <item>
      <title>Spelling out numbers in words (French)</title>
      <description>&lt;p&gt;Here’s an algorithm (in pseudo-code) for spelling out numbers in French words (e.g. convert &lt;code&gt;123&lt;/code&gt; to &lt;code&gt;&quot;cent vingt-trois&quot;&lt;/code&gt;): 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;-- spell out an integer number in words (French)
function numberToWordsFrench(number)
  var result, iteration, iterationText, hundreds, hundredsText

  if number = 0
    return &amp;quot;zero&amp;quot;
  end
  
  result ← &amp;quot;&amp;quot;
  iteration ← 1
  
  -- iterate per 3 digits (starting with last)
  while number &amp;gt; 0
    hundreds ← number modulo 1000 -- e.g. 23456 → 456
    number ← floor(number / 1000) -- e.g. 23456 → 23
    
    if hundreds &amp;gt; 0
      -- 3 digits to text
      hundredsText ← getHundredsText(hundreds)
      if iteration &amp;gt; 1
        -- mille, million, …
        iterationText ← getIterationText(iteration)
        hundredsText ← hundredsText + iterationText
        if hundredsText = &amp;quot;un mille &amp;quot;
          hundredsText ← &amp;quot; mille &amp;quot;
        end
      end
      
      result ← hundredsText + result
    end
    
    iteration ← iteration + 1
  end
  
  return trim(result)
end

function getHundredsText(number)
  var result, hundreds, tens
  
  result ← &amp;quot;&amp;quot;
  
  hundreds ← floor(number / 100) -- e.g. 456 → 4
  if hundreds &amp;gt; 0
    number ← number modulo 100 -- e.g. 456 → 56
    if hundreds &amp;gt; 1
      -- deux cents, trois cents, …
      result ← result + getLessThanTwentyText(hundreds) + &amp;quot; cents&amp;quot;
    else
      result ← result + &amp;quot;cent&amp;quot;
    end
  end
  
  if number &amp;gt; 0
    if hundreds &amp;gt; 0
      -- space after &amp;quot;cent(s)&amp;quot;
      result ← result + &amp;quot; &amp;quot;
    end
    
    if number &amp;lt; 20
      -- &amp;lt; 20 ⇒ look up
      result ← result + getLessThanTwentyText(number)
    else
      tens ← floor(number / 10) -- e.g. 42 → 4
      number ← number modulo 10 -- e.g. 42 → 2
      
      case tens
        when 7
          -- soixante dix, soixante onze, …
          result ← result + &amp;quot;soixante&amp;quot;
          number ← number + 10
        when 8
          if number &amp;gt; 0
            result ← result + &amp;quot;quatre-vingt&amp;quot;
          else
            result ← result + &amp;quot;quatre-vingts&amp;quot;
          end
        when 9
          -- quatre-vingt dix, quatre-vingt onze, …
          result ← result + &amp;quot;quatre-vingt&amp;quot;
          number ← number + 10
        otherwise
          -- vingt, trente, quarante, …
          result ← result + getTensText(tens)
      end
      
      if number &amp;gt; 0
        if number = 1 and tens ≠ 8
          result ← result + &amp;quot; et un&amp;quot;
        else
          result ← result + &amp;quot;-&amp;quot; + getLessThanTwentyText(number)
        end
      end
    end
  end
  
  return result
end

function getLessThanTwentyText(number)
  case number
    when 1 return &amp;quot;un&amp;quot;
    when 2 return &amp;quot;deux&amp;quot;
    when 3 return &amp;quot;trois&amp;quot;
    when 4 return &amp;quot;quatre&amp;quot;
    when 5 return &amp;quot;cinq&amp;quot;
    when 6 return &amp;quot;six&amp;quot;
    when 7 return &amp;quot;sept&amp;quot;
    when 8 return &amp;quot;huit&amp;quot;
    when 9 return &amp;quot;neuf&amp;quot;
    when 10 return &amp;quot;dix&amp;quot;
    when 11 return &amp;quot;onze&amp;quot;
    when 12 return &amp;quot;douze&amp;quot;
    when 13 return &amp;quot;treize&amp;quot;
    when 14 return &amp;quot;quatorze&amp;quot;
    when 15 return &amp;quot;quinze&amp;quot;
    when 16 return &amp;quot;seize&amp;quot;
    when 17 return &amp;quot;dix-sept&amp;quot;
    when 18 return &amp;quot;dix-huit&amp;quot;
    when 19 return &amp;quot;dix-neuf&amp;quot;
    otherwise error
  end
end

function getTensText(tens)
  case tens
    when 2 return &amp;quot;vingt&amp;quot;
    when 3 return &amp;quot;trente&amp;quot;
    when 4 return &amp;quot;quarante&amp;quot;
    when 5 return &amp;quot;cinquante&amp;quot;
    when 6 return &amp;quot;soixante&amp;quot;
    otherwise error
  end
end

function getIterationText(iteration)
  case iteration
    when 1 return &amp;quot;&amp;quot;
    when 2 return &amp;quot; mille &amp;quot;
    when 3 return &amp;quot; million &amp;quot;
    when 4 return &amp;quot; milliard &amp;quot;
    when 5 return &amp;quot; billion &amp;quot;
    when 6 return &amp;quot; billiard &amp;quot;
    when 7 return &amp;quot; trillion &amp;quot;
    when 8 return &amp;quot; trilliard &amp;quot;
    otherwise return &amp;quot; ??? &amp;quot;
  end
end&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Tue, 15 Sep 2015 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2015/numbers-to-words-fr/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2015/numbers-to-words-fr/</guid>
    </item>
    
    <item>
      <title>Spelling out numbers in words (Dutch)</title>
      <description>&lt;p&gt;Here’s an algorithm (in pseudo-code) for spelling out numbers in Dutch words (e.g. convert &lt;code&gt;123&lt;/code&gt; to &lt;code&gt;&quot;honderddrieëntwintig&quot;&lt;/code&gt;): 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;-- spell out an integer number in words (Dutch)
function numberToWordsDutch(number)
  var result, iteration, iterationText, hundreds, hundredsText

  if number = 0
    return &amp;quot;nul&amp;quot;
  end
  
  result ← &amp;quot;&amp;quot;
  iteration ← 1
  
  -- iterate per 3 digits (starting with last)
  while number &amp;gt; 0
    hundreds ← number modulo 1000 -- e.g. 23456 → 456
    number ← floor(number / 1000) -- e.g. 23456 → 23
    
    if hundreds &amp;gt; 0
      -- 3 digits to text
      hundredsText ← getHundredsText(hundreds)
      if iteration &amp;gt; 1
        -- duizend, miljoen, …
        iterationText ← getIterationText(iteration)
        hundredsText ← hundredsText + iterationText
        if hundredsText = &amp;quot;eenduizend &amp;quot;
          hundredsText ← &amp;quot;duizend &amp;quot;
        end
      end
      
      result ← hundredsText + result
    end
    
    iteration ← iteration + 1
  end
  
  return trim(result)
end

function getHundredsText(number)
  var result, hundreds, tens
  
  result ← &amp;quot;&amp;quot;
  
  hundreds ← floor(number / 100) -- e.g. 456 → 4
  if hundreds &amp;gt; 0
    number ← number modulo 100 -- e.g. 456 → 56
    if hundreds &amp;gt; 1
      result ← result + getLessThanTwentyText(hundreds)
    end
    result ← result + &amp;quot;honderd&amp;quot;
  end
  
  if number &amp;gt; 0
    if hundreds &amp;gt; 0 and number ≤ 12
      result ← result + &amp;quot;en&amp;quot;
    end
    
    if number &amp;lt; 20
      -- &amp;lt; 20 ⇒ look up
      result ← result + getLessThanTwentyText(number)
    else
      tens ← floor(number / 10) -- e.g. 42 → 4
      number ← number modulo 10 -- e.g. 42 → 2
      
      if number &amp;gt; 0
        -- een, twee, drie, …
        result ← result + getLessThanTwentyText(number)
        if number = 2 or number = 3
          result ← result + &amp;quot;ën&amp;quot;
        else
          result ← result + &amp;quot;en&amp;quot;
        end
      end
      
      -- dertig, veertig, …
      result ← result + getTensText(tens)
    end
  end
  
  return result
end

function getLessThanTwentyText(number)
  case number
    when 1 return &amp;quot;een&amp;quot;
    when 2 return &amp;quot;twee&amp;quot;
    when 3 return &amp;quot;drie&amp;quot;
    when 4 return &amp;quot;vier&amp;quot;
    when 5 return &amp;quot;vijf&amp;quot;
    when 6 return &amp;quot;zes&amp;quot;
    when 7 return &amp;quot;zeven&amp;quot;
    when 8 return &amp;quot;acht&amp;quot;
    when 9 return &amp;quot;negen&amp;quot;
    when 10 return &amp;quot;tien&amp;quot;
    when 11 return &amp;quot;elf&amp;quot;
    when 12 return &amp;quot;twaalf&amp;quot;
    when 13 return &amp;quot;dertien&amp;quot;
    when 14 return &amp;quot;veertien&amp;quot;
    when 15 return &amp;quot;vijftien&amp;quot;
    when 16 return &amp;quot;zestien&amp;quot;
    when 17 return &amp;quot;zeventien&amp;quot;
    when 18 return &amp;quot;achttien&amp;quot;
    when 19 return &amp;quot;negentien&amp;quot;
    otherwise error
  end
end

function getTensText(tens)
  case tens
    when 2 return &amp;quot;twintig&amp;quot;
    when 3 return &amp;quot;dertig&amp;quot;
    when 4 return &amp;quot;veertig&amp;quot;
    when 5 return &amp;quot;vijftig&amp;quot;
    when 6 return &amp;quot;zestig&amp;quot;
    when 7 return &amp;quot;zeventig&amp;quot;
    when 8 return &amp;quot;tachtig&amp;quot;
    when 9 return &amp;quot;negentig&amp;quot;
    otherwise error
  end
end

function getIterationText(iteration)
  case iteration
    when 1 return &amp;quot;&amp;quot;
    when 2 return &amp;quot;duizend &amp;quot;
    when 3 return &amp;quot; miljoen &amp;quot;
    when 4 return &amp;quot; miljard &amp;quot;
    when 5 return &amp;quot; biljoen &amp;quot;
    when 6 return &amp;quot; biljard &amp;quot;
    when 7 return &amp;quot; triljoen &amp;quot;
    when 8 return &amp;quot; triljard &amp;quot;
    otherwise return &amp;quot; ??? &amp;quot;
  end
end&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Mon, 14 Sep 2015 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2015/numbers-to-words-nl/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2015/numbers-to-words-nl/</guid>
    </item>
    
    <item>
      <title>Spelling out numbers in words (English)</title>
      <description>&lt;p&gt;Here’s an algorithm (in pseudo-code) for spelling out numbers in English words (e.g. convert &lt;code&gt;123&lt;/code&gt; to &lt;code&gt;&quot;one hundred twenty-three&quot;&lt;/code&gt;): 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;-- spell out an integer number in words (English)
function numberToWordsEnglish(number)
  var result, iteration, iterationText, hundreds, hundredsText

  if number = 0
    return &amp;quot;zero&amp;quot;
  end
  
  result ← &amp;quot;&amp;quot;
  iteration ← 1
  
  -- iterate per 3 digits (starting with last)
  while number &amp;gt; 0
    hundreds ← number modulo 1000 -- e.g. 23456 → 456
    number ← floor(number / 1000) -- e.g. 23456 → 23
    
    if hundreds &amp;gt; 0
      -- 3 digits to text
      hundredsText ← getHundredsText(hundreds)
      if iteration &amp;gt; 1
        -- thousand, million, …
        iterationText ← getIterationText(iteration)
        hundredsText ← hundredsText + iterationText
      end
      
      result ← hundredsText + result
    end
    
    iteration ← iteration + 1
  end
  
  return trim(result)
end

function getHundredsText(number)
  var result, hundreds, tens
  
  result ← &amp;quot;&amp;quot;
  
  hundreds ← floor(number / 100) -- e.g. 456 → 4
  if hundreds &amp;gt; 0
    number ← number modulo 100 -- e.g. 456 → 56
    result ← result + getLessThanTwentyText(hundreds) + &amp;quot; hundred&amp;quot;
  end
  
  if number &amp;gt; 0
    if hundreds &amp;gt; 0
      -- space after &amp;quot;hundred&amp;quot;
      result ← result + &amp;quot; &amp;quot;
    end
    
    if number &amp;lt; 20
      -- &amp;lt; 20 ⇒ look up
      result ← result + getLessThanTwentyText(number)
    else
      tens ← floor(number / 10) -- e.g. 42 → 4
      number ← number modulo 10 -- e.g. 42 → 2
      
      -- thirty, forty, …
      result ← result + getTensText(tens)
      
      if number &amp;gt; 0
        -- one, two, three, …
        result ← result + &amp;quot;-&amp;quot; + getLessThanTwentyText(number)
      end
    end
  end
  
  return result
end

function getLessThanTwentyText(number)
  case number
    when 1 return &amp;quot;one&amp;quot;
    when 2 return &amp;quot;two&amp;quot;
    when 3 return &amp;quot;three&amp;quot;
    when 4 return &amp;quot;four&amp;quot;
    when 5 return &amp;quot;five&amp;quot;
    when 6 return &amp;quot;six&amp;quot;
    when 7 return &amp;quot;seven&amp;quot;
    when 8 return &amp;quot;eight&amp;quot;
    when 9 return &amp;quot;nine&amp;quot;
    when 10 return &amp;quot;ten&amp;quot;
    when 11 return &amp;quot;eleven&amp;quot;
    when 12 return &amp;quot;twelve&amp;quot;
    when 13 return &amp;quot;thirteen&amp;quot;
    when 14 return &amp;quot;fourteen&amp;quot;
    when 15 return &amp;quot;fifteen&amp;quot;
    when 16 return &amp;quot;sixteen&amp;quot;
    when 17 return &amp;quot;seventeen&amp;quot;
    when 18 return &amp;quot;eighteen&amp;quot;
    when 19 return &amp;quot;nineteen&amp;quot;
    otherwise error
  end
end

function getTensText(tens)
  case tens
    when 2 return &amp;quot;twenty&amp;quot;
    when 3 return &amp;quot;thirty&amp;quot;
    when 4 return &amp;quot;forty&amp;quot;
    when 5 return &amp;quot;fifty&amp;quot;
    when 6 return &amp;quot;sixty&amp;quot;
    when 7 return &amp;quot;seventy&amp;quot;
    when 8 return &amp;quot;eighty&amp;quot;
    when 9 return &amp;quot;ninety&amp;quot;
    otherwise error
  end
end

function getIterationText(iteration)
  case iteration
    when 1 return &amp;quot;&amp;quot;
    when 2 return &amp;quot; thousand &amp;quot;
    when 3 return &amp;quot; million &amp;quot;
    when 4 return &amp;quot; billion &amp;quot;
    when 5 return &amp;quot; trillion &amp;quot;
    when 6 return &amp;quot; quadrillion &amp;quot;
    when 7 return &amp;quot; quintillion &amp;quot;
    when 8 return &amp;quot; sextillion &amp;quot;
    otherwise return &amp;quot; ??? &amp;quot;
  end
end&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Fri, 11 Sep 2015 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2015/numbers-to-words-en/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2015/numbers-to-words-en/</guid>
    </item>
    
    <item>
      <title>Synchronize Google Calendar &amp; Contacts with iOS 6</title>
      <description>&lt;p&gt;I still use a 4th generation iPod Touch. Although I’m stuck with iOS 6, it still works fine for doing the things I use it for: e-mail, contacts, calendar, alarm clock, reading &lt;abbr&gt;RSS&lt;/abbr&gt;-feeds (&lt;a href=&quot;http://reederapp.com/ios/&quot;&gt;Reeder&lt;/a&gt;, reading from &lt;a href=&quot;https://feedly.com/&quot;&gt;Feedly&lt;/a&gt;), Twitter (using &lt;a href=&quot;http://tapbots.com/tweetbot/&quot;&gt;Tweetbot&lt;/a&gt;), and &lt;a href=&quot;https://getpocket.com/&quot;&gt;Pocket&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;For e-mail, I use the GMail application. For contacts and calendar, I use Apple’s native Contacts and Calendars apps, synchronized with my Google account via the Exchange protocol. Until recently, this worked fine. I had offline access to my contacts and calendar events, and it synchronized when I was online.

&lt;p&gt;About a month ago, synchronization stopped working. I don’t get any error message, it just doesn’t synchronize anymore. Today, I solved the problem by removing the Exchange account, and performing the following steps.&lt;/p&gt;

&lt;h2&gt;Synchronized calendars: add a Google account&lt;/h2&gt;
&lt;ol&gt;
&lt;li&gt;Go to “Settings › Mail, Contacts, Calendar › Add Account › GMail”&lt;/li&gt;
&lt;li&gt;Enter the following information:&lt;table&gt;
  &lt;tr&gt;&lt;th&gt;Name&lt;td&gt;your full name&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;Email&lt;td&gt;your e-mail address&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;Password&lt;td&gt;your Google account password&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;Description&lt;td&gt;a description of the account&lt;/tr&gt;
&lt;/table&gt;&lt;/li&gt;
&lt;li&gt;Select which services you want to synchronize: E-mail, Calendars, Notes (I only synchronize calendars)&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;Synchronized contacts: add a &lt;abbr&gt;&lt;a href=&quot;https://en.wikipedia.org/wiki/CardDAV&quot;&gt;CardDAV&lt;/a&gt;&lt;/abbr&gt; account&lt;/h2&gt;
&lt;ol&gt;
&lt;li&gt;Go to “Settings › Mail, Contacts, Calendar › Add Account › Other › Add CardDAV Account”&lt;/li&gt;
&lt;li&gt;Enter the following information:&lt;table&gt;
  &lt;tr&gt;&lt;th&gt;Server&lt;td&gt;google.com&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;User Name&lt;td&gt;your e-mail address&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;Password&lt;td&gt;your Google account password&lt;/tr&gt;
  &lt;tr&gt;&lt;th&gt;Description&lt;td&gt;a description of the account&lt;/tr&gt;
&lt;/table&gt;&lt;/li&gt;
&lt;/ol&gt;
</description>
      <pubDate>Mon, 24 Aug 2015 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2015/google-ios6/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2015/google-ios6/</guid>
    </item>
    
    <item>
      <title>Messaging protocols</title>
      <description>&lt;p&gt;While investigating messaging protocols for communication between devices and systems, I collected a list of articles, documents, presentations and specifications. Because this might be useful for other developers, I decided to share it here. The protocols I investigated are &lt;abbr title=&quot;Advanced Message Queuing Protocol&quot;&gt;AMQP&lt;/abbr&gt;, &lt;abbr title=&quot;Message Queue Telemetry Transport&quot;&gt;MQTT&lt;/abbr&gt;, &lt;abbr title=&quot;Constrained Application Protocol&quot;&gt;CoAP&lt;/abbr&gt;, and &lt;abbr title=&quot;Streaming Text Oriented Messaging Protocol&quot;&gt;STOMP&lt;/abbr&gt;.
  
&lt;p&gt;&lt;small&gt;&lt;b&gt;Update&lt;/b&gt;: &lt;a href=&quot;https://twitter.com/dobermai/status/578591904360726528&quot;&gt;I received a link&lt;/a&gt; to a series of articles about the essentials of &lt;abbr&gt;MQTT&lt;/abbr&gt;, which I added to the list.&lt;/small&gt;

&lt;h2&gt;&lt;abbr&gt;AMQP&lt;/abbr&gt;&lt;/h2&gt;
&lt;ul class=print-href&gt;
&lt;li&gt;&lt;a href=&quot;https://www.amqp.org/&quot;&gt;Official website&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;https://en.wikipedia.org/wiki/Advanced_Message_Queuing_Protocol&quot; title=&quot;Advanced Message Queuing Protocol&quot;&gt;Wikipedia article&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://docs.oasis-open.org/amqp/core/v1.0/amqp-core-complete-v1.0.pdf&quot;&gt;Specification&lt;/a&gt;
&lt;/ul&gt;

&lt;h2&gt;&lt;abbr&gt;MQTT&lt;/abbr&gt;&lt;/h2&gt;
&lt;ul class=print-href&gt;
&lt;li&gt;&lt;a href=&quot;http://mqtt.org/&quot;&gt;Official website&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;https://en.wikipedia.org/wiki/MQTT&quot; title=&quot;MQTT&quot;&gt;Wikipedia article&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://docs.oasis-open.org/mqtt/mqtt/v3.1.1/mqtt-v3.1.1.pdf&quot;&gt;Specification&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;https://github.com/mqtt/mqtt.github.io/wiki&quot;&gt;Community Wiki&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://www.slideshare.net/andypiper/lightweight-messaging-for-a-connected-planet&quot;&gt;Lightweight Messaging for a connected planet&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://www.redbooks.ibm.com/redbooks/pdfs/sg248054.pdf&quot;&gt;Building Smarter Planet Solutions with &lt;abbr&gt;MQTT&lt;/abbr&gt; and &lt;abbr&gt;IBM&lt;/abbr&gt; WebSphere MQ Telemetry&lt;/a&gt;
&lt;li&gt;&lt;abbr&gt;MQTT&lt;/abbr&gt; Essentials:
  &lt;ul&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-1-introducing-mqtt/&quot;&gt;Introducing &lt;abbr&gt;MQTT&lt;/abbr&gt;&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part2-publish-subscribe/&quot;&gt;Publish &amp;amp; Subscribe&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-3-client-broker-connection-establishment/&quot;&gt;Client, Broker and Connection Establishment&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-4-mqtt-publish-subscribe-unsubscribe/&quot;&gt;&lt;abbr&gt;MQTT&lt;/abbr&gt; Publish, Subscribe &amp;amp; Unsubscribe&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-5-mqtt-topics-best-practices/&quot;&gt;&lt;abbr&gt;MQTT&lt;/abbr&gt; Topics &amp;amp; Best Practices&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-6-mqtt-quality-of-service-levels/&quot;&gt;Quality of Service 0, 1 &amp;amp; 2&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-7-persistent-session-queuing-messages/&quot;&gt;Persistent Session and Queuing Messages&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-8-retained-messages/&quot;&gt;Retained Messages&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-9-last-will-and-testament/&quot;&gt;Last Will and Testament&lt;/a&gt;
    &lt;li&gt;&lt;a href=&quot;http://www.hivemq.com/mqtt-essentials-part-10-alive-client-take-over/&quot;&gt;Keep Alive and Client Take-Over&lt;/a&gt;
  &lt;/ul&gt;
&lt;/ul&gt;

&lt;h2&gt;&lt;abbr&gt;CoAP&lt;/abbr&gt;&lt;/h2&gt;
&lt;ul class=print-href&gt;
&lt;li&gt;&lt;a href=&quot;https://en.wikipedia.org/wiki/Constrained_Application_Protocol&quot; title=&quot;Constrained Application Protocol&quot;&gt;Wikipedia article&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;https://tools.ietf.org/html/rfc7252&quot;&gt;Specification&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://www.coapsharp.com/basics-of-coap/&quot;&gt;Basics of &lt;abbr&gt;CoAP&lt;/abbr&gt;&lt;/a&gt;
&lt;/ul&gt;

&lt;h2&gt;&lt;abbr&gt;STOMP&lt;/abbr&gt;&lt;/h2&gt;
&lt;ul class=print-href&gt;
&lt;li&gt;&lt;a href=&quot;https://stomp.github.io/&quot;&gt;Official website&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;https://en.wikipedia.org/wiki/Streaming_Text_Oriented_Messaging_Protocol&quot; title=&quot;Streaming Text Oriented Messaging Protocol&quot;&gt;Wikipedia article&lt;/a&gt;
&lt;/ul&gt;

&lt;h2&gt;Comparisons&lt;/h2&gt;
&lt;ul class=print-href&gt;
&lt;li&gt;&lt;a href=&quot;http://eclipse.org/community/eclipse_newsletter/2014/february/article2.php&quot;&gt;&lt;abbr&gt;MQTT&lt;/abbr&gt; &amp;amp; &lt;abbr&gt;CoAP&lt;/abbr&gt;&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://blogs.vmware.com/vfabric/2013/02/choosing-your-messaging-protocol-amqp-mqtt-or-stomp.html&quot;&gt;Choosing your Messaging Protocol: &lt;abbr&gt;AMQP&lt;/abbr&gt;, &lt;abbr&gt;MQTT&lt;/abbr&gt;, or &lt;abbr&gt;STOMP&lt;/abbr&gt;&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://www.slideshare.net/paolopat/mqtt-iot-protocols-comparison&quot;&gt;&lt;abbr&gt;MQTT&lt;/abbr&gt; &amp;amp; &lt;abbr title=&quot;Internet Of Things&quot;&gt;IoT&lt;/abbr&gt; protocols comparison
(&lt;abbr&gt;MQTT&lt;/abbr&gt; versus &lt;abbr&gt;HTTP&lt;/abbr&gt;, &lt;abbr&gt;CoAP&lt;/abbr&gt;, &lt;abbr&gt;AMQP&lt;/abbr&gt;)&lt;/a&gt;
&lt;li&gt;&lt;a href=&quot;http://java.dzone.com/sites/all/files/StormMQ_WhitePaper_-_A_Comparison_of_AMQP_and_MQTT.pdf&quot;&gt;A comparison of &lt;abbr&gt;AMQP&lt;/abbr&gt; and &lt;abbr&gt;MQTT&lt;/abbr&gt;&lt;/a&gt;
&lt;/ul&gt;</description>
      <pubDate>Thu, 19 Mar 2015 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2015/messaging-protocols/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2015/messaging-protocols/</guid>
    </item>
    
    <item>
      <title>ASCII, Unicode and UTF‑8</title>
      <description>&lt;p&gt;In the following video, Tom Scott gives an overview of the history of &lt;abbr&gt;ASCII&lt;/abbr&gt;, Unicode and &lt;abbr&gt;UTF-8&lt;/abbr&gt;, providing a great explanation how it works.&lt;br&gt;&lt;a href=&quot;https://youtu.be/MijmeoH9LT4&quot;&gt;youtu.be/MijmeoH9LT4&lt;/a&gt; (&lt;time datetime=&quot;9m37s&quot;&gt;9:37&lt;/time&gt;)&lt;p class=&quot;wrap-16-9-25 no-print&quot;&gt;&lt;iframe src=&quot;https://www.youtube.com/embed/MijmeoH9LT4?rel=0&amp;amp;theme=light&quot; width=&quot;870&quot; height=&quot;523&quot; allowfullscreen&gt;&lt;/iframe&gt;</description>
      <pubDate>Mon, 30 Sep 2013 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2013/ascii-unicode-utf8/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2013/ascii-unicode-utf8/</guid>
    </item>
    
    <item>
      <title>Properly using and implementing the IDisposable pattern</title>
      <description>&lt;p&gt;&lt;a href=&quot;http://msdn.microsoft.com/en-us/library/system.idisposable.aspx&quot;&gt;&lt;var&gt;IDisposable&lt;/var&gt;&lt;/a&gt; is a pattern in .NET that is used to implement deterministic cleanup of unmanaged resources. .NET has a garbage collector, but that is only used to manage memory, not resources like &lt;abbr&gt;I/O&lt;/abbr&gt; (file handles, sockets, …). While in C++ destructors are called deterministically when an object goes out of scope, &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/0s71x931.aspx&quot;&gt;finalizers&lt;/a&gt; in C# get called by the garbage collector, but we can’t determine when that will happen (indeterministic deallocation). &lt;i&gt;Don’t depend on the garbage collector for unmanaged resources!&lt;/i&gt;

&lt;h2&gt;Properly disposing resources&lt;/h2&gt;
&lt;p&gt;The &lt;var&gt;IDisposable&lt;/var&gt;-interface has a single method &lt;code&gt;void &lt;b&gt;Dispose&lt;/b&gt;()&lt;/code&gt;. This method is used to clean up the disposable object and release the unmanaged resources it holds. To make sure that you always call it, even if an exception occurs in the code between creating the object and calling its &lt;var&gt;Dispose&lt;/var&gt;-method, you should use the &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/zwc8s4fz.aspx&quot;&gt;&lt;var&gt;try-finally&lt;/var&gt;&lt;/a&gt;-construct, like this: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;var x = new X(); // X is a class that implements IDisposable
try
{
  // do something with x
}
finally
{
  x.Dispose();
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Because this pattern is so common, C# has the &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/yh598w02.aspx&quot;&gt;&lt;var&gt;using&lt;/var&gt;&lt;/a&gt;-construct that does this more succinctly: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using (var x = new X())
{
  // do something with x
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;The advantage of this construct is that you can easily nest it without writing a lot of code: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using (var stream = new FileStream(fileName, FileMode.Create, FileAccess.Write))
{
  using (var writer = new StreamWriter(stream, Encoding.UTF8))
  {
    foreach (string line in lines)
    {
      writer.WriteLine(line);
    }
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Or with less indentation and curly braces: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using (var stream = new FileStream(fileName, FileMode.Create, FileAccess.Write))
using (var writer = new StreamWriter(stream, Encoding.UTF8))
{
  foreach (string line in lines)
  {
    writer.WriteLine(line);
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This is (more or less) equivalent to the following code: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;var stream = new FileStream(fileName, FileMode.Create, FileAccess.Write);
try
{
  var writer = new StreamWriter(stream, Encoding.UTF8);
  try
  {
    foreach (string line in lines)
    {
      writer.WriteLine(line);
    }
  }
  finally
  {
    writer.Dispose();
  }
}
finally
{
  stream.Dispose();
}&lt;/code&gt;&lt;/pre&gt;

&lt;h2&gt;Properly implementing &lt;var&gt;IDisposable&lt;/var&gt; in your own classes&lt;/h2&gt;
&lt;p&gt;Here’s the minimal proper implementation of &lt;var&gt;IDisposable&lt;/var&gt; for a regular class that can be inherited (i.e. is not &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/88c54tsw.aspx&quot;&gt;sealed&lt;/a&gt;): 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;public class MyDisposableType : IDisposable
{
  ~MyDisposableType()
  {
    // the finalizer also has to release unmanaged resources,
    // in case the developer forgot to dispose the object.
    Dispose(false);
  }
 
  public void Dispose()
  {
    Dispose(true);
 
    // this tells the garbage collector not to execute the finalizer
    GC.SuppressFinalize(this);
  }
 
  protected virtual void Dispose(bool disposing)
  {
    if (disposing)
    {
      // clean up managed resources:
      // dispose child objects that implement IDisposable
    }
 
    // clean up unmanaged resources
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;In the classes that derive from such a disposable class, you don’t have to implement the entire pattern again: you can just override the &lt;code&gt;Dispose(bool disposing)&lt;/code&gt;-method to add extra clean-up code. Just make sure you call the base-method (after the added code, in a &lt;var&gt;finally&lt;/var&gt;-block): 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;public class MyDerivedDisposableType : MyDisposableType
{
  protected override void Dispose(bool disposing)
  {
    try
    {
      if (disposing)
      {
        // clean up managed resources:
        // dispose child objects that implement IDisposable
      }
 
      // clean up unmanaged resources
    }
    finally
    {
      // always call the base-method!
      base.Dispose(disposing);
    }
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;If your class is sealed (so there can be no derived classes), you cannot have virtual methods. To properly implement the &lt;var&gt;IDisposable&lt;/var&gt;-pattern, you could make the &lt;code&gt;Dispose(bool disposing)&lt;/code&gt;-method private and not virtual: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;public sealed class MySealedDisposableType : IDisposable
{
  ~MySealedDisposableType()
  {
    // the finalizer also has to release unmanaged resources,
    // in case the developer forgot to dispose the object.
    Dispose(false);
  }
 
  public void Dispose()
  {
    Dispose(true);
 
    // this tells the garbage collector not to execute the finalizer
    GC.SuppressFinalize(this);
  }
 
  private void Dispose(bool disposing)
  {
    if (disposing)
    {
      // clean up managed resources:
      // dispose child objects that implement IDisposable
    }
 
    // clean up unmanaged resources
  }
}&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Fri, 16 Nov 2012 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2012/idisposable/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2012/idisposable/</guid>
    </item>
    
    <item>
      <title>GitHub &amp; Gist</title>
      <description>&lt;p&gt;I decided to create a &lt;a href=&quot;https://github.com/&quot;&gt;GitHub&lt;/a&gt;-account, specifically to manage the code snippets I occasionally publish on this blog via &lt;a href=&quot;https://gist.github.com/&quot;&gt;Gist&lt;/a&gt;. Now you get nice syntax-coloring, and it’s easier for me to manage and update the snippets.

&lt;p&gt;My GitHub account-name is &lt;a href=&quot;https://github.com/tommy-carlier&quot;&gt;&lt;var&gt;tommy-carlier&lt;/var&gt;&lt;/a&gt;, and you can find my code snippets &lt;a href=&quot;https://gist.github.com/tommy-carlier&quot;&gt;here&lt;/a&gt;.</description>
      <pubDate>Thu, 22 Mar 2012 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2012/github-gist/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2012/github-gist/</guid>
    </item>
    
    <item>
      <title>Removing diacritics from a string</title>
      <description>&lt;p&gt;Recently I had to write a function that removes all &lt;a href=&quot;https://en.wikipedia.org/wiki/Diacritic&quot; title=&quot;Diacritic&quot;&gt;diacritics&lt;/a&gt; from a string (e.g.: turning &lt;code&gt;José&lt;/code&gt; into &lt;code&gt;Jose&lt;/code&gt;). Searching the web, I quickly found the blog post &lt;a href=&quot;http://blogs.msdn.com/b/michkap/archive/2007/05/14/2629747.aspx&quot;&gt;“Stripping is an interesting job”&lt;/a&gt; by Michael Kaplan. His code is simple and good, but I saw some opportunities for optimizations (obvious stuff): because we know the approximate length (actually the maximum length) of the resulting string, we could give the &lt;var&gt;StringBuilder&lt;/var&gt;-instance an initial capacity equal to the length of the original string. In some simple cases I actually like using a &lt;var&gt;char&lt;/var&gt;-array instead of a &lt;var&gt;StringBuilder&lt;/var&gt;, because it has even less overhead. Another obvious optimization is to check whether the original string is not empty. Here’s my optimized version: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using System;
using System.Globalization;
using System.Text;
 
namespace TC
{
  // Removes diacritics from a string
  //
  // Original version by Michael Kaplan: 
  // → http://blogs.msdn.com/b/michkap/archive/2007/05/14/2629747.aspx
  //
  // Optimized version by Tommy Carlier:
  // → http://www.tcx.be/blog/2011/remove-diacritics/
  public static class DiacriticsRemover
  {
    public static string RemoveDiacritics(this string text)
    {
      if (text == null) throw new ArgumentNullException(&amp;quot;text&amp;quot;);
 
      if (text.Length &amp;gt; 0)
      {
        char[] chars = new char[text.Length];
        int charIndex = 0;
 
        text = text.Normalize(NormalizationForm.FormD);
        for (int i = 0; i &amp;lt; text.Length; i++)
        {
          char c = text[i];
          if (CharUnicodeInfo.GetUnicodeCategory(c) != UnicodeCategory.NonSpacingMark)
          {
            chars[charIndex++] = c;
          }
        }
 
        return new string(chars, 0, charIndex).Normalize(NormalizationForm.FormC);
      }
 
      return text;
    }
  }
}&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Thu, 17 Nov 2011 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2011/remove-diacritics/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2011/remove-diacritics/</guid>
    </item>
    
    <item>
      <title>Google Analytics in ASP.NET</title>
      <description>&lt;p&gt;Here’s a little C# function I occasionally use to insert a &lt;a href=&quot;http://www.google.com/analytics/&quot;&gt;Google Analytics&lt;/a&gt;-snippet in an &lt;abbr&gt;ASP.NET&lt;/abbr&gt; website. It takes a Google Analytics-ID as an argument, which you can leave blank in debug-mode (to not render the snippet). It uses the recently introduced asynchronous loading method (which doesn’t block the rendering of your website). It’s not literally the same snippet you can find on the Google Analytics site, but it does the same thing (only with a slightly smaller dynamically built JavaScript-snippet). 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using System;
using System.Web;
 
namespace TC
{
  public static class GoogleAnalytics
  {
    public static string RenderScript(string googleAnalyticsID)
    {
      return string.IsNullOrEmpty(googleAnalyticsID)
        ? &amp;quot;&amp;quot;
        : &amp;quot;&amp;lt;script&amp;gt;&amp;quot;
        + &amp;quot;var _gaq=_gaq||[];&amp;quot;
        + &amp;quot;_gaq.push([&amp;apos;_setAccount&amp;apos;,&amp;apos;&amp;quot; + googleAnalyticsID + &amp;quot;&amp;apos;]);&amp;quot;
        + &amp;quot;_gaq.push([&amp;apos;_trackPageview&amp;apos;]);&amp;quot;
        + &amp;quot;(function(d,s){&amp;quot;
        + &amp;quot;var e=d.getElementsByTagName(s)[0],&amp;quot;
        + &amp;quot;x=d.createElement(s);&amp;quot;
        + &amp;quot;x.async=1;&amp;quot;
        + &amp;quot;x.src=&amp;apos;&amp;quot;
        + (HttpContext.Current.Request.IsSecureConnection
            ? &amp;quot;https://ssl&amp;quot; : &amp;quot;http://www&amp;quot;)
        + &amp;quot;.google-analytics.com/ga.js&amp;apos;;&amp;quot;
        + &amp;quot;e.parentNode.insertBefore(x,e)}(document,&amp;apos;script&amp;apos;))&amp;lt;/script&amp;gt;&amp;quot;;
    }
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;I usually keep the Google Analytics-ID in my application settings (&lt;var&gt;web.config&lt;/var&gt;), which allows me to use a different one for different deployments (or an empty one for debugging). So I have a second function (in a &lt;var&gt;SiteUtilities&lt;/var&gt;-class) that doesn’t take an argument, but takes the Google Analytics-ID from the settings: 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;public static string RenderGoogleAnalyticsScript()
{
  return TC.GoogleAnalytics.RenderScript(Settings.Default.GoogleAnalyticsID);
}&lt;/code&gt;&lt;/pre&gt;
  
&lt;p&gt;In my master-page, I then use the following snippet to insert it into the body of the page (note that you have to use the fully qualified type name, including namespace): 

&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;&amp;lt;%= MyNamespace.SiteUtilities.RenderGoogleAnalyticsScript() %&amp;gt;&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Thu, 04 Mar 2010 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2010/aspnet-ga/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2010/aspnet-ga/</guid>
    </item>
    
    <item>
      <title>if-read-do-while-read – part 2</title>
      <description>&lt;p&gt;I just received a comment on &lt;a href=&quot;/blog/2009/if-read-do-while-read/&quot;&gt;my previous post about the &lt;i&gt;if-read-do-while-read&lt;/i&gt; construction&lt;/a&gt;. Tanton suggests that I could create a method that encapsulates this construction, using delegates for the &lt;i&gt;before&lt;/i&gt;, &lt;i&gt;during&lt;/i&gt; and &lt;i&gt;after&lt;/i&gt; steps. Here’s a quick version of an extension method on &lt;var&gt;IDataReader&lt;/var&gt; that does this:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;public static class DataReaderExtensions
{
  public static void ReadAll(
    this IDataReader reader,
    Action before,
    Action&amp;lt;IDataRecord&amp;gt; during,
    Action after)
  {
    if (reader == null) throw new ArgumentNullException(&amp;quot;reader&amp;quot;);

    if (reader.Read())
    {
      if (before != null)
      {
        before();
      }
      
      do
      {
        if (during != null)
        {
          during(reader);
        }
      }
      while (reader.Read());
      
      if (after != null)
      {
        after();
      }
    }
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;And here’s a rewrite of the HTML-example, using this extension method:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;StringBuilder html = new StringBuilder();
using (IDataReader reader = command.ExecuteReader())
{
  reader.ReadAll(
    () =&amp;gt; html.Append(&amp;quot;&amp;lt;ul&amp;gt;&amp;quot;),
    record =&amp;gt; html.AppendFormat(&amp;quot;&amp;lt;li&amp;gt;{0}&amp;quot;, record.GetValue(0)),
    () =&amp;gt; html.Append(&amp;quot;&amp;lt;/ul&amp;gt;&amp;quot;));
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;It’s surely shorter, but I’m not entirely convinced it’s cleaner.</description>
      <pubDate>Fri, 08 Jan 2010 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2010/if-read-do-while-read-2/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2010/if-read-do-while-read-2/</guid>
    </item>
    
    <item>
      <title>if-read-do-while-read</title>
      <description>&lt;p&gt;Here’s a construction I occasionally need when reading items from a &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/system.data.idatareader.aspx&quot;&gt;&lt;var&gt;IDataReader&lt;/var&gt;&lt;/a&gt;: to execute some code before and after reading through the &lt;var&gt;IDataReader&lt;/var&gt;, but only if there are rows in the &lt;var&gt;IDataReader&lt;/var&gt;.

&lt;p&gt;One option is to use a boolean variable that determines whether the collection has items, like this:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using (IDataReader reader = command.ExecuteReader())
{
  bool hasRows = false;
  while (reader.Read())
  {
    if (!hasRows)
    {
      hasRows = true;
      Before();
    }

    During();
  }

  if (hasRows)
  {
    After();
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;But the following construction (which I call the &lt;i&gt;if-read-do-while-read&lt;/i&gt; construction) does not need the boolean variable and is cleaner:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using (IDataReader reader = command.ExecuteReader())
{
  if (reader.Read())
  {
    Before();

    do
    {
      During();
    }
    while (reader.Read());

    After();
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Here’s a practical example: creating &lt;abbr title=&quot;Hypertext Markup Language&quot;&gt;HTML&lt;/abbr&gt;-code with a UL-list for the data, but only if there are items:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;StringBuilder html = new StringBuilder();
using (IDataReader reader = command.ExecuteReader())
{
  if (reader.Read())
  {
    html.Append(&amp;quot;&amp;lt;ul&amp;gt;&amp;quot;);

    do
    {
      html.AppendFormat(
        &amp;quot;&amp;lt;li&amp;gt;{0}&amp;quot;,
        reader.GetValue(0));
    }
    while (reader.Read());

    html.Append(&amp;quot;&amp;lt;/ul&amp;gt;&amp;quot;);
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;You could use the same technique on an &lt;var&gt;IEnumerable&amp;lt;T&amp;gt;&lt;/var&gt;, but you wouldn’t be able to use &lt;var&gt;foreach&lt;/var&gt; anymore:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using (var enumerator = collection.GetEnumerator())
{
  if (enumerator.MoveNext())
  {
    Before();

    do
    {
      var item = enumerator.Current;
      During();
    }
    while (enumerator.MoveNext());

    After();
  }
}&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Tue, 29 Dec 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/if-read-do-while-read/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/if-read-do-while-read/</guid>
    </item>
    
    <item>
      <title>NDepend</title>
      <description>&lt;p&gt;A while ago, I received an e-mail from &lt;a href=&quot;http://codebetter.com/patricksmacchia/&quot;&gt;Patrick Smacchia&lt;/a&gt;, offering me a license for &lt;a href=&quot;http://www.ndepend.com/&quot;&gt;NDepend&lt;/a&gt; and asking me whether I could try it out, give some feedback and if I liked it, maybe I could blog about my experience with NDepend. Because I was already subscribed to the &lt;abbr&gt;RSS&lt;/abbr&gt;-feed of Patrick’s blog, I knew about NDepend and how it could help developers write better code. I like trying out stuff like this, but somehow I hadn’t found time to install and properly test it. I was already using Visual Studio’s Code Analysis (FxCop) and &lt;a href=&quot;https://stylecop.codeplex.com/&quot;&gt;StyleCop&lt;/a&gt; to analyze my code and improve its quality, so I never had the right incentives to use additional tools. But it would be rude to just say no to Patrick, so I decided to give it a try.

&lt;p&gt;After installing it (which just means downloading: NDepend is a portable application that doesn’t really have to be “installed”), I started Visual NDepend (the &lt;abbr title=&quot;Graphical User Interface&quot;&gt;GUI&lt;/abbr&gt; version of NDepend) and was greeted with a start page that looks like the Visual Studio start page. I decided not to just jump in and try stuff, but to first watch some of the &lt;a href=&quot;http://www.ndepend.com/docs/getting-started-with-ndepend&quot;&gt;screen casts and tutorials on the NDepend website&lt;/a&gt;. And I’m glad I did. After trying to analyze some of my projects, I discovered that NDepend produces a lot of data, reports and graphs that only make sense after you have learnt what it all means. This is a tool that you have to learn how to use and how to interpret its results. The user interface is very flexible, but also a bit overwhelming. But because I don’t really have an idea how I would design a &lt;abbr title=&quot;User Interface&quot;&gt;UI&lt;/abbr&gt; for an application like this, I can’t really criticize it.

&lt;p&gt;Comparing it to FxCop and StyleCop is not really fair. There is some overlapping functionality between the 3 tools, but NDepend offers a lot more. First of all, FxCop and StyleCop just analyze your code according to fixed rules and the result is a bunch of errors and warnings. NDepend can also be used like this, but the rules are not fixed and are defined in &lt;abbr&gt;CQL&lt;/abbr&gt;, a query language that looks and feels like &lt;abbr title=&quot;Structured Query Language&quot;&gt;SQL&lt;/abbr&gt;, but allows you to query code constructs. The advantage of this approach is that you can write ad-hoc queries to gain insight in your code (or someone else’s assemblies). Here’s an example of a &lt;abbr&gt;CQL&lt;/abbr&gt; query:

&lt;pre&gt;&lt;code&gt;WARN IF Count &amp;gt; 0 IN SELECT TOP 10 TYPES WHERE NbMethods &amp;gt; 20 ORDER BY NbMethods DESC&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This query will generate a warning if your code has classes (and structs) with more than 20 methods. All the built-in rules are written as &lt;abbr&gt;CQL&lt;/abbr&gt; queries, which you can just modify (or you could just create additional rules).

&lt;p&gt;Another area of analysis that NDepend offers that FxCop and StyleCop do not have is the visual views of your projects. There’s a metrics &lt;a href=&quot;https://en.wikipedia.org/wiki/Treemapping&quot; title=&quot;Treemapping&quot;&gt;treemap&lt;/a&gt; that shows the proportions of different metrics of your project (methods, types, fields, …) and there are 2 ways to show dependencies: a &lt;a href=&quot;https://en.wikipedia.org/wiki/Dependency_graph&quot; title=&quot;Dependency graph&quot;&gt;dependency graph&lt;/a&gt; and a &lt;a href=&quot;https://en.wikipedia.org/wiki/Design_structure_matrix&quot; title=&quot;Design structure matrix&quot;&gt;dependency matrix&lt;/a&gt;. While the dependency graph looks familiar and very graphical, it fails when there are too many elements and dependencies. This is not a failure of NDepend, but just a limitation of dependency graphs in general. Dependency matrices on the other hand are great to understand dependencies, even when there are a lot of elements, but they are less intuitive and you have to learn how to use them and interpret what you see.

&lt;p&gt;My conclusion is that NDepend is a great tool to analyze your code and improve its quality, but it takes getting used to. You have to learn how to use it and how to interpret the results you get. I feel like I have just seen the tip of the iceberg. NDepend also contains a console-application, and can be automated and integrated in your build process (MSBuild, NAnt, …). It has add-ins for Visual Studio and Reflector, and can be used to compare different versions of a code base (for example: to see if compatibility is broken).

&lt;p&gt;If you want to try it yourself, I suggest you first &lt;a href=&quot;http://www.ndepend.com/docs/getting-started-with-ndepend&quot;&gt;watch the screen casts&lt;/a&gt;, &lt;a href=&quot;http://www.ndepend.com/download&quot;&gt;download NDepend&lt;/a&gt; and start analyzing some of your projects. Another suggestion I have is to start reading &lt;a href=&quot;http://codebetter.com/patricksmacchia/&quot;&gt;Patrick Smacchia’s blog&lt;/a&gt;, because he has written about some cool things you can do with NDepend. He also explains how he has analyzed some existing .NET applications (&lt;a href=&quot;http://codebetter.com/patricksmacchia/2008/10/20/controlling-the-usage-of-libraries/&quot;&gt;Paint.NET&lt;/a&gt;, &lt;a href=&quot;http://codebetter.com/patricksmacchia/2009/07/21/nhibernate-2-1-changes-overview/&quot;&gt;NHibernate&lt;/a&gt;, &lt;a href=&quot;http://codebetter.com/patricksmacchia/2009/04/26/the-big-picture-of-the-sharpdevelop-code-base/&quot;&gt;SharpDevelop&lt;/a&gt;, …) and even how he uses NDepend to find what has changed between &lt;a href=&quot;http://codebetter.com/patricksmacchia/2009/10/21/interesting-findings-in-the-diff-between-net-fx-v4-beta1-and-beta2/&quot;&gt;different versions of the .NET Framework BCL&lt;/a&gt;.</description>
      <pubDate>Thu, 12 Nov 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/ndepend/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/ndepend/</guid>
    </item>
    
    <item>
      <title>Awesome videos on Channel 9 this week</title>
      <description>&lt;p&gt;Channel 9 has always produced nice videos with interviews, or weekly shows (This Week on Channel 9, Ping), but this week they have exceeded themselves in quality and awesomeness. I especially liked the following videos:

&lt;ul&gt;
&lt;li&gt;Reactive Framework (&lt;abbr&gt;Rx&lt;/abbr&gt;) Under the Hood: &lt;a href=&quot;http://channel9.msdn.com/shows/Going+Deep/E2E-Erik-Meijer-and-Wes-Dyer-Reactive-Framework-Rx-Under-the-Hood-1-of-2/&quot;&gt;part 1&lt;/a&gt;, &lt;a href=&quot;http://channel9.msdn.com/shows/Going+Deep/E2E-Erik-Meijer-and-Wes-Dyer-Reactive-Framework-Rx-Under-the-Hood-2-of-2/&quot;&gt;part 2&lt;/a&gt;
&lt;li&gt;The Visual Studio Documentary: &lt;a href=&quot;http://channel9.msdn.com/series/visualstudiodocumentary/the-visual-studio-documentary-part-one&quot;&gt;part 1&lt;/a&gt;, &lt;a href=&quot;http://channel9.msdn.com/series/visualstudiodocumentary/the-visual-studio-documentary-part-two&quot;&gt;part 2&lt;/a&gt;
&lt;li&gt;&lt;abbr&gt;C9&lt;/abbr&gt; Lectures: Dr. Erik Meijer – Functional Programming Fundamentals, &lt;a href=&quot;http://channel9.msdn.com/Series/C9-Lectures-Erik-Meijer-Functional-Programming-Fundamentals/Lecture-Series-Erik-Meijer-Functional-Programming-Fundamentals-Chapter-1&quot;&gt;Chapter 1 of 13&lt;/a&gt;
&lt;/ul&gt;

&lt;p&gt;Besides being a fan of &lt;a href=&quot;http://channel9.msdn.com/shows/This+Week+On+Channel+9/&quot;&gt;This Week on Channel 9&lt;/a&gt; and &lt;a href=&quot;http://channel9.msdn.com/shows/PingShow/&quot;&gt;Ping&lt;/a&gt;, I also loved the series “&lt;a href=&quot;http://channel9.msdn.com/series/history&quot;&gt;The History of Microsoft&lt;/a&gt;” (25 episodes) a while ago. I think Channel 9 is still revolutionary (related to the videos), despite the buggy forum.</description>
      <pubDate>Fri, 02 Oct 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/c9-videos/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/c9-videos/</guid>
    </item>
    
    <item>
      <title>Calctor 2.1.2</title>
      <description>&lt;p&gt;I’ve just made a small update to &lt;a href=&quot;https://www.tcx.be/projects/calctor/&quot;&gt;Calctor&lt;/a&gt;. I added the option to use comma as a decimal separator.
&lt;p&gt;You can &lt;a href=&quot;https://app.box.com/s/hd1fulwrkasfnm2qxeev&quot;&gt;download it from Box&lt;/a&gt;.
</description>
      <pubDate>Tue, 28 Jul 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/calctor-2-1-2/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/calctor-2-1-2/</guid>
    </item>
    
    <item>
      <title>for-i-repeat 1.1</title>
      <description>&lt;p&gt;I just uploaded a new version of &lt;a href=&quot;https://www.tcx.be/projects/for-i-repeat/&quot;&gt;for-i-repeat&lt;/a&gt;. The only major changes are:
&lt;ul&gt;
&lt;li&gt;The location and size of the window are now remembered (stored in a settings-file)
&lt;li&gt;The visual style has been improved (uses more recent version of the &lt;a href=&quot;http://tc.codeplex.com/&quot;&gt;TC Libraries&lt;/a&gt;)
&lt;/ul&gt;

&lt;p&gt;You can &lt;a href=&quot;http://www.box.net/shared/afyf5kkpsy&quot;&gt;download it from Box&lt;/a&gt;.</description>
      <pubDate>Sun, 31 May 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/for-i-repeat-1-1/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/for-i-repeat-1-1/</guid>
    </item>
    
    <item>
      <title>Twitter</title>
      <description>&lt;p&gt;I’ve been trying out &lt;a href=&quot;https://twitter.com/&quot;&gt;Twitter&lt;/a&gt; for about a week now. I’m still a bit skeptical about it, but I can see at least 1 advantage: there’s a very close contact between followers and followees. It’s a lot easier to write a quick tweet to someone than it is to comment on their blog. There’s a very convenient bi-directional communication. The 140 character limit is something to get used to, but it also makes you think about what you write. I do like the conventions of replying to someone or mentioning someone via &lt;kbd&gt;@&lt;/kbd&gt;, or referencing an event via &lt;kbd&gt;#&lt;/kbd&gt;.

&lt;p&gt;My twitter address: &lt;a href=&quot;https://twitter.com/tommycarlier&quot;&gt;&lt;var&gt;@tommycarlier&lt;/var&gt;&lt;/a&gt;.</description>
      <pubDate>Thu, 02 Apr 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/twitter/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/twitter/</guid>
    </item>
    
    <item>
      <title>for-i-repeat</title>
      <description>&lt;p&gt;I just finished developing a small tool called &lt;a href=&quot;https://www.tcx.be/projects/for-i-repeat/&quot;&gt;for-i-repeat&lt;/a&gt; that can duplicate a text-fragment a number of times using a counter. The reason I needed this is for the following scenario: at work we have a machine that has 50 databases that all have the same schema, but different data. If I want to modify the schema of all 50 databases, I create a &lt;abbr title=&quot;Structured Query Language&quot;&gt;SQL&lt;/abbr&gt; script that applies the modifications to 1 database, put USE Database01 in front of it, and run it 50 times, each time modifying the USE-statement with the next database number. &lt;i&gt;for-i-repeat&lt;/i&gt; allows me to convert this input:

&lt;pre&gt;&lt;code&gt;USE Database{0:00}
ALTER TABLE …&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;into this output:

&lt;pre&gt;&lt;code&gt;USE Database01
ALTER TABLE …
USE Database02
ALTER TABLE …
USE Database03
ALTER TABLE …
…
USE Database50
ALTER TABLE …&lt;/code&gt;&lt;/pre&gt;
  
&lt;p&gt;A real time-saver! To format the counter &lt;code&gt;{0}&lt;/code&gt;, you can use the full range of &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/427bttx3.aspx&quot;&gt;.NET numeric formatting options&lt;/a&gt;, including hexadecimal formatting (&lt;code&gt;{0:X}&lt;/code&gt;).

&lt;p&gt;You can &lt;a href=&quot;http://www.box.net/shared/afyf5kkpsy&quot;&gt;download it from Box&lt;/a&gt;.</description>
      <pubDate>Sun, 15 Feb 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/for-i-repeat/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/for-i-repeat/</guid>
    </item>
    
    <item>
      <title>Visual Dooby 0.1</title>
      <description>&lt;p&gt;I just uploaded an initial version of &lt;a href=&quot;https://www.tcx.be/projects/visual-dooby/&quot;&gt;Visual Dooby&lt;/a&gt;, a portable lightweight database client.

&lt;p&gt;This initial release is quite limited. You can currently only connect to a SQL Server database, the database browser only displays tables, views and columns, and you can save the results of a query to an &lt;nobr&gt;&lt;abbr title=&quot;Extensible Markup Language&quot;&gt;XML&lt;/abbr&gt;-file&lt;/nobr&gt;.

&lt;p&gt;Some nice features are the advanced customizations when saving to &lt;abbr&gt;XML&lt;/abbr&gt;, the visualization of data types in the result grid and the grid row numbering.

&lt;p&gt;You can &lt;a href=&quot;http://www.box.net/shared/1ief43febt&quot;&gt;download it from Box&lt;/a&gt;.</description>
      <pubDate>Sun, 11 Jan 2009 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2009/visual-dooby-0-1/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2009/visual-dooby-0-1/</guid>
    </item>
    
    <item>
      <title>.NET BCL proposal: read‑only collection interfaces</title>
      <description>&lt;p&gt;As a result of this thread on Channel 9, here’s a proposition for a simple enhancement of the .NET &lt;abbr title=&quot;Base Class Library&quot;&gt;BCL&lt;/abbr&gt;, related to collections.

&lt;p&gt;If a class wants to expose a collection of items, the best thing to do is expose the collection as an abstract interface, so the internal class that is used can be changed without changing the &lt;abbr title=&quot;Application Programming Interface&quot;&gt;API&lt;/abbr&gt;. If you want to expose a read-only collection, the options you have are &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/9eekhta0.aspx&quot;&gt;&lt;code&gt;IEnumerable&amp;lt;T&amp;gt;&lt;/code&gt;&lt;/a&gt;, &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/92t2ye13.aspx&quot;&gt;&lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt;&lt;/a&gt; or &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/5y536ey6.aspx&quot;&gt;&lt;code&gt;IList&amp;lt;T&amp;gt;&lt;/code&gt;&lt;/a&gt;. &lt;code&gt;IEnumerable&amp;lt;T&amp;gt;&lt;/code&gt; represents a read-only collection that can be enumerated, but you can’t ask it how much elements it has. &lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IList&amp;lt;T&amp;gt;&lt;/code&gt; represent collections that could be read-only, but this can only be checked at runtime and not defined at compile-time.

&lt;p&gt;My proposal is to add 2 additional interfaces &lt;code&gt;IReadableCollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IReadableList&amp;lt;T&amp;gt;&lt;/code&gt; that contain a subset of the members of &lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IList&amp;lt;T&amp;gt;&lt;/code&gt; that can be performed on read-only collections. &lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt; could then implement &lt;code&gt;IReadableCollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IList&amp;lt;T&amp;gt;&lt;/code&gt; could implement &lt;code&gt;IReadableList&amp;lt;T&amp;gt;&lt;/code&gt; (and also &lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt;, like it does now). Adding these interfaces would not break existing code, they would be fully backward compatible and would not even require changes to the classes that implement &lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IList&amp;lt;T&amp;gt;&lt;/code&gt;: they would automatically also implement the new interfaces (because &lt;code&gt;ICollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IList&amp;lt;T&amp;gt;&lt;/code&gt; implement &lt;code&gt;IReadableCollection&amp;lt;T&amp;gt;&lt;/code&gt; and &lt;code&gt;IReadableList&amp;lt;T&amp;gt;&lt;/code&gt;).

&lt;p&gt;Here’s what the interface hierarchy would look like:


&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;public interface IEnumerable&amp;lt;T&amp;gt; : IEnumerable
{
  IEnumerator&amp;lt;T&amp;gt; GetEnumerator();
}

public interface IReadableCollection&amp;lt;T&amp;gt; : IEnumerable&amp;lt;T&amp;gt;
{
  int Count { get; }
  bool Contains(T item);
  void CopyTo(T[] array, int arrayIndex);
}

public interface IReadableList&amp;lt;T&amp;gt; : IReadableCollection&amp;lt;T&amp;gt;
{
  T this[int index] { get; }
  int IndexOf(T item);
}

public interface ICollection&amp;lt;T&amp;gt; : IReadableCollection&amp;lt;T&amp;gt;
{
  void Clear();
  void Add(T item);
  bool Remove(T item);
  bool IsReadOnly { get; }
}

public interface IList&amp;lt;T&amp;gt; : ICollection&amp;lt;T&amp;gt;, IReadableList&amp;lt;T&amp;gt;
{
  T this[int index] { get; set; }
  void Insert(int index, T item);
  void RemoveAt(int index);
}&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Tue, 09 Dec 2008 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2008/readonly-collection/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2008/readonly-collection/</guid>
    </item>
    
    <item>
      <title>Google Chrome</title>
      <description>&lt;p&gt;This week the tech news was primarily dominated by the launch of &lt;a href=&quot;http://www.google.com/chrome/&quot;&gt;Google Chrome&lt;/a&gt;. I was going to write about it earlier, but because EVERYBODY was blogging about it, I didn’t think I could add anything useful (I’m not a &lt;i&gt;“me too”&lt;/i&gt;-blogger). But now that the hype is starting to fade a bit, I want to express my opinion about it.

&lt;p&gt;My first impression: I was pleasantly surprised about the smooth installation, the fast startup and the general performance. But the thing I loved the most, was the subtle and minimalist &lt;abbr title=&quot;User Interface&quot;&gt;UI&lt;/abbr&gt;. It has very little features, but I think most &lt;i&gt;normal&lt;/i&gt; people (= non-tech) don’t need many features.

&lt;p&gt;Of course, the main criticism you hear about Chrome is the fact that it’s a Google product. And Google has created it for data mining purposes, to track your every move. I don’t believe this. I think they created it because they NEED a healthy web. They NEED browsers that are powerful enough to run Google’s web applications (GMail, Google Docs, Google Maps, …). And I&apos;m not naïve: I know that Chrome is also a new channel to strengthen Google’s position on the web.

&lt;p&gt;To counter the paranoia, I’ll refer to Matt Cutts’ blog post &lt;a href=&quot;https://www.mattcutts.com/blog/google-chrome-communication/&quot;&gt;&lt;i&gt;“Preventing paranoia: when does Google Chrome talk to Google.com?”&lt;/i&gt;&lt;/a&gt;. The only thing I’m a bit worried about is the auto-suggest function that sends whatever you type in the omnibar to Google. Luckily, you can turn it off (see Matt’s post). Matt goes into great detail about what gets sent to Google and what gets downloaded from Google. His conclusion should silence the paranoids: You can double-check me because the browser is &lt;a href=&quot;http://www.chromium.org/&quot;&gt;open-source&lt;/a&gt;.</description>
      <pubDate>Sun, 07 Sep 2008 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2008/google-chrome/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2008/google-chrome/</guid>
    </item>
    
    <item>
      <title>Microsoft releases Photosynth</title>
      <description>&lt;p&gt;&lt;a href=&quot;http://blogs.msdn.com/photosynth/archive/2008/08/20/welcome-to-photosynth.aspx&quot;&gt;Yesterday&lt;/a&gt;, Microsoft released the highly anticipated &lt;a href=&quot;http://photosynth.net/&quot;&gt;Photosynth&lt;/a&gt; to the public. Now everyone can start synthing (ooh, new verb).

&lt;p&gt;Awesome technology!</description>
      <pubDate>Thu, 21 Aug 2008 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2008/photosynth/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2008/photosynth/</guid>
    </item>
    
    <item>
      <title>Making password TextBox more secure</title>
      <description>&lt;p&gt;If you use a Windows Forms &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/system.windows.forms.textbox.aspx&quot;&gt;&lt;var&gt;TextBox&lt;/var&gt;&lt;/a&gt; to let your users enter a password, you should know it’s not very secure: external applications can get the password from the &lt;var&gt;TextBox&lt;/var&gt; by sending it the &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/ms632627.aspx&quot;&gt;&lt;var&gt;WM_GETTEXT&lt;/var&gt;&lt;/a&gt; message. There are even applications written specifically to do this. If you want to prevent this, you can use the following control that is derived from &lt;var&gt;System.Windows.Forms.TextBox&lt;/var&gt; and that prevents external applications from getting the password via &lt;var&gt;WM_GETTEXT&lt;/var&gt;. Just use it instead of the regular &lt;var&gt;TextBox&lt;/var&gt; for password fields.&lt;/p&gt;



&lt;pre class=&quot;code&quot;&gt;&lt;code&gt;using System;
using System.ComponentModel;
using System.Drawing;
using System.Windows.Forms;
 
namespace TC.WinForms
{
  /// &amp;lt;summary&amp;gt;Represents a text box control for entering passwords.&amp;lt;/summary&amp;gt;
  [ToolboxItem(true), ToolboxBitmap(typeof(TextBox))]
  public class PasswordTextBox : TextBox
  {
    private const int
      WM_GETTEXT = 0x000D,
      WM_GETTEXTLENGTH = 0x000E,
      EM_SETPASSWORDCHAR = 0x00CC;
    
    private bool _isAccessingText;
    
    /// &amp;lt;summary&amp;gt;Initializes a new instance of the &amp;lt;see cref=&amp;quot;T:PasswordTextBox&amp;quot; /&amp;gt; class.&amp;lt;/summary&amp;gt;
    public PasswordTextBox()
    {
      UseSystemPasswordChar = true;
    }
 
    /// &amp;lt;summary&amp;gt;Gets or sets the current text in the &amp;lt;see cref=&amp;quot;T:TextBox&amp;quot;/&amp;gt;.&amp;lt;/summary&amp;gt;
    /// &amp;lt;returns&amp;gt;The text displayed in the control.&amp;lt;/returns&amp;gt;
    public override string Text
    {
      get
      {
        _isAccessingText = true;
        try { return base.Text; }
        finally { _isAccessingText = false; }
      }
      set
      {
        _isAccessingText = true;
        try { base.Text = value; }
        finally { _isAccessingText = false; }
      }
    }
 
    /// &amp;lt;summary&amp;gt;Gets the length of text in the control.&amp;lt;/summary&amp;gt;
    /// &amp;lt;returns&amp;gt;The number of characters contained in the text of the control.&amp;lt;/returns&amp;gt;
    public override int TextLength
    {
      get
      {
        _isAccessingText = true;
        try { return base.TextLength; }
        finally { _isAccessingText = false; }
      }
    }
 
    /// &amp;lt;summary&amp;gt;Processes Windows message.&amp;lt;/summary&amp;gt;
    /// &amp;lt;param name=&amp;quot;m&amp;quot;&amp;gt;The Windows &amp;lt;see cref=&amp;quot;T:Message&amp;quot; /&amp;gt; to process.&amp;lt;/param&amp;gt;
    protected override void WndProc(ref Message m)
    {
      switch (m.Msg)
      {
        case WM_GETTEXT:
        case WM_GETTEXTLENGTH:
          if (!_isAccessingText)
          {
            m.Result = IntPtr.Zero;
            return;
          }
          break;
        
        case EM_SETPASSWORDCHAR:
          return;
      }
 
      base.WndProc(ref m);
    }
  }
}&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;&lt;small&gt;&lt;b&gt;EDIT&lt;/b&gt;: I added code to also ignore &lt;a href=&quot;http://msdn.microsoft.com/en-us/library/bb761653.aspx&quot;&gt;&lt;var&gt;EM_SETPASSWORDCHAR&lt;/var&gt;&lt;/a&gt; which can also be used to make the password visible.&lt;br&gt;
&lt;b&gt;EDIT 2&lt;/b&gt; (2008-04-22): I fixed the documentation tags in the code.&lt;br&gt;
&lt;b&gt;EDIT 3&lt;/b&gt; (2008-04-22): I fixed some bugs that denied access to the password from within your program.&lt;/small&gt;</description>
      <pubDate>Mon, 21 Apr 2008 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2008/password-textbox/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2008/password-textbox/</guid>
    </item>
    
    <item>
      <title>PowerShell + Speech API</title>
      <description>&lt;p&gt;I just read &lt;a href=&quot;http://blogs.msdn.com/b/marcelolr/archive/2008/01/31/say-you-say-me-say-task-complete.aspx&quot;&gt;a blog post about using the Speech API in command-line scripts&lt;/a&gt;. So I had to try it but instead of using JScript, I wrote it in &lt;a href=&quot;http://technet.microsoft.com/en-us/scriptcenter/powershell.aspx&quot;&gt;PowerShell&lt;/a&gt;. It’s so easy and fun:
  
&lt;pre&gt;&lt;code&gt;$v = New-Object -ComObject SAPI.SpVoice
$v.Speak(&quot;Who let the dogs out?&quot;)&lt;/code&gt;&lt;/pre&gt;</description>
      <pubDate>Fri, 01 Feb 2008 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2008/powershell-speech/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2008/powershell-speech/</guid>
    </item>
    
    <item>
      <title>TC Animation Library</title>
      <description>&lt;p&gt;I just released the source code of a Windows Forms animation library I wrote last weekend. I first didn’t want to release the source code because the animations looked terrible.

&lt;p&gt;I knew the code I wrote was good and should work, but it ran horribly. The &lt;abbr title=&quot;User Interface&quot;&gt;UI&lt;/abbr&gt; would just freeze when 1 animation ran; running multiple animations simultaneously was impossible. This morning I woke up and had a mad idea: to slow down the animation. The reason the &lt;abbr&gt;UI&lt;/abbr&gt; would freeze was because all the animation steps were performed on the &lt;nobr&gt;&lt;abbr&gt;UI&lt;/abbr&gt;-thread&lt;/nobr&gt; and apparently the animation system flooded the &lt;nobr&gt;&lt;abbr&gt;UI&lt;/abbr&gt;-thread&lt;/nobr&gt; with work to do, so the normal &lt;nobr&gt;&lt;abbr&gt;UI&lt;/abbr&gt;-activities&lt;/nobr&gt; (painting controls, handling input, …) were severely delayed. By adding 1 line of code (&lt;code&gt;Thread.Sleep(5);&lt;/code&gt;) to the animation loop, I managed to make the animations run fluently while keeping the &lt;abbr&gt;UI&lt;/abbr&gt; responsive.

&lt;p&gt;You can find the source code in the Channel 9 Sandbox, &lt;a href=&quot;http://channel9.msdn.com/forums/sandbox/258660-TC-Animation-Library&quot;&gt;here&lt;/a&gt;.</description>
      <pubDate>Thu, 01 Nov 2007 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2007/tc-animation-library/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2007/tc-animation-library/</guid>
    </item>
    
    <item>
      <title>Calctor 2.1.1</title>
      <description>&lt;p&gt;I’ve just made a small update to &lt;a href=&quot;https://www.tcx.be/projects/calctor/&quot;&gt;Calctor&lt;/a&gt;. No additional functionality has been added. I just made some modifications so you can install it on Windows Vista.
&lt;p&gt;You can &lt;a href=&quot;https://app.box.com/s/hd1fulwrkasfnm2qxeev&quot;&gt;download it from Box&lt;/a&gt;.
</description>
      <pubDate>Sun, 01 Jul 2007 00:00:00 +0000</pubDate>
      <link>https://www.tcx.be/blog/2007/calctor-2-1-1/</link>
      <guid isPermaLink="true">https://www.tcx.be/blog/2007/calctor-2-1-1/</guid>
    </item>
    
  </channel>
</rss>
