<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>eric.ness.net &#187; Programming</title>
	<atom:link href="http://eric.ness.net/archives/tag/programming/feed/" rel="self" type="application/rss+xml" />
	<link>http://eric.ness.net</link>
	<description>...I never learned to read.</description>
	<lastBuildDate>Sat, 21 Jan 2012 05:27:48 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>Cryptanalysis Using n-Gram Probabilities</title>
		<link>http://eric.ness.net/archives/cryptanalysis-using-n-gram-probabilities/</link>
		<comments>http://eric.ness.net/archives/cryptanalysis-using-n-gram-probabilities/#comments</comments>
		<pubDate>Sat, 01 May 2010 09:35:31 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Machine Learning]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[Natural Language Processing]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=472</guid>
		<description><![CDATA[Cryptanalysis Using Microsoft Web N-Gram Service]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fcryptanalysis-using-n-gram-probabilities%2F' data-shr_title='Cryptanalysis+Using+n-Gram+Probabilities'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fcryptanalysis-using-n-gram-probabilities%2F' data-shr_title='Cryptanalysis+Using+n-Gram+Probabilities'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><img class="alignnone" src="/wp-content/uploads/2010/05/cryptanalysis.jpg" alt="" width="577" height="360" /></p>
<p>One of my favorite programmers is <a href="http://norvig.com/">Peter Norvig</a> who is currently Director of Research at Google. This summer I picked up a book called <a href="http://oreilly.com/catalog/9780596157128">Beautiful Data</a> in which Norvig contributed a chapter called &#8220;Natural Language Corpus Data&#8221; in which he outlined a number of very cool things you can do with n-grams in the google  corpus. It covers some of the things you&#8217;d imagine that it would cover: spelling correction, word segmentation, etc. The one item covered that I had never considered was in the area of cryptanalysis.</p>
<p>The cool thing is that Google will give you their corpus to <a href="http://googleresearch.blogspot.com/2006/08/all-our-n-gram-are-belong-to-you.html">download</a>. The only problem is that it contains &#8220;1,024,908,267,229 words of running text&#8221; and is 24 GB compressed in size. This is a bit impractical to run on your dev box. Enter Microsoft &#8211; the <a href="http://web-ngram.research.microsoft.com/info/">Microsoft Web N-gram Service </a>just went Beta and is now available to Professors and Students so I immediately signed up and I have to say that it pretty cool!</p>
<p>So I wanted to try out the new service using one of Norvig&#8217;s examples in his book &#8211; specifically using n-gram probabilities and character shifting. This is a very simple example and fairly basic type of encryption where the if the user types an &#8216;a&#8217; it gets shifted to &#8216;n&#8217; or whatever. So you simply run through all 26 possibilities and use the individual words combined probabilities to determine the answer to the encoded message.</p>
<p>This project has a Service Refrence connected to <a href="http://web-ngram.research.microsoft.com/info/">Microsoft&#8217;s n-Gram Service</a>. The service requires an n-gram model and a user id which you get when you sign up (<a href="http://web-ngram.research.microsoft.com/info/quickstart.htm">see their quickstart tutorial</a>). So let&#8217;s take a look at some code:</p>
<pre class="brush: jscript; title: ; notranslate">
using System;
using System.Collections.Generic;
using System.Configuration;
using System.Linq;
using MicrosoftNGramTest.NGramService;

namespace MicrosoftNGramTest.classes
{
    internal class Shift
    {
        #region Variables

        private readonly string _alphabet = &quot;abcdefghijklmnopqrstuvwxyz&quot;;
        private readonly string _ngramModel = ConfigurationManager.AppSettings.Get(&quot;ngramModel&quot;);
        private readonly string _userToken = ConfigurationManager.AppSettings.Get(&quot;userToken&quot;);

        #endregion

        #region Run The Test

        /// &lt;summary&gt;
        /// Runs the test
        /// &lt;/summary&gt;
        public void Test()
        {
            // Print title
            Console.WriteLine(&quot;Character Shift Cryptanalysis&quot;);
            Console.WriteLine(&quot;#############################&quot;);

            // Local Variables
            const string phrase = &quot;Yvfgra, qb lbh jnag gb xabj n frperg?&quot;;
            string[] words = phrase.ToLower().Split(' ');
            var newPhrase = new string[26];
            var client = new LookupServiceClient();
            var result = new Dictionary&lt;string, int&gt;();

            try
            {
                // Loop the word variations
                foreach (string s in words)
                {
                    char[] currentWord = s.ToCharArray();

                    foreach (char c in currentWord)
                    {
                        for (int i = 0; i &lt; 26; i++)
                        {
                            newPhrase[i] += CharShift(c, i);
                        }
                    }

                    for (int i = 0; i &lt; newPhrase.Count(); i++)
                    {
                        newPhrase[i] += &quot; &quot;;
                    }
                }

                // Print phrases with probabilities
                foreach (string s in newPhrase)
                {
                    string[] newWords = s.Split(' ');
                    double prob = 0;
                    foreach (string word in newWords)
                    {
                        prob += client.GetProbability(_userToken, _ngramModel, word);
                    }
                    Console.WriteLine(s + &quot; &quot; + Convert.ToInt32(prob));
                    result.Add(s, Convert.ToInt32(prob));
                }

                // Print answer
                Console.WriteLine();
                Console.WriteLine(&quot;The answer is:&quot;);
                KeyValuePair&lt;string, int&gt; q = (from t in result
                                               orderby t.Value descending
                                               select t).FirstOrDefault();
                Console.WriteLine(q.Key + &quot; &quot; + q.Value);
            }
            finally
            {
                client.Close();
            }
        }

        #endregion

        #region Shifting

        /// &lt;summary&gt;
        /// Gets the alphabet array.
        /// &lt;/summary&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        private char[] GetAlphabetArray()
        {
            return _alphabet.ToCharArray();
        }

        /// &lt;summary&gt;
        /// Gets the current char array position.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;c&quot;&gt;The c.&lt;/param&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        private int GetCurrentCharArrayPosition(char c)
        {
            int position = 0;
            int count = 0;

            foreach (char letter in GetAlphabetArray())
            {
                if (letter == c)
                {
                    position = count;
                }
                count++;
            }
            return position;
        }

        /// &lt;summary&gt;
        /// Shifts the character.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;c&quot;&gt;The c.&lt;/param&gt;
        /// &lt;param name=&quot;increase&quot;&gt;The increase.&lt;/param&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        private char CharShift(char c, int increase)
        {
            const int numOfLetters = 26;
            char[] alphabet = GetAlphabetArray();
            int currentArrayPosition = GetCurrentCharArrayPosition(c);
            char letter = c;

            if (IsCharInArray(c))
            {
                if ((currentArrayPosition + increase) &lt; numOfLetters)
                {
                    letter = alphabet[currentArrayPosition + increase];
                }
                else
                {
                    int newPosition = (currentArrayPosition + increase) - numOfLetters;
                    letter = alphabet[newPosition];
                }
            }
            return letter;
        }

        /// &lt;summary&gt;
        /// Determines whether the char is in the array.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;c&quot;&gt;The c.&lt;/param&gt;
        /// &lt;returns&gt;
        /// 	&lt;c&gt;true&lt;/c&gt; if [is char in array] [the specified c]; otherwise, &lt;c&gt;false&lt;/c&gt;.
        /// &lt;/returns&gt;
        private bool IsCharInArray(char c)
        {
            bool isCharInArray = false;
            IEnumerable&lt;char&gt; q = (from t in GetAlphabetArray()
                                   where t == c
                                   select t);
            if (q.Count() &gt; 0)
            {
                isCharInArray = true;
            }
            return isCharInArray;
        }

        #endregion
    }
}
</pre>
<p>And here is the result!<br />
<img src="/wp-content/uploads/2010/05/crypt_results.jpg" alt="Results" width="577" /></p>
<div class="shr-publisher-472"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/cryptanalysis-using-n-gram-probabilities/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Benford&#8217;s Law and Trailing Digit Tests</title>
		<link>http://eric.ness.net/archives/befords-law-and-trailing-digit-tests/</link>
		<comments>http://eric.ness.net/archives/befords-law-and-trailing-digit-tests/#comments</comments>
		<pubDate>Wed, 11 Nov 2009 14:23:50 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=371</guid>
		<description><![CDATA[Looking at Benford's Law and Trailing Digit Test]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fbefords-law-and-trailing-digit-tests%2F' data-shr_title='Benford%27s+Law+and+Trailing+Digit+Tests'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fbefords-law-and-trailing-digit-tests%2F' data-shr_title='Benford%27s+Law+and+Trailing+Digit+Tests'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/11/benfordstrailing.jpg"><img class="alignnone size-full wp-image-389" title="benfordstrailing" src="http://eric.ness.net/wp-content/uploads/2009/11/benfordstrailing.jpg" alt="" width="577" height="360" /></a></p>
<p>As of late I&#8217;ve been coming across <a href="http://eric.ness.net/archives/benfords-law/">Benford&#8217;s Law</a> all over the place and so I thought I would revisit the topic. Beford&#8217;s Law essentially states &#8220;that in lists of numbers from many (but not all) real-life sources of data, the leading digit is distributed in a specific, non-uniform way&#8221;. More specifically you should expect the leading digit &#8217;1&#8242; to appear about 30.1% fo the time, &#8217;2&#8242; about 17.6% and so on [<a href="http://en.wikipedia.org/wiki/Benford%27s_law#Mathematical_statement">see table</a>]. One classic example for the use of Benford&#8217;s Law is in fraud detection.</p>
<p>One of the reasons I wanted to revisit this topic is that after having a conversation with a friend about this very topic, I came across a series of articles written by Nate Silver regarding the polling firm Strategic Vision. Strategic Vision released a poll focusing on <a href="http://www.fivethirtyeight.com/2009/09/are-oklahoma-students-really-this-dumb.html">Oklahoma students</a> and it <a href="http://www.fivethirtyeight.com/2009/09/strategic-vision-polls-exhibit-unusual.html">motivated Silver to ask a series of questions about the firm</a>.</p>
<p>Now I don&#8217;t want to really focus in on all the Strategic Vision stuff but, I do want to talk about a method Silver used to detect anomalies in their polling. As Silver correctly suggests, polling would not be a good candidate to using Benford&#8217;s Law (i.e. take the last Presidential race where for the most part the two candidates were going back and forth in the 40~50% range &#8211; Benford&#8217;s wouldn&#8217;t work). However, there is another method that might give you a little insight as Silver explains:</p>
<blockquote><p><span id="fullpost">For each question, I recorded the <span style="font-style: italic;">trailing digit</span> for each candidate or line item. For instance, if Strategic Vision had Barack Obama beating John McCain 48-43 in a particular state, I&#8217;d record a tally in the 8 column and another in the 3 column. Or if they had voters opposing a particular policy 50-45, I&#8217;d record a tally in the 0 column (for 50) and another in the 5 column (for 45). </span></p></blockquote>
<p><span>And what Silver says essentially is, that if you look at the last digit you should have roughly a </span>uniform distribution. Put it another way, that if I have roughly 200 4&#8242;s I would expect roughly 200 8&#8242;s too. Silver also says that when using the trailing digit method that in some cases, you might find deviations from this distribution might be due to rounding error&#8217;s or a specific mathematical method. The trailing digit test is clearly not a sure fire way to detect fraud or anything, but just another useful tool to see if the data passes the smell test.</p>
<p>Silver&#8217;s insight prompted me to write some code and play around with these two methods just to see what comes up. Because I am fairly familiar with the the United Nation&#8217;s World Health Database, I thought I would run some tests using these methods. Here are the results:</p>
<p><strong>Gross Domestic Product (GDP)</strong></p>
<p>As you can see, GDP generally follows Benford&#8217;s Law and the trailing digit test. Something to note on the trailing digit results &#8211; the average for each number (bin) is 23.7 so the number of 1&#8242;s and the number of 5&#8242;s are roughly equidistant from the average, even though it seems a little odd finding a GDP with a value ending in 1 is almost twice as likely as finding a value ending in 5.</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/gdp.jpg"><img class="alignnone size-full wp-image-374" title="gdp" src="http://eric.ness.net/wp-content/uploads/2009/11/gdp.jpg" alt="gdp" width="600" height="250" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/gdp-trail.jpg"><img class="alignnone size-full wp-image-375" title="gdp trail" src="http://eric.ness.net/wp-content/uploads/2009/11/gdp-trail.jpg" alt="gdp trail" width="600" height="250" /></a></p>
<p><strong>Life expectancy at birth (years)</strong></p>
<p>Now here is an example where Benford&#8217;s Law will not work. The reason is because the range of life spans for all countries is from 40-83 years of age, so we are going to have to focus in on the trailing digit test.</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/life-exp.jpg"><img class="alignnone size-full wp-image-378" title="life exp" src="http://eric.ness.net/wp-content/uploads/2009/11/life-exp.jpg" alt="life exp" width="600" height="250" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/life-exp-trail.jpg"><img class="alignnone size-full wp-image-379" title="life exp trail" src="http://eric.ness.net/wp-content/uploads/2009/11/life-exp-trail.jpg" alt="life exp trail" width="600" height="250" /></a></p>
<p>You will notice that there is something weird here with the trailing digits. First, the average value is 19.3 and we have 0&#8242;s and 2&#8242;s appearing almost 3 times more than 7&#8242;s. One thing that might account for this disparity is the fact that we have a little over 20 countries that fall in the range of 80-83, which would tilt the values of 0,1,2,3 a little higher than normal. And the number of countries in the 40&#8242;s is also a little sparse. So what I did was remove these from the set and re-ran the test. Here are the following results.</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/life-exp-norm-benford.jpg"><img class="alignnone size-full wp-image-382" title="life exp norm benford" src="http://eric.ness.net/wp-content/uploads/2009/11/life-exp-norm-benford.jpg" alt="life exp norm benford" width="600" height="250" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/life-exp-norm-trail.jpg"><img class="alignnone size-full wp-image-383" title="life exp norm trail" src="http://eric.ness.net/wp-content/uploads/2009/11/life-exp-norm-trail.jpg" alt="life exp norm trail" width="600" height="250" /></a></p>
<p>You will notice that after cleaning up the data a 3 is still almost 3 times as likely to appear as a 7 in what should be some fairly naturally occurring numbers. The average for this set is <span id="Label1">14.8.</span></p>
<p><span>Now I think it would be inappropriate for me to draw any hard conclusions about the Life Expectancy data other than to say that some form of rounding has likely occurred due to the fact that the data are all whole numbers.<br />
</span></p>
<p><span>That said though, you can see how these two simple/practical tests can assist in determining whether there has been some human manipulation of the data. Here is the code that I used:</span></p>
<pre class="brush: jscript; title: ; notranslate">
using System;
using System.Linq;

namespace BenfordsLaw
{
    /// &lt;summary&gt;
    /// Benfords Law Class
    /// &lt;/summary&gt;
    public class Benfords
    {
        /// &lt;summary&gt;
        /// Adds the data.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;data&quot;&gt;The data.&lt;/param&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        public double[] CalculateBenfordsDistribution(double[] data)
        {
            if (data.Count() == 0)
            {
                throw new ArgumentException(&quot;Error: There are no items in your data array.&quot;);
            }

            //Create benford bins to hold counts
            var benfordsContainer = new double[9];

            // Loop through array
            foreach (double number in data)
            {
                // Get absolute value of number
                double currentNumber = Math.Abs(number);

                // for items smaller than 1 * multiply it so you
                // can find the first number
                if ((currentNumber &lt; 1) &amp;&amp; (currentNumber &gt; 0))
                {
                    double num = (currentNumber*10000);
                    while (num &gt;= 10)
                        num /= 10;
                    PackageNumberInBenfordBin(benfordsContainer, num);
                }
                else
                {
                    double num = currentNumber;
                    while (num &gt;= 10)
                        num /= 10;
                    PackageNumberInBenfordBin(benfordsContainer, num);
                }
            }

            return benfordsContainer;
        }

        /// &lt;summary&gt;
        /// Trailings the digit check.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;data&quot;&gt;The data.&lt;/param&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        public double[] TrailingDigitCheck(double[] data)
        {
            if (data.Count() == 0)
            {
                throw new ArgumentException(&quot;Error: There are no items in your data array.&quot;);
            }

            //Create benford bins to hold counts
            var trailingContainer = new double[10];

            // Loop through array
            foreach (double number in data)
            {
                // Get absolute value of number
                double currentNumber = Math.Abs(number);
                string numTemp = currentNumber.ToString();
                string numTemp2 = numTemp.Substring(numTemp.Length - 1);
                PackageNumberInTrailingBin(trailingContainer, Convert.ToDouble(numTemp2));
            }

            return trailingContainer;
        }

        /// &lt;summary&gt;
        /// Packages the number in benford bin.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;myContainer&quot;&gt;My container.&lt;/param&gt;
        /// &lt;param name=&quot;num&quot;&gt;The num.&lt;/param&gt;
        private static void PackageNumberInBenfordBin(double[] myContainer, double num)
        {
            // Update container totals
            int myNum = Convert.ToInt32(Math.Floor(num));
            myContainer[myNum-1] += 1;
        }

        /// &lt;summary&gt;
        /// Packages the number in trailing bin.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;myContainer&quot;&gt;My container.&lt;/param&gt;
        /// &lt;param name=&quot;num&quot;&gt;The num.&lt;/param&gt;
        private static void PackageNumberInTrailingBin(double[] myContainer, double num)
        {
            // Update container totals
            int myNum = Convert.ToInt32(Math.Floor(num));
            myContainer[myNum] += 1;
        }
    }
}
</pre>
<div class="shr-publisher-371"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/befords-law-and-trailing-digit-tests/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Latent Semantic Indexing</title>
		<link>http://eric.ness.net/archives/latent-semantic-indexing/</link>
		<comments>http://eric.ness.net/archives/latent-semantic-indexing/#comments</comments>
		<pubDate>Sun, 01 Nov 2009 15:48:26 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Machine Learning]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=309</guid>
		<description><![CDATA[Latent Semantic Indexing in C#]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Flatent-semantic-indexing%2F' data-shr_title='Latent+Semantic+Indexing'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Flatent-semantic-indexing%2F' data-shr_title='Latent+Semantic+Indexing'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/11/lsiblog.jpg"><img class="alignnone size-full wp-image-331" title="lsiblog" src="http://eric.ness.net/wp-content/uploads/2009/11/lsiblog.jpg" alt="" width="577" height="360" /></a></p>
<p>Latent Semantic Indexing (LSI) is commonly described as a &#8220;indexing and retrieval method that uses a mathematical technique called <a href="http://eric.ness.net/archives/singular-value-decomposition/">Singular Value Decomposition</a> (SVD) to identify patterns in the relationships between the terms and concepts contained in an unstructured collection of text.&#8221;. To be a bit more clear Sujit Pal has one of the best descriptions of what LSI is and how it occures:</p>
<blockquote><p>Latent Semantic Indexing attempts to uncover latent relationships among documents based on word co-occurence. So if document A contains (w1,w2) and document B contains (w2,w3), we can conclude that there is something common between documents A and B. LSI does this by decomposing the input raw term frequency matrix (A, see below) into three different matrices (U, S and V) using Singular Value Decomposition (SVD). Once that is done, the three vectors are &#8220;reduced&#8221; and the original vector rebuilt from the reduced vectors. Because of the reduction, noisy relationships are suppressed and relations become very clearly visible.</p></blockquote>
<p><strong>So how is this done?</strong></p>
<p>To start with let&#8217;s use the example in &#8220;<a href="http://lsa.colorado.edu/papers/JASIS.lsi.90.pdf">Indexing by Latent Semantic Analysis</a>&#8221; (Deerwester et al.) because you see this example repeated in a number of places on the web. The example in the paper says let&#8217;s take a look at 9 titles of papers that fall in to two categories &#8220;human computer interaction&#8221; &amp; &#8220;graphs &amp; trees&#8221;. <a href="http://eric.ness.net/wp-content/uploads/2009/11/listofwords.jpg"></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/listofwords.jpg"><img class="alignnone size-full wp-image-310" style="margin-left: 100px; margin-right: 100px;" title="listofwords" src="http://eric.ness.net/wp-content/uploads/2009/11/listofwords.jpg" alt="listofwords" width="400" height="505" /></a></p>
<p>In this example the matrix is comprised of the word counts in the different document. The next step is take this matrix and break it down in to it&#8217;s different parts using SVD. The result looks like this:</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/svd.jpg"><img class="alignnone size-full wp-image-320" title="svd" src="http://eric.ness.net/wp-content/uploads/2009/11/svd.jpg" alt="svd" width="600" /></a></p>
<p>After you have preformed SVD on the original matrix you then reduce the individual vectors. What the reduction of the vectors does is get rid of some of the &#8220;noise&#8221; &#8211; exposing the relationship between words and documents.</p>
<p>One question that arises is how much do you want to reduce the vectors (often called k)? There seems to be no hard and fast rule to this as different papers have different approaches/results with different values. In Sujit Pal&#8217;s <a href="http://sujitpal.blogspot.com/2008/09/ir-math-with-java-tf-idf-and-lsi.html">post</a> he uses the square root of the number of columns of the original matrix (m) which is then rounded down minus 1 which is I think a good method to use. It also happens to be the value that is used in the Deerwester paper k=2. The following picture shows what this looks like (please see Jennifer Flynn&#8217;s presentation <a href="http://www.soe.ucsc.edu/classes/cmps290c/Spring07/proj/Flynn_talk.pdf">Latent Semantic Indexing Using SVD and Riemannian SVD</a> for a more elaborate example):</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/reduce.jpg"><img class="alignnone size-full wp-image-323" title="reduce" src="http://eric.ness.net/wp-content/uploads/2009/11/reduce.jpg" alt="reduce" width="600" /></a></p>
<p>After the vectors have been reduced all that is required to do is take the vectors and multiply them back together again and that is it. See the result:</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/11/lsi1.jpg"><img class="alignnone size-full wp-image-326" title="lsi" src="http://eric.ness.net/wp-content/uploads/2009/11/lsi1.jpg" alt="lsi" width="600" /></a></p>
<p>[<strong>Update</strong>: as one of the readers (Jorge) noted v is not exactly correct it should be V.Transpose. Please check out the “Indexing by Latent Semantic Analysis” (Deerwester et al.) paper starting on page 26 for the correct values of the matrices <a rel="nofollow" href="http://lsa.colorado.edu/papers/JASIS.lsi.90.pdf">http://lsa.colorado.edu/papers/JASIS.lsi.90.pdf</a> I will try to update this here shortly]</p>
<p>So lets take a look at the code &#8211; it follows the example outlined in the Deerwester paper and please keep in mind that is just a little class i put together in a asp.net test app that shows a html formatted matrix of the original (m) and the LSI result:</p>
<pre class="brush: jscript; title: ; notranslate">
using System;
using SmartMathLibrary;

namespace LSITest
{
    public class lsi
    {
        // this returns the formated html results
        public string ToPrint;

        /// &lt;summary&gt;
        /// LISs the test.
        /// &lt;/summary&gt;
        public void LSITest()
        {
            //Create Matrix
            var testArray = new double[,]
                                {
                                    {1, 0, 0, 1, 0, 0, 0, 0, 0},
                                    {1, 0, 1, 0, 0, 0, 0, 0, 0},
                                    {1, 1, 0, 0, 0, 0, 0, 0, 0},
                                    {0, 1, 1, 0, 1, 0, 0, 0, 0},
                                    {0, 1, 1, 2, 0, 0, 0, 0, 0},
                                    {0, 1, 0, 0, 1, 0, 0, 0, 0},
                                    {0, 1, 0, 0, 1, 0, 0, 0, 0},
                                    {0, 0, 1, 1, 0, 0, 0, 0, 0},
                                    {0, 1, 0, 0, 0, 0, 0, 0, 1},
                                    {0, 0, 0, 0, 0, 1, 1, 1, 0},
                                    {0, 0, 0, 0, 0, 0, 1, 1, 1},
                                    {0, 0, 0, 0, 0, 0, 0, 1, 1}
                                };

            // Load array in to Matrix
            var a = new Matrix(testArray);

            // print original matrix
            PrintMatrix(a);

            // preform Latent Semantic Indexing
            Transform(a);
        }

        /// &lt;summary&gt;
        /// Prints the matrix.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;myMatrix&quot;&gt;My matrix.&lt;/param&gt;
        private void PrintMatrix(IMatrix myMatrix)
        {
            ToPrint += &quot;&lt;br /&gt;&lt;br /&gt;&quot;;

            for (int i = 0; i &lt; myMatrix.Rows; i++)
            {
                for (int j = 0; j &lt; myMatrix.Columns; j++)
                {
                    ToPrint += String.Format(&quot;{0:0.##}&quot;, myMatrix.MatrixData[i, j]) + &quot;\t&quot;;
                }
                ToPrint += &quot;&lt;br /&gt;&quot;;
            }
        }

        /// &lt;summary&gt;
        /// Transforms the specified my matrix.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;myMatrix&quot;&gt;My matrix.&lt;/param&gt;
        private void Transform(Matrix myMatrix)
        {
            // Run single value decomposition
            var svd = new SingularValueDecomposition(myMatrix);
            svd.ExecuteDecomposition();

            // Put components into individual matrices
            Matrix wordVector = svd.U.Copy();
            Matrix sigma = svd.S.ToMatrix();
            Matrix documentVector = svd.V.Copy();

            // get value of k
            // you can also manually set the value of k
            var k = (int) Math.Floor(Math.Sqrt(myMatrix.Columns));

            // reduce the vectors
            Matrix reducedWordVector = CopyMatrix(wordVector, wordVector.Rows, k - 1);
            Matrix reducedSigma = CreateSigmaMatrix(sigma, k - 1, k - 1);
            Matrix reducedDocumentVector = CopyMatrix(documentVector, documentVector.Rows, k - 1);

            // re-compute matrix
            Matrix a = reducedWordVector*reducedSigma*reducedDocumentVector.Transpose();

            // print result
            PrintMatrix(a);
        }

        /// &lt;summary&gt;
        /// Creates the sigma matrix.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;matrix&quot;&gt;The matrix.&lt;/param&gt;
        /// &lt;param name=&quot;rowEnd&quot;&gt;The row end.&lt;/param&gt;
        /// &lt;param name=&quot;columnEnd&quot;&gt;The column end.&lt;/param&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        private static Matrix CreateSigmaMatrix(IMatrix matrix, int rowEnd, int columnEnd)
        {
            var copyMatrix = new Matrix(rowEnd, columnEnd);

            for (int i = 0; i &lt; columnEnd; i++)
            {
                copyMatrix.MatrixData[i, i] = matrix.MatrixData[i, 0];
            }

            return copyMatrix;
        }

        /// &lt;summary&gt;
        /// Copies the matrix.
        /// &lt;/summary&gt;
        /// &lt;param name=&quot;myMatrix&quot;&gt;My matrix.&lt;/param&gt;
        /// &lt;param name=&quot;rowEnd&quot;&gt;The row end.&lt;/param&gt;
        /// &lt;param name=&quot;columnEnd&quot;&gt;The column end.&lt;/param&gt;
        /// &lt;returns&gt;&lt;/returns&gt;
        private static Matrix CopyMatrix(IMatrix myMatrix, int rowEnd, int columnEnd)
        {
            var copyMatrix = new Matrix(rowEnd, columnEnd);

            for (int i = 0; i &lt; rowEnd; i++)
            {
                for (int j = 0; j &lt; columnEnd; j++)
                {
                    copyMatrix.MatrixData[i, j] = myMatrix.MatrixData[i, j];
                }
            }

            return copyMatrix;
        }
    }
}
</pre>
<p>With much thanks to Sujit Pal, Jennifer Flynn and Deerwester for their excellent explanations.</p>
<p><strong>Recommended Reading</strong></p>
<p><a href="http://sujitpal.blogspot.com/2008/09/ir-math-with-java-tf-idf-and-lsi.html">IR Math with Java : TF, IDF and LSI</a> &#8211; Sujit Pal</p>
<p><a href="http://lsa.colorado.edu/papers/JASIS.lsi.90.pdf">Indexing by Latent Semantic Analysis</a> &#8211; Deerwester et al</p>
<p><a href="http://www.soe.ucsc.edu/classes/cmps290c/Spring07/proj/Flynn_talk.pdf">Latent Semantic Indexing Using SVD and Riemannian SVD</a> &#8211; Jennifer Flynn</p>
<div class="shr-publisher-309"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/latent-semantic-indexing/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Singular Value Decomposition</title>
		<link>http://eric.ness.net/archives/singular-value-decomposition/</link>
		<comments>http://eric.ness.net/archives/singular-value-decomposition/#comments</comments>
		<pubDate>Mon, 26 Oct 2009 16:00:06 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Machine Learning]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=299</guid>
		<description><![CDATA[Singular Value Decomposition using the SmartMathLibrary in C#]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fsingular-value-decomposition%2F' data-shr_title='Singular+Value+Decomposition'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fsingular-value-decomposition%2F' data-shr_title='Singular+Value+Decomposition'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/10/svd.jpg"><img class="alignnone size-full wp-image-300" title="svd" src="http://eric.ness.net/wp-content/uploads/2009/10/svd.jpg" alt="" width="577" height="360" /></a></p>
<p>Singular Value Decomposition is something I&#8217;ve been wanting to wrap my head around for a while now that I am getting really into Machine Learning. Unfortunately, a lot of the material out there is often hard to understand and believe it or not there are few libraries that are available in .NET.</p>
<p>So what is singular value decomposition (SVD)? Probabably, the best description I&#8217;ve run across is:</p>
<blockquote><p>Singular Value Decomposition is a way of factoring matrices into a series of linear approximations that expose the underlying structure of the matrix. SVD is extraordinarily useful and has many applications such as data analysis, signal processing, pattern recognition, image compression, weather prediction, and Latent Semantic Analysis. [<a href="http://puffinwarellc.com/index.php/news-and-articles/articles/30-singular-value-decomposition-tutorial.html">iMetaSearch</a>]</p></blockquote>
<p>SVD formula is:</p>
<p style="text-align: center;"><strong>M=Uâˆ‘V*</strong></p>
<p style="text-align: left;">M is simply a m-by-n matrix, U form a set of orthonormal &#8220;output&#8221; basis vector directions for M, Î£ are the singular values, which can be thought of as scalar &#8220;gain controls&#8221; by which each corresponding input is multiplied to give a corresponding output and V* form a set of orthonormal &#8220;input&#8221; or &#8220;analysing&#8221; basis vector directions for M. The best walk through I&#8217;ve come across is over at iMetaSearch <a href="http://puffinwarellc.com/index.php/news-and-articles/articles/30-singular-value-decomposition-tutorial.html">here</a>.</p>
<p style="text-align: left;"><strong>A lack of good .NET Libraries.</strong></p>
<p style="text-align: left;">I tried out four different libraries: <a href="http://smartmathlibrary.codeplex.com/">SmartMathLibrary</a>, <a href="http://latoolnet.codeplex.com/">LatoolNet</a>, <a href="http://www.alglib.net/">ALGLIB</a> and <a href="http://www.codeproject.com/KB/recipes/psdotnetmatrix.aspx?msg=2345970">DotNetMatrix</a>. Out of these four I could only get two of them completely working and I ultimately came to the conclusion that <a href="http://smartmathlibrary.codeplex.com/">SmartMathLibrary</a> was the best for doing SVD.</p>
<p style="text-align: left;"><strong>The Code</strong></p>
<p style="text-align: left;">Here is the code to replicate this tutorial over at <a href="http://web.mit.edu/be.400/www/SVD/Singular_Value_Decomposition.htm">MIT</a>.</p>
<pre class="brush: jscript; title: ; notranslate">
using System;
using SmartMathLibrary;

namespace MatrixTest2
{
    internal class Program
    {
        private static void Main(string[] args)
        {
            SVDTest();
            Console.ReadLine();
        }

        private static void SVDTest()
        {
            // Create/load array
            var holeDifficulty = new double[,]
                                     {
                                         {2, 1, 0, 0},
                                         {4, 3, 0, 0}
                                     };

            // Load in to Matrix
            var a = new Matrix(holeDifficulty);

            // Singular Value Decomposition
            var SVD = new SingularValueDecomposition(a);
            SVD.ExecuteDecomposition();

            // Get the general vector
            GeneralVector s = SVD.S;

            // Display results
            Console.WriteLine(a.Transpose().ToString());
            Console.WriteLine();
            Console.WriteLine(s.ToString());
            Console.WriteLine();
            Console.WriteLine(SVD.U.ToString());
            Console.WriteLine();
            Console.WriteLine(SVD.V.ToString());
        }
    }
}
</pre>
<p><strong>Additional Resources</strong></p>
<p><a href="http://puffinwarellc.com/index.php/news-and-articles/articles/30-singular-value-decomposition-tutorial.html">iMetaSearch</a></p>
<p><a href="http://sujitpal.blogspot.com/2008/09/ir-math-with-java-tf-idf-and-lsi.html">IR Math with Java : TF, IDF and LSI</a></p>
<p><a href="http://alias-i.com/lingpipe/demos/tutorial/svd/read-me.html">SVD Tutorial</a></p>
<div class="shr-publisher-299"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/singular-value-decomposition/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Pearson&#8217;s Correlation Coefficient</title>
		<link>http://eric.ness.net/archives/pearsons-correlation-coefficient/</link>
		<comments>http://eric.ness.net/archives/pearsons-correlation-coefficient/#comments</comments>
		<pubDate>Sun, 25 Oct 2009 19:33:25 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Machine Learning]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[Statistics]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=272</guid>
		<description><![CDATA[Pearson's Correlation Coefficient walk through]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fpearsons-correlation-coefficient%2F' data-shr_title='Pearson%27s+Correlation+Coefficient'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fpearsons-correlation-coefficient%2F' data-shr_title='Pearson%27s+Correlation+Coefficient'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/10/Pearsons_Correlation_Coeffi.jpg"><img class="alignnone size-full wp-image-282" title="Pearsons_Correlation_Coeffi" src="http://eric.ness.net/wp-content/uploads/2009/10/Pearsons_Correlation_Coeffi.jpg" alt="" width="577" height="360" /></a></p>
<p>In Toby Segaran&#8217;s book &#8220;Programming Collective Intelligence&#8221; one additional methods used &#8220;to determine the similarity between people&#8217;s interests is to use the Pearson&#8217;s correlation coefficient. In statistics Pearson&#8217;s correlation coefficient is often symbolized as simply r. I also covered Toby&#8217;s Euclidean Distance Score <a title="http://eric.ness.net/archives/euclidean-distance-score/" href="http://eric.ness.net/archives/euclidean-distance-score/">here</a>.</p>
<p><img src="http://eric.ness.net/wp-content/uploads/2009/10/hl_correl_frm_r.png" alt="hl_correl_frm_r" width="197" height="102" /></p>
<p>Is how r is calculated.</p>
<p>And here is some sloppy source code to get you going:</p>
<pre class="brush: jscript; title: ; notranslate">
using System;
using System.Linq;

namespace PearsonTest
{
    internal class Program
    {
        private static void Main(string[] args)
        {
            var myP = new Correlation();

            var lisaRose = new double[] {0, 2, 4, 6, 8, 10, 12};
            var jackMatthews = new[] {2.1, 5, 9, 12.6, 17.3, 21, 24.7};

            double score = myP.PearsonCorrelation(lisaRose, jackMatthews);

            Console.WriteLine(score);
            Console.ReadLine();

            // The answer is 0.99887956534852
        }
    }

    internal class Correlation
    {
        public double PearsonCorrelation(double[] x, double[] y)
        {
            double result;
            double xMean = 0;
            double yMean = 0;
            double xDenom = 0;
            double yDenom = 0;
            double denominator;
            double numerator = 0;
            double n;

            // Make sure arrays are same size and greater than 1
            if ((x.Count() == y.Count()) &amp;&amp; (x.Count() &gt;= 1))
            {
                n = x.Count();
            }
            else
            {
                result = 0;
                return result;
            }

            // Find Means
            for (int i = 0; i &lt;= n - 1; i++)
            {
                xMean += x[i];
                yMean += y[i];
            }
            xMean = xMean/n;
            yMean = yMean/n;

            // Caluculate numerator and denominator
            for (int i = 0; i &lt;= n - 1; i++)
            {
                //Caluculate numerator
                double numX = x[i] - xMean;
                double numY = y[i] - yMean;
                numerator += numX*numY;

                // Caluculate denominator parts
                xDenom += Math.Pow(numX, 2);
                yDenom += Math.Pow(numY, 2);
            }

            // Caluculate denominator
            denominator = Math.Sqrt(xDenom*yDenom);

            // Check for division by zero
            if (denominator == 0)
            {
                result = 0;
            }
            else
            {
                result = numerator/denominator;
            }

            return result;
        }
    }
}
</pre>
<div class="shr-publisher-272"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/pearsons-correlation-coefficient/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>SQL Server Migration Assistant for Access Walk Through.</title>
		<link>http://eric.ness.net/archives/sql-server-migration-assistant-for-access-walk-through/</link>
		<comments>http://eric.ness.net/archives/sql-server-migration-assistant-for-access-walk-through/#comments</comments>
		<pubDate>Fri, 16 Oct 2009 10:07:47 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=242</guid>
		<description><![CDATA[SQL Server Migration Assistant for Access Walk Through.]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fsql-server-migration-assistant-for-access-walk-through%2F' data-shr_title='SQL+Server+Migration+Assistant+for+Access+Walk+Through.'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fsql-server-migration-assistant-for-access-walk-through%2F' data-shr_title='SQL+Server+Migration+Assistant+for+Access+Walk+Through.'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/10/SQL_Server_Migration_Assist.jpg"><img class="alignnone size-full wp-image-243" title="SQL_Server_Migration_Assist" src="http://eric.ness.net/wp-content/uploads/2009/10/SQL_Server_Migration_Assist.jpg" alt="" width="577" height="360" /></a><br />
I am currently traveling and do not have MS SQL Server Workgroup edition loaded up on my laptop and needed to import some data from an Microsoft Access database. In doing a quick search I cam across this great utility called SQL Server Migration Assistant for Access which you can <a href="http://www.microsoft.com/downloads/details.aspx?familyid=D842F8B4-C914-4AC7-B2F3-D25FFF4E24FB&amp;displaylang=en">download for free here</a>. Does everything I need and is pretty easy to use &#8211; but, I took some screen shots to show you how it&#8217;s done.</p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/1.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/1.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/2.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/2.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/3.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/3.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/4.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/4.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/5.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/5.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/6.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/6.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/7.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/7.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/8.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/8.jpg" alt="1" width="562" height="366" /></a></p>
<p><a href="http://eric.ness.net/wp-content/uploads/2009/10/9.jpg"><img class="alignnone size-full wp-image-246" title="1" src="http://eric.ness.net/wp-content/uploads/2009/10/9.jpg" alt="1" width="562" height="366" /></a></p>
<div class="shr-publisher-242"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/sql-server-migration-assistant-for-access-walk-through/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>My toolbox: A little list of programming tools.</title>
		<link>http://eric.ness.net/archives/my-toolbox-a-little-list-of-programming-tools/</link>
		<comments>http://eric.ness.net/archives/my-toolbox-a-little-list-of-programming-tools/#comments</comments>
		<pubDate>Sat, 06 Jun 2009 17:05:53 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Tools]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=213</guid>
		<description><![CDATA[A little list of tools I use.]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fmy-toolbox-a-little-list-of-programming-tools%2F' data-shr_title='My+toolbox%3A+A+little+list+of+programming+tools.'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fmy-toolbox-a-little-list-of-programming-tools%2F' data-shr_title='My+toolbox%3A+A+little+list+of+programming+tools.'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/06/mytoolbox.jpg"><img class="alignnone size-full wp-image-214" title="mytoolbox" src="http://eric.ness.net/wp-content/uploads/2009/06/mytoolbox.jpg" alt="" width="577" height="360" /></a></p>
<p>List of tools I use:</p>
<h2><strong>Add-In&#8217;s</strong></h2>
<p><strong>Resharper:</strong> Is one of those add-ins that once you start using it would be hard to give up â€“ as it provides solutions to programming errors, helps out with refactoring, unit testing, code formatting and clean up. [<a title="Resharper" href="http://www.jetbrains.com/resharper/" target="_blank">link</a>]<br />
<strong>VisualSVN:</strong> You need a plug-in that connects your solution to some form of version control. Iâ€™ve always been a fan of Subversion [free] and VisualSVN helps me connect to it.<a title="ankhsvn" href="http://ankhsvn.open.collab.net/" target="_blank"> AnkhSVN</a> is also a great free alternative. I would also recommend that you check out <a title="Visual SVN Server" href="http://www.visualsvn.com/server/" target="_blank">Visual SVN Server</a> as it allows you configure and manage Subversion for your whole team and it is free. [<a title="VisualSVN" href="http://www.visualsvn.com/" target="_blank">link</a>]<br />
<strong>GhostDoc:</strong> This free extension automatically generates your documentation comments for your code. A must. [<a title="ghostdoc" href="http://submain.com/products/ghostdoc.aspx" target="_blank">link</a>]<br />
<strong>Clone Detective: </strong>This add-in tells you where you are repeating code. Very helpful but sometimes does not play well with others add-ins. [<a title="Clone Detective" href="http://www.codeplex.com/CloneDetectiveVS" target="_blank">link</a>]</p>
<h2><strong>Controls</strong></h2>
<p><strong>Dundas:</strong> Best graphing framework on .NET period. Only negative is that it is not cheap but you can accomplish most stuff with ASP.NET Charting Controls. [<a title="Dundas" href="http://dundas.com/" target="_blank">link</a>]<br />
<strong>Virtual Earth:</strong> Fun control to use Virtual Earth. [<a title="Virtual Earth" href="http://msdn.microsoft.com/en-us/library/dd877180.aspx" target="_blank">link</a>]<br />
<strong>Telerik RadControls:</strong> Great controls and is a must but like Dundas is not cheap. [<a title="telerik" href="http://www.telerik.com/" target="_blank">link</a>]<br />
<strong>ASP.Net Ajax Framework:</strong> A must if you are still doing web forms page. [<a title="ASP.NET Ajax" href="http://www.asp.net/ajax/">link</a>]<br />
<strong>ASP.Net Ajax Toolkit:</strong> The bells and whistles for the framework. [<a title="ASP.NET Ajax Toolkit" href="http://www.asp.net/ajax/AjaxControlToolkit/Samples/" target="_blank">link</a>]</p>
<div class="shr-publisher-213"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/my-toolbox-a-little-list-of-programming-tools/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>ASP.NET MVC Links</title>
		<link>http://eric.ness.net/archives/aspnet-mvc-links/</link>
		<comments>http://eric.ness.net/archives/aspnet-mvc-links/#comments</comments>
		<pubDate>Sat, 18 Apr 2009 18:13:00 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Link Roundup]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[ASP.NET MVC]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=192</guid>
		<description><![CDATA[There have been a number of outstanding articles as of late regarding ASP.NET MVC.]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Faspnet-mvc-links%2F' data-shr_title='ASP.NET+MVC+Links'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Faspnet-mvc-links%2F' data-shr_title='ASP.NET+MVC+Links'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/04/mvc.jpg"><img class="alignnone size-full wp-image-193" title="mvc" src="http://eric.ness.net/wp-content/uploads/2009/04/mvc.jpg" alt="" width="577" height="360" /></a></p>
<p>There have been a number of outstanding articles as of late regarding ASP.NET MVC.</p>
<p><a href="http://weblogs.asp.net/rashid/archive/2009/4/1/asp-net-mvc-best-practices-part-1.aspx">ASP.NET MVC Best Practices (Part 1)</a><br />
<a href="http://weblogs.asp.net/rashid/archive/2009/04/03/asp-net-mvc-best-practices-part-2.aspx">ASP.NET MVC Best Practices (Part 2) </a><br />
<a href="http://ericdotnet.wordpress.com/2009/04/09/jquery-search-box-and-aspnet-mvc/">jQuery Search box and Asp.net MVC</a><br />
<a href="http://bradwilson.typepad.com/blog/2009/04/dataannotations-and-aspnet-mvc.html">DataAnnotations and ASP.NET MVC</a><br />
<a href="http://blog.whiletrue.com/2009/04/aspnet-mvc-performance/"> ASP.NET MVC Performance</a></p>
<div class="shr-publisher-192"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/aspnet-mvc-links/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Haack MVC Video: Cross-site Request Forgery Attack</title>
		<link>http://eric.ness.net/archives/haack-mvc-video-cross-site-request-forgery-attack/</link>
		<comments>http://eric.ness.net/archives/haack-mvc-video-cross-site-request-forgery-attack/#comments</comments>
		<pubDate>Fri, 10 Apr 2009 14:54:28 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Security]]></category>
		<category><![CDATA[ASP.NET MVC]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=166</guid>
		<description><![CDATA[I was going to post a link to this video a couple of days ago.]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fhaack-mvc-video-cross-site-request-forgery-attack%2F' data-shr_title='Haack+MVC+Video%3A+Cross-site+Request+Forgery+Attack'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fhaack-mvc-video-cross-site-request-forgery-attack%2F' data-shr_title='Haack+MVC+Video%3A+Cross-site+Request+Forgery+Attack'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2009/04/phil-haack.jpg"><img class="alignnone size-full wp-image-167" title="phil-haack" src="http://eric.ness.net/wp-content/uploads/2009/04/phil-haack.jpg" alt="" width="577" height="360" /></a></p>
<p>I was going to post a link to this video a couple of days ago &#8211; it&#8217;s Phil Haack&#8217;s MIX09 &#8220;ASP.NET MVC Ninjas on Fire Black Belt Tips&#8221; presentation.</p>
<p>This presentation covers among other things Cross-Site Request Forgery Attacks. Haack also wrote up a great blog post on the topic as well.</p>
<p><a href="http://videos.visitmix.com/MIX09/T44F">http://videos.visitmix.com/MIX09/T44F</a> [Video]<br />
<a href="http://haacked.com/archive/2009/04/02/anatomy-of-csrf-attack.aspx">http://haacked.com/archive/2009/04/02/anatomy-of-csrf-attack.aspx</a> [Blog Post]</p>
<div class="shr-publisher-166"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/haack-mvc-video-cross-site-request-forgery-attack/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>MVC Pair Programming Videos</title>
		<link>http://eric.ness.net/archives/mvc-pair-programming-videos/</link>
		<comments>http://eric.ness.net/archives/mvc-pair-programming-videos/#comments</comments>
		<pubDate>Sat, 23 Aug 2008 16:19:24 +0000</pubDate>
		<dc:creator>Eric</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Video/Audio]]></category>
		<category><![CDATA[TDD]]></category>
		<category><![CDATA[Video]]></category>

		<guid isPermaLink="false">http://eric.ness.net/?p=58</guid>
		<description><![CDATA[ASP.Net MVC Site has some new paired programming videos featuring Charlie Pool of NUnit.]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop Automatic --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-fblike' data-shr_layout='button_count' data-shr_showfaces='false' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fmvc-pair-programming-videos%2F' data-shr_title='MVC+Pair+Programming+Videos'></a><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Feric.ness.net%2Farchives%2Fmvc-pair-programming-videos%2F' data-shr_title='MVC+Pair+Programming+Videos'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetTop Automatic --><p><a href="http://eric.ness.net/wp-content/uploads/2008/08/mvc_charlie_pool.jpg"><img class="alignnone size-full wp-image-55" title="mvc_charlie_pool" src="http://eric.ness.net/wp-content/uploads/2008/08/mvc_charlie_pool.jpg" alt="" width="577" height="360" /></a></p>
<p>ASP.Net MVC Site has some new <a title="MVC Pair Programming Videos" href="http://www.asp.net/learn/mvc-videos/#MVCPairProgramming">paired programming videos</a> featuring Charlie Pool of <a title="NUnit" href="http://www.nunit.org">NUnit</a>.</p>
<div class="shr-publisher-58"></div><!-- Start Shareaholic LikeButtonSetBottom Automatic --><!-- End Shareaholic LikeButtonSetBottom Automatic -->]]></content:encoded>
			<wfw:commentRss>http://eric.ness.net/archives/mvc-pair-programming-videos/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

