<?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>FORTH GO &#187; Code</title>
	<atom:link href="http://www.forthgo.com/blog/category/code/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.forthgo.com/blog</link>
	<description>Code and Recreations of Xan Gregg</description>
	<lastBuildDate>Sat, 20 Aug 2011 17:32:24 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.2.1</generator>
		<item>
		<title>Google Code Jam 2011 Round 2</title>
		<link>http://www.forthgo.com/blog/2011/06/04/google-code-jam-2011-round-2/</link>
		<comments>http://www.forthgo.com/blog/2011/06/04/google-code-jam-2011-round-2/#comments</comments>
		<pubDate>Sat, 04 Jun 2011 21:09:24 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[Code]]></category>
		<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/?p=483</guid>
		<description><![CDATA[My luck ran out in Round 2 of the Google Code Jam 2011. I placed 626th but needed to be in the top 500 to advance. At least I qualified for a T-shirt for being in the top 1000. There &#8230; <a href="http://www.forthgo.com/blog/2011/06/04/google-code-jam-2011-round-2/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>My luck ran out in Round 2 of the <a href="http://code.google.com/codejam/">Google Code Jam</a> 2011. I placed 626<sup>th</sup> but needed to be in the top 500 to advance. At least I qualified for a T-shirt for being in the top 1000.</p>
<p>There were four problems this time, with less variation in difficulty than usual. I solved the first problem, <a href="http://code.google.com/codejam/contest/dashboard?c=1150486#s=p0">Airport Walkways</a>, completely and got partial credit for my correct-but-inefficient solutions to two other problems. Of course, I figured out how to make my solutions efficient shortly after the contest ended. I didn&#8217;t get to the fourth problem, <a href="http://code.google.com/codejam/contest/dashboard?c=1150486#s=p3">A. I. War</a>, but it looks more straightforward than I expected from a title alluding to artificial intelligence. Maybe I could have solved that one completely instead of one of the partial solutions.</p>
<p>The third problem, <a href="http://code.google.com/codejam/contest/dashboard?c=1150486#s=p2">Expensive Dinner</a>, involved finding the difference between the best and worst case for a particular problem involving least common multiples. I set about computing both cases separately and taking the difference. I thought I was doing well to reduce the naive O(n<sup>2</sup>) solution to O(n), but when n is 10<sup>12</sup>, that&#8217;s not good enough (for full credit). I reduced the best case to be the number of primes less than or equal to n, aka &pi;(n), and the worst case to be the number of primes powers less than n. That seemed like a dead-end, though, since it&#8217;s not so easy to calculate &pi;(10<sup>12</sup>). What I didn&#8217;t see in time is that since I was going to be taking the difference of the two and they both included &pi;(n), I didn&#8217;t have to compute that part at all. And counting the higher prime powers is much easier, and that&#8217;s all I really needed to do. Oh well.</p>
<p>The second problem, <a href="http://code.google.com/codejam/contest/dashboard?c=1150486#s=p1">Spinning Blade</a>, didn&#8217;t involve any fancy math, but required a clever data structure to reduce it from O(n<sup>4</sup>) to O(n<sup>2</sup>) or so. (n was limited to 500, so O(n<sup>2</sup>) is fine.) I didn&#8217;t find it in time, though, and went with my brute force solution for the partial credit.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2011/06/04/google-code-jam-2011-round-2/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Google Code Jam 2011 Round 1</title>
		<link>http://www.forthgo.com/blog/2011/05/24/google-code-jam-2011-round-1/</link>
		<comments>http://www.forthgo.com/blog/2011/05/24/google-code-jam-2011-round-1/#comments</comments>
		<pubDate>Wed, 25 May 2011 01:24:43 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[Code]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/?p=473</guid>
		<description><![CDATA[Round 1 of the Google Code Jam 2011 contest was last week-end. I stayed up Friday night for the first of three sessions for round 1 qualification. The top 1000 in each two-and-a-half-hour session advance to round 2. I was &#8230; <a href="http://www.forthgo.com/blog/2011/05/24/google-code-jam-2011-round-1/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p><a href="http://code.google.com/codejam/contest/dashboard?c=1145485#s=a">Round 1</a> of the <a href="http://code.google.com/codejam/">Google Code Jam</a> 2011 contest was last week-end. I stayed up Friday night for the first of three sessions for round 1 qualification. The top 1000 in each two-and-a-half-hour session advance to round 2. I was fortunate to end up around 200<sup>th</sup>, so I didn&#8217;t have to try the other sessions after all. I don&#8217;t know how many competitors there were, but there were 3100 who solved at least one problem correctly.</p>
<p>There were three problems, each with a small and large challenge test cases. The first problem was relatively easy, and basically boiled down to computing greatest common denominators to reduce fractions. I used a fraction class I had from <a href="http://projecteuler.net/">Project Euler</a> work, which made things even simpler. That got me 20 points in under 20 minutes, which turns out was already good enough to place around #640 in the final scores. Time is used for tie-breaking, and there were about 1500 partipants with 20 points.</p>
<p>The second problem was worth 30 points but had a very long description, so I skipped it. It looked interesting reading it later, but I wasn&#8217;t confident about boiling down all that prose correctly under time pressure. The problem was basically to find the hardest word(s) for someone to guess in hangman, given the guesser&#8217;s letter-picking order.</p>
<p>The third problem was the hardest and worth 50 points. You had to basically find the maximum score for a solitaire card game, given the order of cards in the deck. I thought it would be a simple <a href="http://en.wikipedia.org/wiki/Dynamic_programming">dynamic programming</a> solution, but the parameterization I chose was obviously not optimal. I included the current cards in the hand as part of the state, but with up to 80 cards in play, there could be a disastrous 2<sup>80</sup> possible states. After several tries, I was able to add enough tree-pruning to my code to solve the small test cases and get 15 points, but I never solved the large test case which included more pathological card sequences, defeating my pruning logic.</p>
<p>As a consolation prize, my code did trigger an internal JVM error at one point:</p>
<p><code>*** java.lang.instrument ASSERTION FAILED ***: "!errorOutstanding" with message can't create name string at ../../../src/share/instrument/JPLISAgent.c line: 769</code></p>
<p><strong><em>Update</em></strong>: Turns out my parameterization was OK, but I had bugs in the pruning logic.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2011/05/24/google-code-jam-2011-round-1/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Google Code Jam 2011 Qualification</title>
		<link>http://www.forthgo.com/blog/2011/05/09/google-code-jam-2011-qualification/</link>
		<comments>http://www.forthgo.com/blog/2011/05/09/google-code-jam-2011-qualification/#comments</comments>
		<pubDate>Tue, 10 May 2011 00:31:12 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[Code]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/?p=466</guid>
		<description><![CDATA[I advanced through the qualification round for the Google Code Jam 2011 over the week-end. It was a relatively low stress format allowing 24 hours to solve 8 problems, with only about 3 successful answers needed to move to the &#8230; <a href="http://www.forthgo.com/blog/2011/05/09/google-code-jam-2011-qualification/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>I advanced through the <a title="Qualification Round Problems" href="http://code.google.com/codejam/contest/dashboard?c=975485#">qualification round</a> for the Google Code Jam 2011 over the week-end. It was a relatively low stress format allowing 24 hours to solve 8 problems, with only about 3 successful answers needed to move to the next round. There were really 4 problems, but each one had two input sets to solve, one small and one large.</p>
<p>The first two problems were easy &#8212; basically just seeing if you could carefully convert the prose instructions into code. The third problem required a little bit of math insight to reduce the simplistic O(2<sup>n</sup>) solution to O(n). I got those three done, but it still took a few hours, which would not be good enough for future rounds where time is more constrained.</p>
<p>The fourth problem, <a href="http://code.google.com/codejam/contest/dashboard?c=975485#s=p3">GoroSort</a>, was pretty fun but required a little more thinking than I could put together. Basically, the problem is to sort a list of the first n integers by randomly permuting a subset of your choice. Because of the randomness, the answer is the expected number of permute operations to six decimal places. Fortunately, the problem statement included an example that suggested cycles should be sorted separately. I worked on a recursive solution to iterate through the possible cycle combinations (equivalent to <a href="http://en.wikipedia.org/wiki/Partition_(number_theory)">integer partitions</a>) resulting from a random permutation while weighting each one by its probability, but I didn&#8217;t get a successful submission.</p>
<p>Turns out my logic was good, but my probability formula was bad (which I should have realized since the total for all partitions was greater than 1). The next day I <a href="http://math.stackexchange.com/questions/37860/number-of-permutations-with-a-given-partition-of-cycle-sizes">posed the question</a> to the <a href="http://math.stackexchange.com/">Mathematics StackExchange</a> site and got a quick answer, which at least let me verify my logic (and learn more about combinatorial counting).</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2011/05/09/google-code-jam-2011-qualification/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Fast Factoring for 64-bit Integers</title>
		<link>http://www.forthgo.com/blog/2008/10/19/fast-factoring-for-64-bit-integers/</link>
		<comments>http://www.forthgo.com/blog/2008/10/19/fast-factoring-for-64-bit-integers/#comments</comments>
		<pubDate>Sun, 19 Oct 2008 18:57:57 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[Code]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Math]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/?p=269</guid>
		<description><![CDATA[Some of the Project Euler problems involve factoring numbers which are either large or small depending on your perspective. Problems are generally limited to 64-bit integers (about 18 digits) which are big numbers for most of us, but in the &#8230; <a href="http://www.forthgo.com/blog/2008/10/19/fast-factoring-for-64-bit-integers/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>Some of the <a href="http://www.projecteuler.com/">Project Euler</a> problems involve factoring numbers which are either large or small depending on your perspective. Problems are generally limited to 64-bit integers (about 18 digits) which are big numbers for most of us, but in the field of factorization those numbers are terribly small compared to the 100+ digit numbers security protocols deal with. Most advanced methods deal with optimizing the factoring of those huge numbers and don&#8217;t mind significant amount of overhead, but I want to know what&#8217;s fastest for 64-bit integers.</p>
<p>To find out, I ran some tests on some variations on three basic, low-overhead methods: Trial Division, <a href="http://en.wikipedia.org/wiki/Fermat%27s_factorization_method">Fermat&#8217;s method</a>, and <a href="http://en.wikipedia.org/wiki/Pollard_rho">Pollard&#8217;s Rho method</a>. All of these take a long time if the number being factored is actually prime, so it&#8217;s worthwhile to add in a fourth component which is a Miller-Rabin primality check. Here are my timing results for 400,000 random 64-bit integers. Actually, only the first test uses 400,000 numbers since I limited each test to 1 hour and extrapolated beyond that.</p>
<table>
<tr>
<th align="right">Seconds</th>
<th>Method</th>
</tr>
<tr>
<td align="right">811</td>
<td>Rho + Trial Division + MR</td>
</tr>
<tr>
<td align="right">6359</td>
<td>Fermat + Trial Division + MR</td>
</tr>
<tr>
<td align="right">6393</td>
<td>Trial Division + MR after each factor found</td>
</tr>
<tr>
<td align="right">29397</td>
<td>Trial Division +MR at start</td>
</tr>
<tr>
<td align="right">71195</td>
<td>Trial Division without MR</td>
</tr>
</table>
<p>I was really surprised at how well the Rho method worked in practice. It&#8217;s a probabilistic method that&#8217;s basically like trial division except it chooses numbers at random instead of sequentially. However, the &#8220;random&#8221; generator uses a polynomial such that lots of the values can be tested at once using some fancy number theory.</p>
<p>Fermat&#8217;s Method works best when there are two divisors near &radic;n, which apparently doesn&#8217;t happen very often.  Here is my Rho code, which is adapted from some pseudocode in a <a href="http://www.gamedev.net/community/forums/topic.asp?topic_id=279283">gamedev forum thread</a>.</p>
<p>[sourcecode language='java']   long rhoFactor(long n, int c, int max) {<br />
        int check = 10;<br />
        long x1 = 2;<br />
        long x2 = 4 + c;<br />
        long range = 1;<br />
        long product = 1;<br />
        int terms = 0;</p>
<p>        for (int i = 0; i < max; i++) {<br />
            for (int j = 0; j < range; j++) {<br />
                x2 = (squareMod(x2, n) + c) % n;<br />
                long next = multiplyMod(product, Math.abs(x1 - x2), n);<br />
                if (next == 0) {<br />
                    return Math.max(gcd(product, n), gcd(Math.abs(x1 - x2), n));<br />
                }<br />
                else if (++terms == check || j == range - 1) {<br />
                    long g = gcd(next, n);<br />
                    if (g > 1)<br />
                        return g;<br />
                    product = 1;<br />
                    terms = 0;<br />
                }<br />
                else<br />
                    product = next;<br />
            }</p>
<p>            x1 = x2;<br />
            range *= 2;<br />
            for (int j = 0; j < range; j++) {<br />
                x2 = (squareMod(x2, n) + c) % n;<br />
            }<br />
        }<br />
        return 1;<br />
    }<br />
[/sourcecode]</p>
<p>For the parameters, I used small odd numbers for c, the polynomial constant term, and 16 &#8211; 20 for max which limits the generated values at around 2^max. If the factorization fails, I increase c by 2 and try again. For max = 16, it failed to find a factor about once for every 10,000 numbers and never failed twice in my tests. And those numbers had already had any small factors (less than about 50,000) removed with trial division.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2008/10/19/fast-factoring-for-64-bit-integers/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Xcode Non-Distributed Builds</title>
		<link>http://www.forthgo.com/blog/2008/03/21/xcode-non-distributed-builds/</link>
		<comments>http://www.forthgo.com/blog/2008/03/21/xcode-non-distributed-builds/#comments</comments>
		<pubDate>Fri, 21 Mar 2008 13:39:51 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[Code]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/2008/03/21/xcode-non-distributed-builds/</guid>
		<description><![CDATA[One of my hobbies since buying an 8-core Mac Pro is to actually make use of all of the processing power. So far I haven&#8217;t had much success. And, of course, the web and disk are not any faster, so &#8230; <a href="http://www.forthgo.com/blog/2008/03/21/xcode-non-distributed-builds/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>One of my hobbies since buying an 8-core Mac Pro is to actually make use of all of the processing power. So far I haven&#8217;t had much success. And, of course, the web and disk are not any faster, so the extra cores don&#8217;t do much good in general.</p>
<p>The only app I use that&#8217;s really built for that kind of thing is <a href="http://developer.apple.com/tools/xcode/">Xcode</a>, which will spawn off separate compiler threads in parallel. However, I wasn&#8217;t seeing more the two cores busy when compiling a large project, though Xcode claimed to be working on 8 files at a time. I was thinking that disk or memory constraints were the problem, but it turned out to be a configuration issue. </p>
<p><img src='http://www.forthgo.com/blog/wp-content/uploads/2008/03/monitor8.png' alt='CPU Monitor of Mac Pro' align='right' hspace='4'/>At some point in the past, I had innocently turned on the Distributed Builds option, which is meant for distributing tasks to other machines on a local network. However, a side effect is that the compiling is throttled, presumably with thread priorities, so the build is more of a background activity. Turning off Distributed Builds gets all 8 local cores working in parallel.</p>
<p>Now I just need to get my own programs to use those cores&#8230;</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2008/03/21/xcode-non-distributed-builds/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>XML Schema Type Tables and Substitution Groups</title>
		<link>http://www.forthgo.com/blog/2008/02/10/xml-schema-comments/</link>
		<comments>http://www.forthgo.com/blog/2008/02/10/xml-schema-comments/#comments</comments>
		<pubDate>Sun, 10 Feb 2008 13:12:39 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[XML]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/2008/02/10/xml-schema-comments/</guid>
		<description><![CDATA[The XML Schema 1.1 was already running behind when I left the Working Group in 2004, and it&#8217;s still a work in progress. Though I no longer write XML tools, I try to keep up with the group&#8217;s activities and &#8230; <a href="http://www.forthgo.com/blog/2008/02/10/xml-schema-comments/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>The <a href="http://www.w3.org/XML/Schema">XML Schema 1.1</a> was already running behind when I left the Working Group in 2004, and it&#8217;s still a work in progress. Though I no longer write XML tools, I try to keep up with the group&#8217;s activities and provide hopefully useful comments to public working drafts. However, knowing the WG is so far behind schedule, I&#8217;m hesitant to make too many official comments since each comment must be addressed by the group, adding to the delay.</p>
<p>Many of my comments have been resolved recently in a relative flurry of activity. (The <a href="http://lists.w3.org/Archives/Public/www-xml-schema-comments/">comment archive</a> shows more activity last month than any previous three month period.) When a comment is resolved, the original poster can (silently) accept the resolution or appeal to the W3C director. I disagreed with the resolution of my comment on <a href="http://www.w3.org/Bugs/Public/show_bug.cgi?id=5079">type tables and substitution groups</a>, but just registered my dissent and closed it anyway rather than appeal &#8212; I trust the working group&#8217;s expertise over my casual interest.</p>
<p>Substitution groups have always been questionable in my mind. I&#8217;d prefer <a href="http://www.w3.org/TR/xmlschema-11-req/#N4001F6">typed wildcards</a> or, at least, an opt-in mechanism rather than opt-out for substitution groups to limit their unintended use.</p>
<p>Type tables is a big feature added late in the game and doesn&#8217;t seem to interact well with substitution groups. Type tables allow alternative types to apply to an element based on its context, such as an attribute value. I thought such context-based constraints should be in a separate layer, as is done with <a href="http://www.schematron.com/">Schematron</a>, but it seems like half the schema-dev questions are about how to impose such constraints within XML Schema, so I can understand why the Working Group would want to add it.</p>
<p>The problem, as I see it, is that type alternatives live as element declaration properties rather than within the type hierarchy. Substitution group members must have types in proper derivation relationships, but that only applies to the declared types, not the alternatives types. So combining type tables with substitution groups can break the spirit of the derivation hierarchy, if not the letter of it.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2008/02/10/xml-schema-comments/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Updated Matrix Multiply Times</title>
		<link>http://www.forthgo.com/blog/2007/10/01/updated-matrix-multiply-times/</link>
		<comments>http://www.forthgo.com/blog/2007/10/01/updated-matrix-multiply-times/#comments</comments>
		<pubDate>Mon, 01 Oct 2007 21:33:54 +0000</pubDate>
		<dc:creator>xan</dc:creator>
				<category><![CDATA[Code]]></category>
		<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://www.forthgo.com/blog/2007/10/01/updated-matrix-multiply-times/</guid>
		<description><![CDATA[I finally got around to running my matrix multiply microbenchmarks on Windows as well as Mac. Here&#8217;s the summary of times on Mac OS X and Windows XP on the same Mac Book Pro. 200&#215;200 Matrix Multiply times in milliseconds &#8230; <a href="http://www.forthgo.com/blog/2007/10/01/updated-matrix-multiply-times/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>I finally got around to running my <a href="http://www.forthgo.com/blog/2007/06/21/microbenchmark-on-java-and-c-matrix-multiplication/">matrix multiply microbenchmarks</a> on Windows as well as Mac. Here&#8217;s the summary of times on Mac OS X and Windows XP on the same Mac Book Pro.</p>
<table border = "1" cellpadding ="1">
<caption>200&#215;200 Matrix Multiply times in milliseconds</caption>
<thead>
<tr>
<th colspan="2">Mac OS X</th>
<th colspan="2">Windows XP</th>
</tr>
<tr>
<th>Java 1.5</th>
<th>C</th>
<th>Java 1.6</th>
<th>C</th>
</tr>
</thead>
<tfoot>
<tr>
<td>ms</td>
<td>ms</td>
<td>ms</td>
<td>ms</td>
</tr>
</tfoot>
<tbody>
<tr>
<td>22</td>
<td>11.2</td>
<td>12.2</td>
<td>12.7</td>
</tr>
</tbody>
</table>
<p>(Though not a big table, I&#8217;m using it to test out support for HTML 4 (ca. 1999) table elements like <code>THEAD</code>.)</p>
]]></content:encoded>
			<wfw:commentRss>http://www.forthgo.com/blog/2007/10/01/updated-matrix-multiply-times/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

