<?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>Booleangate</title>
	<atom:link href="http://blog.booleangate.org/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.booleangate.org</link>
	<description>Blog of Wonders</description>
	<lastBuildDate>Thu, 29 Apr 2010 21:02:50 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.6</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Semicolon insertion finally caught me</title>
		<link>http://blog.booleangate.org/development/javascript/semicolon-insertion-finally-caught-me/</link>
		<comments>http://blog.booleangate.org/development/javascript/semicolon-insertion-finally-caught-me/#comments</comments>
		<pubDate>Fri, 09 Apr 2010 02:14:50 +0000</pubDate>
		<dc:creator>Justin</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[bugs]]></category>
		<category><![CDATA[dammit]]></category>
		<category><![CDATA[semicolon insertion]]></category>

		<guid isPermaLink="false">http://blog.booleangate.org/?p=38</guid>
		<description><![CDATA[While debugging a caching class today, I realized that I had finally been caught by semicolon insertion.
Here&#8217;s the original code cut from a larger object literal
isValid: function(hash) {
    return
        // Is cached AND
        typeof this.entries[hash] != "undefined" &#38;&#38;
 [...]]]></description>
			<content:encoded><![CDATA[<p>While debugging a caching class today, I realized that I had finally been caught by semicolon insertion.</p>
<p>Here&#8217;s the original code cut from a larger object literal</p>
<pre>isValid: function(hash) {
    return
        // Is cached AND
        typeof this.entries[hash] != "undefined" &amp;&amp;
        // Cache doesn't expire (e.g.: -1) OR hasn't expired yet
        (this.entries[hash].expires &lt; 0 || this.entries[hash].expires &gt; new Date().getTime());
}</pre>
<p>After about 10 minutes and a gratuitous amount of debug output, I realized that this function was returning `undefined`.  &#8220;Nonsense,&#8221; I said to myself, &#8220;it&#8217;s returning a boole&#8230;wha&#8230;wait. Dammit.&#8221;</p>
<p>In my effort to document and format at the same time, I dropped the expression to the next line after the `return`.  Being that `return` by itself on a line is a complete and valid expression, JavaScript&#8217;s automatic semicolon did its thing and ended the statement there and my conditional expression was never evaluated.</p>
<p>Wrapping the whole conditional expression in parenthesis fixed the problem by invalidating the `return` line as a whole statement.</p>
<pre>isValid: function(hash) {
    return (
        // Is cached AND
        typeof this.entries[hash] !== "undefined" &amp;&amp;
        // Cache doesn't expire (e.g.: -1) OR hasn't expired yet
        (this.entries[hash].expires &lt; 0 || this.entries[hash].expires &gt; new Date().getTime())
    );
}</pre>
<p>Let that be a lesson to us all. I suppose it was bound to happen at some point.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.booleangate.org/development/javascript/semicolon-insertion-finally-caught-me/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Learning Python with Google, Day 1</title>
		<link>http://blog.booleangate.org/development/python/learning-python-with-google-python-class-strings/</link>
		<comments>http://blog.booleangate.org/development/python/learning-python-with-google-python-class-strings/#comments</comments>
		<pubDate>Mon, 22 Mar 2010 01:03:46 +0000</pubDate>
		<dc:creator>Justin</dc:creator>
				<category><![CDATA[Python]]></category>
		<category><![CDATA[functions]]></category>
		<category><![CDATA[learning]]></category>
		<category><![CDATA[strings]]></category>

		<guid isPermaLink="false">http://blog.booleangate.org/?p=19</guid>
		<description><![CDATA[If programmers can agree on one thing, I think it&#8217;s that new languages are good to learn.  And why not?  Exposing yourself to new ideas helps you grow and refine your skills as a professional or hobbyist as the case may be.  Practically speaking, it gives you a larger skill set which can make you [...]]]></description>
			<content:encoded><![CDATA[<p>If programmers can agree on one thing, I think it&#8217;s that <em>new languages are good to learn</em>.  And why not?  Exposing yourself to new ideas helps you grow and refine your skills as a professional or hobbyist as the case may be.  Practically speaking, it gives you a larger skill set which can make you more hire-able and might even increase your pay.  But all that&#8217;s besides the point:  I want to learn something new</p>
<p>So after some farting around with a couple of different candidates, I&#8217;ve decide to learn me some Python.  The runners up were Haskel and node.js.  Although incredibly interesting and a whole new way of thinking (functional vs procedural, that is), Haskel doesn&#8217;t seem like it would be immediately useful or practical.  As for node.js, since I already know JavaScript well, it&#8217;s more of just learning an API rather than a new language, which doesn&#8217;t seem like much of a stretch, but I&#8217;ll probably still tinker with it.<span id="more-19"></span></p>
<p>So Python it is, and I have two main motivations for choosing it:</p>
<ol>
<li>It&#8217;s a respectable language that doesn&#8217;t get nearly the flack that something like PHP (which I still enjoy) gets.</li>
<li>Threading.  As I look more and more toward automation, this becomes more and more valuable.</li>
</ol>
<p>It&#8217;s also been a really long time since I&#8217;ve picked up a new language.  New technologies, sure, but I haven&#8217;t started a new language since 2002 when I transitioned from C++ into PHP and JavaScript.  As such, any comparisons that I may draw, will likely be against those languages.</p>
<p>Another motivator for getting my ass in gear on this endeavor is <a href="http://code.google.com/edu/languages/google-python-class/" target="_blank">Google&#8217;s Python class</a>.  Having randomly stumbled upon it, everything has been put in motion.</p>
<p>Today, I got started with the <a href="http://code.google.com/edu/languages/google-python-class/introduction.html" target="_blank">introduction</a> and chapter on <a href="http://code.google.com/edu/languages/google-python-class/strings.html" target="_blank">strings</a>.  Here&#8217;s the solutions that I came up with for the string exercises.  Python gurus feel free to offer a critique, but realize that the techniques that I&#8217;ve been exposed to are limited to the aforementioned chapters and a few cursory searches.</p>
<h3>Basic exercise: string1.py</h3>
<pre># A. donuts
# Given an int count of a number of donuts, return a string
# of the form 'Number of donuts: &lt;count&gt;', where &lt;count&gt; is the number
# passed in. However, if the count is 10 or more, then use the word 'many'
# instead of the actual count.
# So donuts(5) returns 'Number of donuts: 5'
# and donuts(23) returns 'Number of donuts: many'
def donuts(count):
  return "Number of donuts: %s" % (count if count &lt; 10 else "many") 

# B. both_ends
# Given a string s, return a string made of the first 2
# and the last 2 chars of the original string,
# so 'spring' yields 'spng'. However, if the string length
# is less than 2, return instead the empty string.
def both_ends(s):
  if len(s) &lt; 2:
    return ""
  return s[:2] + s[-2:]

# C. fix_start
# Given a string s, return a string
# where all occurences of its first char have
# been changed to '*', except do not change
# the first char itself.
# e.g. 'babble' yields 'ba**le'
# Assume that the string is length 1 or more.
# Hint: s.replace(stra, strb) returns a version of string s
# where all instances of stra have been replaced by strb.
def fix_start(s):
  return s[0:1] + s[1:].replace(s[0], '*')

# D. MixUp
# Given strings a and b, return a single string with a and b separated
# by a space '&lt;a&gt; &lt;b&gt;', except swap the first 2 chars of each string.
# e.g.
#   'mix', pod' -&gt; 'pox mid'
#   'dog', 'dinner' -&gt; 'dig donner'
# Assume a and b are length 2 or more.
def mix_up(a, b):
  return b[0:2] + a[2:] + " " + a[0:2] + b[2:]</pre>
<h3>Basic exercise: string2.py</h3>
<pre># D. verbing
# Given a string, if its length is at least 3,
# add 'ing' to its end.
# Unless it already ends in 'ing', in which case
# add 'ly' instead.
# If the string length is less than 3, leave it unchanged.
# Return the resulting string.
def verbing(s):
  if len(s) &lt; 3:
    return s
  return s + 'ing' if s[-3:] != 'ing' else s +'ly'

# E. not_bad
# Given a string, find the first appearance of the
# substring 'not' and 'bad'. If the 'bad' follows
# the 'not', replace the whole 'not'...'bad' substring
# with 'good'.
# Return the resulting string.
# So 'This dinner is not that bad!' yields:
# This dinner is good!
def not_bad(s):
  ni = s.find("not")
  nb = s.find("bad")

  if ni &gt; -1 and nb &gt; ni:
    return s[0:ni] + "good" + s[nb+3:]
  return s

# F. front_back
# Consider dividing a string into two halves.
# If the length is even, the front and back halves are the same length.
# If the length is odd, we'll say that the extra char goes in the front half.
# e.g. 'abcde', the front half is 'abc', the back half 'de'.
# Given 2 strings, a and b, return a string of the form
#  a-front + b-front + a-back + b-back
def front_back(a, b):
  a = half(a)
  b = half(b)
  return a[0] + b[0] + a[1] + b[1]

def half(s):
  l = len(s)
  m =  l / 2

  if l % 2 == 1:
    m += 1

  return [s[:m], s[m:]]</pre>
<p>So there you have it, my first dive into Python.  Let me know what you think of my solutions and I&#8217;ll be sure to post my progress as I continue.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.booleangate.org/development/python/learning-python-with-google-python-class-strings/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>The Developer Who Cried &#8220;Done!&#8221;</title>
		<link>http://blog.booleangate.org/development/the-developer-who-cried-done/</link>
		<comments>http://blog.booleangate.org/development/the-developer-who-cried-done/#comments</comments>
		<pubDate>Mon, 07 Jul 2008 18:00:36 +0000</pubDate>
		<dc:creator>Justin</dc:creator>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[Management]]></category>
		<category><![CDATA[client projects]]></category>
		<category><![CDATA[coworker projects]]></category>
		<category><![CDATA[development cycle]]></category>
		<category><![CDATA[pit falls]]></category>
		<category><![CDATA[progamming cycle]]></category>
		<category><![CDATA[project appraisal]]></category>
		<category><![CDATA[project management]]></category>
		<category><![CDATA[solutions]]></category>
		<category><![CDATA[specifications]]></category>
		<category><![CDATA[thinking ahead]]></category>
		<category><![CDATA[understanding problems]]></category>

		<guid isPermaLink="false">http://blog.booleangate.org/?p=12</guid>
		<description><![CDATA[Whether it&#8217;s an internal or external project, for coworkers or clients, the trap of being the boy who cried &#8220;wolf&#8221;, or in this case, the developer who cried &#8220;done,&#8221; is an easy one to fall into.  The issue here, besides an elongated development time, is that this trap cuts at our credibility as programmers, [...]]]></description>
			<content:encoded><![CDATA[<p>Whether it&#8217;s an internal or external project, for coworkers or clients, the trap of being the <em>boy who cried &#8220;wolf&#8221;</em>, or in this case, the <em>developer who cried &#8220;done,&#8221;</em> is an easy one to fall into.  The issue here, besides an elongated development time, is that this trap cuts at our credibility as programmers, even—and especially—when the circumstances are out of our hands.  If you say it&#8217;s done,  it&#8217;d damn well better be done.  So, to avoid such an incredulous rap, try following these steps to make sure that projects actually get completed on time, the first time.<span id="more-12"></span></p>
<h2>Understanding the problem</h2>
<p>To solve any problem, you must first <em>understand </em>the problem.  As programmers, we should all know this, as it is our business to solve problems.  However, it&#8217;s not always clear to the client or coworker what their problem really is (although I&#8217;m sure we can point out a few).  In order to <em>finish something once</em>, and to avoid that ridiculous state of being <em>finished finishing</em>, it&#8217;s important to have a solid understanding of the problem, and to be able to answer the &#8220;Five What&#8217;s.&#8221;</p>
<ul>
<li>What&#8217;s the goal</li>
<li>What&#8217;s needed</li>
<li>What&#8217;s <em>not </em>needed</li>
<li>What can be done with other, existing solutions</li>
<li>What does the client/coworker expect</li>
</ul>
<p>First off, <em>what&#8217;s the goal?</em> This is deceptively simple, and answers that smack like, &#8220;to make a website,&#8221; are just begging the question.  &#8220;To make a website to increase company exposure and generate sales from the Internet market,&#8221; is a real answer, and the type we&#8217;re after.  Be sure to get at specifics, as that is what this whole exercise is about.</p>
<p>Second and thirdly, <em>what is </em>and <em>what is not needed? </em>If the goal of making said website is to drive sales and increase exposure, things like a solid SEO campaign and a web store are needed. But what about a neat-o staff section? That depends on the company and their product. How about customer tracking for Internet sales?  I would say so.  A contact form?  Most definitely.  Weather widgets?  Bite me.  Be realistic with each feature requested.  Is it practical and useful, will it be used more than once, will anyone that&#8217;s not a local customer &#8220;get it&#8221; (i.e.: beware of gimmicks), is it worth the time to develop?  These are the types of questions that you should ask yourself and your client/coworker when determining the project&#8217;s feature-set.</p>
<p>And what about <em>what can be done with other, existing solutions?</em> Don&#8217;t forget that there are a lot of out-of-the-box solutions for a wicked variety of things. However, if it will take away from your paycheck and the client can afford it, then as long as it meets the due date, I wholeheartedly encourage your to reinvent the wheel, the pencil, and to make better spatulas until the cows come home. But, for example, if you&#8217;re working on some internal project, chances are there may already be another tool that does just what your coworker is asking for.  Use it, modify it if necessary, and spend your time doing things that actually need to get done (like reading <a title="Reddit's programming feed" href="http://reddit.com/r/programming" target="_blank">reddit</a>).</p>
<p>Lastly, <em>what does the client/coworker expect?</em> This &#8220;what&#8221; leads into my next point, because believe me, we aren&#8217;t out of the woods yet.  You aren&#8217;t the only one that needs to understand the problem. We must also make sure that the client/coworker knows what&#8217;s up, and that we&#8217;re all on the same page.</p>
<h2>Understanding the problem <em>with the user</em></h2>
<p>It may seem a bit redundant, but it&#8217;s true.  Now that you&#8217;ve got all the pieces put together in your head (or on a white board), make sure that the client/coworker understands the problem to the same extent that you do.   Often times, you may find that while you thought that you had a firm grasp on the task at hand, the client/coworker was saying one thing but trying to describe something completely different.  Chances are the client/coworker is not a programming-savvy person, and that&#8217;s okay.  The issue is that while a programmer would sit down and think about all the necessary features of some (hypothetical) admin tool, as well as, and more importantly, what might be needed in the future, the client/coworker will probably never try to look beyond their immediate needs.  This leads to the painfully familiar situation of  being a wee few hours away from finishing this great new tool, when suddenly it needs to have a translation system, tag clouds, region specific data, oven mitts, and an RSS feed to boot.</p>
<p>It&#8217;s important that you explain to the client/coworker how you understand their problem, the way you see their vision for this project, what you&#8217;ve understood as they&#8217;ve explained it to you. Explain to them what you&#8217;ll do—not how you&#8217;ll do it—and why the features that you will create are necessary.  No one will be impressed with your technical jargon if they don&#8217;t know what you&#8217;re talking about, so unless necessary or well accepted, during all of this explanation be sure to spare the technical details, as it normally only muddles the matter further.</p>
<h2>Thinking ahead</h2>
<p>As mentioned earlier, clients/coworkers will hardly ever look beyond their immediate needs for a given project.  It&#8217;s because of this lack of thinking ahead that clients/coworkers are prone to that we must reiterate the<em> </em>problem<em> and its solution</em> to the them in terms that they can understand, while even going as far to speculate about additional features that we think may be necessary now or in the near future.  It has often been the case in my experience that while relating my own speculations for the project and my understanding of how the whole shebang is going to work, that many new-to-me but incredibly important features rise to surface.</p>
<h2>Multiple perspectives</h2>
<p>Today&#8217;s topic was spurred from an unfortunate situation that I recently fell into where a project at work has been unduly dragging on for well over two months.  Worse yet, it&#8217;s still not done.  I&#8217;ll take responsibility for that, but not for a lack of programming aptitude.  Rather, I realized today that this whole mess arose out of underestimation and a lack of understanding of the <em>whole picture</em> as I&#8217;ve layed out here in this article.  The real leason here is that, as developers, we must understand the whole picture from <em>multiple perspectives</em>: our own, how the client/coworker see it, and how the end-user sees it—but that&#8217;s a whole other story.  More than that, we must also lead the client/coworker to the same understanding so that we are all on the same page, and to avoid suprises and curveballs further down the project timeline.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.booleangate.org/development/the-developer-who-cried-done/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>PHP Benchmarking: Arrays and Iteration (Part 1)</title>
		<link>http://blog.booleangate.org/development/php/php-benchmarking-arrays-and-iteration-part-1/</link>
		<comments>http://blog.booleangate.org/development/php/php-benchmarking-arrays-and-iteration-part-1/#comments</comments>
		<pubDate>Sun, 06 Jul 2008 18:00:32 +0000</pubDate>
		<dc:creator>Justin</dc:creator>
				<category><![CDATA[Optimization]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[arrays]]></category>
		<category><![CDATA[benchmarking]]></category>
		<category><![CDATA[iteration]]></category>
		<category><![CDATA[loops]]></category>
		<category><![CDATA[speed]]></category>

		<guid isPermaLink="false">http://blog.booleangate.org/?p=6</guid>
		<description><![CDATA[Author&#8217;s note: This article was originally posted at Frye / Wiles, and has been re-posted here for consolidation.
As a programming department, it is always our goal to code in such a manner that makes use of methods that provide, on average, the fastest execution times. In today&#8217;s discussion, we&#8217;ll be testing the many different ways [...]]]></description>
			<content:encoded><![CDATA[<blockquote><p><em class="notice" title="2008-07-06">Author&#8217;s note: This article was originally posted at <a title="Original posting" rel="nofollow" href="http://blog.fryewiles.com/development/03-02-2008/php-benchmarking-arrays-and-iteration-part-1" target="_blank">Frye / Wiles</a>, and has been re-posted here for consolidation.</em></p></blockquote>
<p>As a programming department, it is always our goal to code in such a manner that makes use of methods that provide, on average, the fastest execution times. In today&#8217;s discussion, we&#8217;ll be testing the many different ways to process and interact with arrays in PHP in the first of three main areas: reading, modifying, and reconstructing. <span id="more-6"></span></p>
<p>We&#8217;ve got some ground work to establish today, so modifying and reconstructing will be saved for later. Also, as time goes on, we&#8217;ll be talking about many different areas of PHP (like functions versus objects and static methods). But, for today, arrays have been chosen as our first point of discussion because, at least in my experience, they are more than ubiquitous when it comes to developing dynamic or content-driven applications, and dealing with large amounts of data (e.g.: user lists, pages, resources of all kinds, etc).</p>
<h3>Preface</h3>
<p>As PHP is an interpreted language, and all machines/OS&#8217;s/configurations/processors are not created equal, please note that results will vary from machine to machine. My configuration for these tests are as follows: AMD Athlon 64 X2 Dual core 6000+, 2 GB Kingston PC-6400, Windows XP sp2.</p>
<h3>Getting started</h3>
<p>When benchmarking, the goal is to determine the comparable <em>time percent difference</em> for a given group of methods; however, it is equally important to consider the data that being used in these test, and how it is applied. It&#8217;s best to use data that would reflect a real, or as close to real-world application as possible. We&#8217;re going to be dealing with a decent size array with 500 elements, each containing a string of 1024 bytes. In the real world, this could reflect a list of pages that we need to parse, or perhaps a list of comments to a blog post such as this one.</p>
<p>I&#8217;ve created a few generic classes to help me out with the nitty-gritty of the benchmarking process. At the end of this series on PHP-specific benchmarks, I&#8217;ll walk everyone through how to use these classes for their own tests. For today though, I&#8217;m just going to gloss over this groundwork and get on to the specific tests. Here&#8217;s how I&#8217;ve setup my test data and iteration control.</p>
<p><code>define('ITERATIONS', 10000);<br />
define('ELEMENTS' , 5000);<br />
define('VALUE_SIZE', 1024);</code></p>
<p><code>$ag = new ArrayGenerator(ELEMENTS, VALUE_SIZE);<br />
$tc = new TimeCompare();<br />
<cite>// The associative array run tests on</cite><br />
<var>$a_assoc</var> = $ag-&gt;generate(AG_TYPE_ASSOC);<br />
<cite>// The indexed array to run tests on</cite><br />
<var>$a_index</var> = $ag-&gt;generate(AG_TYPE_INDEX);<br />
</code></p>
<p><a title="Source code for these benchmarking examples" href="http://blog.booleangate.org/downloads/php/benchmarking/arrays-1.zip">Download the source code</a></p>
<p>As an extra benefit to those who download the source code, <em>ArrayGenerator </em>and all forthcoming <em>Generators </em>provide a small, mostly trivial lesson in PHP 5&#8217;s class inheritance and interface models.</p>
<p>Alright, lets get on with it.</p>
<h2>Reading arrays</h2>
<p>Right off the top of my head, whether they be associative or indexed, I can think of four different iterative structures that can be used to read through an <a title="PHP Arrays" href="http://www.php.net/types.array" target="_blank">array in PHP</a>: <em>for</em>, <em>foreach</em>, <em>list/each</em>, and <em>current/next</em>.</p>
<p>For-loops have several variants. First, we will examine the traditional form, and then we will look at more optimized versions. In our test, we&#8217;re simply going to concatenate all of our array values into a separate variable. This test exemplifies the scenario where there are several pieces of data stored in array that need to be output to the page (sans formatting for us). Here&#8217;s the code for both indexed and associative arrays.</p>
<p><em>Indexed</em><br />
<code>$t = '';<br />
for ( $i=0; $i&lt;count($a_index); $i++ ) {<br />
$t .= $a_index[$i];<br />
}</code></p>
<p><em>Associative</em><br />
<code>$t = '';<br />
$keys = array_keys($a_assoc);<br />
for ( $i=0; $i&lt;count($a_assoc); $i++ ) {<br />
$t .= $a_assoc[$keys[$i]];<br />
}</code></p>
<h4>Indexed vs. associative arrays</h4>
<table class="results-table" border="0">
<tbody>
<tr>
<th>Test</th>
<th>Time (%)</th>
<th>Total time (ms)</th>
</tr>
<tr>
<td>Traditional (index)</td>
<td>100</td>
<td>0.000000126</td>
</tr>
<tr>
<td>Traditional (assoc)</td>
<td>105</td>
<td>0.000000147</td>
</tr>
</tbody>
</table>
<p>The lesson here is to use index arrays when possible; however, this may only be applicable to for and other loops that use index counters. This may not apply to loops that use keys or other means of iteration; associative may be faster, it may be the same — we&#8217;ll find out later.</p>
<p>Now, lets be smart about our resources and move the <em>count()</em> statement outside of the loop-body and eliminate those extra <em>n</em> function calls. In general, we would write something like this.</p>
<p><em>Limit counting outside of the loop body</em><br />
<code>$limit = count($some_array);<br />
for ( $i=0; $i&lt;$limit; $i++ ) {<br />
<cite>// ... do something ...<br />
}</cite></code></p>
<p>Now, applying this method to the previous two loops, lets retest to see what, if any improvement we get. I theory, depending on how <em>count() </em>behaves, this could be quite substantial.</p>
<h4>Pre-counting the array size outside of the loop</h4>
<table class="results-table" border="0">
<tbody>
<tr>
<th>Test</th>
<th>Time (%)</th>
<th>Total time (ms)</th>
</tr>
<tr>
<td>Traditional, pre-count (index)</td>
<td>100</td>
<td>0.000000110</td>
</tr>
<tr>
<td>Traditional, pre-count (assoc)</td>
<td>106</td>
<td>0.000000117</td>
</tr>
</tbody>
</table>
<h4>Pre-counted vs. counting as part of the loop</h4>
<table class="results-table" border="0">
<tbody>
<tr>
<th>Test</th>
<th>Time (%)</th>
<th>Total time (ms)</th>
</tr>
<tr>
<td>Traditional (index)</td>
<td>115</td>
<td>0.000000126</td>
</tr>
<tr>
<td>Traditional (assoc)</td>
<td>134</td>
<td>0.000000147</td>
</tr>
<tr>
<td>Traditional, pre-count (index)</td>
<td>100</td>
<td>0.000000110</td>
</tr>
<tr>
<td>Traditional, pre-count (assoc)</td>
<td>106</td>
<td>0.000000117</td>
</tr>
</tbody>
</table>
<p>Furthermore, if we switch from the post-increment operator, to the pre-increment operator, we should also see some time improvements. The difference is that in using the post-increment operator (<em>a++</em>), a copy of the variable is made, the original value is incremented, and then that copy is returned. With pre-increment operator (<em>++a</em>), the value is incremented and then returned, cutting the process down <a title="See #34" href="http://reinholdweber.com/?p=3" target="_blank">one less step</a>. In general we would write something like this.</p>
<p><em>Pre-incrementing the loop counter</em><br />
<code>$limit = count($some_array);<br />
for ( $i=0; $i&lt;$limit; ++$i ) {<br />
<cite>// ... do something ...<br />
}</cite></code></p>
<p>This gives us the following comparison.</p>
<h4>Post vs. pre-incrementing</h4>
<table class="results-table" border="0">
<tbody>
<tr>
<th>Test</th>
<th>Time (%)</th>
<th>Total time (ms)</th>
</tr>
<tr>
<td>Traditional, pre-count (index)</td>
<td>110</td>
<td>0.000000111</td>
</tr>
<tr>
<td>Traditional, pre-count (assoc)</td>
<td>119</td>
<td>0.000000121</td>
</tr>
<tr>
<td>Traditional, pre-count, pre-increment * (index)</td>
<td>100</td>
<td>0.000000101</td>
</tr>
<tr>
<td>Traditional, pre-count, pre-increment * (assoc)</td>
<td>112</td>
<td>0.000000114</td>
</tr>
</tbody>
</table>
<p>* We&#8217;ll refer to this last version of the for-loop as an <em>optimized for-loop</em> (limit pre-counting, pre-incrementing) from now on.</p>
<p>So now that we have everyone&#8217;s favorite for-loop thoroughly smashed (<a title="Smashed it like an Idaho Potato!" href="http://phobos.apple.com/WebObjects/MZStore.woa/wa/viewAlbum?i=3689557&amp;id=3689585&amp;s=143441" target="_blank">like an Idaho potato</a>), lets move on to the other three methods for iterating over an array. In these final tests, we&#8217;ll be upping our test parameters a tad.</p>
<p><code>define('ITERATIONS', 1000000);<br />
define('ELEMENTS' , 5000);<br />
define('VALUE_SIZE', 1024);</code></p>
<p>The beauty of these final tests is that since the subscripts aren&#8217;t used, we can use the same code and just change the array names where necessary, and since we&#8217;ve spent so much time already, lets just put all the code out there straight away.</p>
<p><em>Foreach indexed/associative</em><br />
<code>$t = '';<br />
foreach ( $some_array as $value ) {<br />
$t .= $value;<br />
}</code></p>
<p><em>List/each indexed/associative</em><br />
<code>$t = '';<br />
while ( list(,$value) = each($some_array) ) {<br />
$t .= $value;<br />
}</code></p>
<p><em>Current/next indexed/associative</em><br />
<code>$t = '';<br />
$value = current($some_array);<br />
while ( $value !== false ) {<br />
$t .= $value;<br />
$value = next($some_array);<br />
}</code></p>
<p>So now that we have our code, lets take a look at our results.</p>
<table class="results-table" border="0">
<tbody>
<tr>
<th>Test</th>
<th>Time (%)</th>
<th>Total time (ms)</th>
</tr>
<tr>
<td>For, optimized (index)</td>
<td>100</td>
<td>0.0000000610</td>
</tr>
<tr>
<td>For, optimized (assoc)</td>
<td>113</td>
<td>0.0000000691</td>
</tr>
<tr>
<td>Foreach (index)</td>
<td>104</td>
<td>0.0000000637</td>
</tr>
<tr>
<td>Foreach (assoc)</td>
<td>104</td>
<td>0.0000000633</td>
</tr>
<tr>
<td>List/each (index)</td>
<td>113</td>
<td>0.0000000692</td>
</tr>
<tr>
<td>List/each (assoc)</td>
<td>111</td>
<td>0.0000000680</td>
</tr>
<tr>
<td>Current/next (index)</td>
<td>109</td>
<td>0.0000000666</td>
</tr>
<tr>
<td>Current/next (assoc)</td>
<td>108</td>
<td>0.0000000659</td>
</tr>
</tbody>
</table>
<p>Interestingly enough, it appears that in the last three methods, associative arrays seems to out-perform indexed array by a slight amount, and although we&#8217;re talking only one to two percent differences, in the grand scheme of things, it all adds up.</p>
<p>So, overall, it appears that <em>for</em> is overall the winner of this match-up. with <em>foreach</em>, <em>current/next </em>and <em>list/each</em> following successively. For associative arrays, <em>foreach </em>appears to be the definite way to go being at least 4% faster than its closest rival, <em>current/next</em>. This is good news, since <em>foreach </em>is used so commonly in almost every piece of code in PHP that I&#8217;ve ever seen. It&#8217;s easy, and the good news is: its fast; but better than that, it appears, at least from this benchmark, that it is the right choice when dealing with associative arrays.</p>
<p>That does it for <em>reading </em>arrays. In the next post we&#8217;ll discuss array <em>modification </em>and <em>reconstruction</em>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.booleangate.org/development/php/php-benchmarking-arrays-and-iteration-part-1/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>XBC: Cross-Browser Consistency</title>
		<link>http://blog.booleangate.org/development/xbc-cross-browser-consistency/</link>
		<comments>http://blog.booleangate.org/development/xbc-cross-browser-consistency/#comments</comments>
		<pubDate>Sat, 05 Jul 2008 18:00:03 +0000</pubDate>
		<dc:creator>Justin</dc:creator>
				<category><![CDATA[CSS]]></category>
		<category><![CDATA[Cross-Browser Consistency]]></category>
		<category><![CDATA[Development]]></category>
		<category><![CDATA[HTML]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[consistency]]></category>
		<category><![CDATA[cross-browser]]></category>
		<category><![CDATA[firefox]]></category>
		<category><![CDATA[functionality]]></category>
		<category><![CDATA[internet explorer (ie)]]></category>
		<category><![CDATA[libraries]]></category>
		<category><![CDATA[markup]]></category>
		<category><![CDATA[noscript]]></category>
		<category><![CDATA[operating systems]]></category>
		<category><![CDATA[resolution]]></category>
		<category><![CDATA[scalability]]></category>
		<category><![CDATA[standards]]></category>
		<category><![CDATA[support]]></category>
		<category><![CDATA[xbc]]></category>
		<category><![CDATA[xslt]]></category>

		<guid isPermaLink="false">http://blog.booleangate.org/?p=7</guid>
		<description><![CDATA[Author&#8217;s note: This article was originally posted at Frye / Wiles, and has been re-posted here for consolidation.
When we talk about topics such about CSS, JavaScript, and sometimes even certain image formats (png24, I&#8217;m looking at you), and how they render in a client&#8217;s browser, we always, or should always also consider cross-browser behavior.  [...]]]></description>
			<content:encoded><![CDATA[<blockquote><p><em class="notice" title="2008-07-05">Author&#8217;s note: This article was originally posted at <a title="Original posting" rel="nofollow" href="http://blog.fryewiles.com/design/03-10-2008/xbc-cross-browser-consistency" target="_blank">Frye / Wiles</a>, and has been re-posted here for consolidation.</em></p></blockquote>
<p>When we talk about topics such about CSS, JavaScript, and sometimes even certain image formats (png24, I&#8217;m looking at you), and how they render in a client&#8217;s browser, we always, or <em>should always</em> also consider cross-browser behavior.  This behavior entails many things: CSS rendering, the availability of CSS specific attributes, whether or not the DOM interface will be the same, general JavaScript behavior — the list goes on and on.   And, since most discussions about CSS and JavaScript (at least the ones that I am having) also concern this variable nature, I&#8217;m coining (maybe I&#8217;m the first) a new term to put all of this into a handy little phrase, &#8220;<strong>Cross-Browser Consistency</strong>,&#8221; or, in typical programmer fashion, simply, &#8220;<strong>XBC</strong>.&#8221;</p>
<p>Let&#8217;s take a brief moment  to establish a more exact meaning for this phrase.   As you may well be aware, the industry commonly talks about <em>cross-browser support</em>, so we&#8217;ll differentiate between <em>support and consistency</em>, as well as defining what <em>cross-browser</em> really means, and some other tidbits as to boot.</p>
<p><span id="more-7"></span></p>
<p>As we all know, the plethora of browsers out there leave some websites in a world of hurt as soon as you access them via an unintended environment.  Between Firefox, Safari, Opera, and all the recent incarnations of Internet Explorer, there are a myriad of issues between the different browsers and their rendering results.  Usually the discussion is focused on aesthetics and, more specifically, how the CSS may render; however, we should broaden the scope of aesthetics to look at the resolution and operating system too as they all have a hand in the end result.  And don&#8217;t forget JavaScript!  That&#8217;s always pushed off to its own thread of discussion, but I think its important that we consider it here.  So, when talk about <strong>Cross-Browser Consistency</strong>, or <strong>XBC</strong>, we&#8217;ll need to be cognizant of two main areas: <em>aesthetics</em> and <em>functionality</em>.</p>
<h2>Aesthetics</h2>
<p>Browser aesthetics is not simply limited to how HTML and CSS are rendered, the concerns of which have already been discussed at length in various articles and wont be rehashed here.  The important issue to realize is that the screen resolution and operating system that a given browser may be running in should also <em>and always </em>be considered as part of aesthetics.</p>
<h3>Resolution and scalability</h3>
<p>What happens when your site, designed for 1024&#215;786 resolution is squeezed down into 800&#215;600?  Or, what about when someone has an even larger resolution, which is more and more common nowadays, like my dual 1680&#215;1050 resolution?   I&#8217;ll tell you that I&#8217;ve seen some funny, very unintended things.  And, while these small and large resolutions may be at the extremes of the spectrum, they still entail a portion of your user base.  These issues can be handled by designing &#8220;out of the box,&#8221; which is also known as using a &#8220;fluid layout.&#8221;  We&#8217;ll discuss those some other time.</p>
<p>Have you ever considered what would happen if someone had a specific font size enforced via their browser?  In some cases, the world would very well explode; however, if we implement our designs in a way that promotes flexible dimensions rather than fixed widths, heights, alignments and so on, we can account for a reasonable amount of font size variance in either direction.  Our office standard is such that we allow for at least two font size increases (in Firefox, the hotkey is ctrl/command and +).  For example, <a title="Yahoooooooooooooooooo!" href="http://www.yahoo.com/" target="_blank">Yahoo&#8217;s home page</a> scales incredibly well.</p>
<h3><span style="color: #888888;">Operating system</span></h3>
<p>In my experience, browser image scaling and font rendering (particularly for larger text) are the two main operating system-dependent issues that I&#8217;ve run into.</p>
<p>When I view a website, and they&#8217;ve used CSS or (gasp!) HTML attributes to resize an image, I am almost 110% sure that everything will look good enough for jazz in Mac OS X.  However, load that same site in Windows XP or prior, and you&#8217;re bound to encounter the unexpected (unless you expected rough edges and other nasties).  The difference comes from the two companies&#8217; conflicting philosophies. They both think they&#8217;re right, but from a design perspective, I tend to lean toward the more visually appealing of the two, which happens in this case to be OS X.</p>
<p>When it comes to fonts, long story short: it&#8217;s better explained by someone else.  <a title="Font smoothing, anti-aliasing, and sub-pixel rendering" href="http://www.joelonsoftware.com/items/2007/06/12.html" target="_blank">Joel Spolsky</a> provides an excellent read on the differences between Windows and OS X.  One more thing to consider is that in XP (and possibly earlier versions), right out of the box clear type is <em>disabled, </em>and call it a hunch but most users would never know where, how or why to turn it on.  Yet, at the risk of being kicked out of the Apple club, I have to say that <a title="What's Wrong With Apple's Font Rendering?" href="http://www.codinghorror.com/blog/archives/000884.html" target="_blank">Vista&#8217;s font rendering with ClearType</a> is more readable than OS X.  Please don&#8217;t shoot me.</p>
<h2>Functionality</h2>
<h3>Libraries</h3>
<p><strong> </strong></p>
<p>If you&#8217;ve done much JavaScript at all, you&#8217;ve probably run into a handful of issues with some method existing in one browser and not in another.  The first thing to realize is that unless you control the end-user&#8217;s client, browser-specific, proprietary methods should never be used.  I always opt for the usage of distributed libraries, such as <a title="Prototype JavaScript framework: Easy Ajax and DOM manipulation for dynamic web applications" href="http://www.prototypejs.org/">Prototype</a>, <a title="jQuery: The Write Less, Do More, JavaScript Library" href="http://jquery.com/">jQuery</a>, et cetera to prevent these issues as much as I can.  However, it is also the case that the same method will be implemented in two different browsers yet behave differently (e.g.: innerHTML doesn&#8217;t on table and related elements in IE, et al), so it is always important to do some testing and research when necessary.</p>
<h3>OMG noscript</h3>
<p>Essentially, are you prepared to provide the same or similar functionality from the server-side as you have already provided via JavaScript?  It is important, at least in non-elitist work, to exclude as little of a potential audience as possible.  This means that we, as developers, must make certain allotments for users that don&#8217;t have or have disabled JavaScript.  Typically, it is my stance that these users either aren&#8217;t accustomed to or expecting the bells and whistles of your fantastic JavaScript du jour, so providing similar, perhaps more basic functionality via the server-side language of your choice is acceptable and suggested.</p>
<h3>XSLT</h3>
<p>Yet another issue to consider is client-side XML/XSL transformations, or more to the point: does the browser support it and will it behave as expected.  Normally, I would opt for the XSL transformations to be <a title="XSLT - On the Server" href="http://www.w3schools.com/xsl/xsl_server.asp" target="_blank">done on the server</a> as this ensures that the markup you expected to be there . . . is there.  Depending upon your server-side language, this has the added benefit of being able to import a namespace of functions from that language to be used in the XSLT as well.  A bonus in my book for sure.</p>
<h3>Tying it all together</h3>
<p>So it didn&#8217;t turn out as brief as I intended, but we&#8217;ve covered a good bit of information.  <em>Cross-Browser Consistency </em>ensures that a site&#8217;s presentation and behavior are the same.  I&#8217;m going to actually be brief now and sumeverything up.  Lists are always fun, so lets use one of those.</p>
<p><strong>Cross-Browser Consistency</strong> refers to the following:</p>
<ul>
<li><em>Aesthetics</em>
<ul>
<li>CSS support, rendering, and available attributes.</li>
<li>Resolution, fluid layout, and scalability.</li>
<li>Operating system rendering of fonts and browser-resized images.</li>
</ul>
</li>
<li><em>Functionality</em>
<ul>
<li>Distributed, common libraries are preferred over browser-specific or proprietary libraries and methods.</li>
<li>Always provide an alternative server-side means of functionality for behaviors implemented in JavaScript.</li>
<li>XSLT is typically wiser to implement on the server to ensure broader support.</li>
</ul>
</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.booleangate.org/development/xbc-cross-browser-consistency/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Now is the palette of my discontent</title>
		<link>http://blog.booleangate.org/development/html/now-is-the-palette-of-my-discontent/</link>
		<comments>http://blog.booleangate.org/development/html/now-is-the-palette-of-my-discontent/#comments</comments>
		<pubDate>Sat, 05 Jul 2008 06:39:16 +0000</pubDate>
		<dc:creator>Justin</dc:creator>
				<category><![CDATA[CSS]]></category>
		<category><![CDATA[Cross-Browser Consistency]]></category>
		<category><![CDATA[HTML]]></category>
		<category><![CDATA[color]]></category>
		<category><![CDATA[firefox]]></category>
		<category><![CDATA[images]]></category>
		<category><![CDATA[internet explorer]]></category>
		<category><![CDATA[palette]]></category>
		<category><![CDATA[rendering]]></category>

		<guid isPermaLink="false">http://blog.booleangate.org/?p=8</guid>
		<description><![CDATA[Author&#8217;s note: This article was originally posted at Frye / Wiles, and has been re-posted here for consolidation.
Today, we&#8217;re talking about color, its use on the web and how it is (in)effectively rendered cross-browser and cross-platform.When using a flat color as a background, such as is the case with the screen shot of salsa2night below, [...]]]></description>
			<content:encoded><![CDATA[<blockquote><p><em><span class="edit footnote" title="2008-07-04">Author&#8217;s note: This article was originally posted at <a title="Original posting" rel="nofollow" href="http://blog.fryewiles.com/design/10-03-2007/now-is-the-palette-of-my-discontent" target="_blank">Frye / Wiles</a>, and has been re-posted here for consolidation.</span></em></p></blockquote>
<p>Today, we&#8217;re talking about color, its use on the web and how it is (in)effectively rendered cross-browser and cross-platform.<span id="more-8"></span>When using a flat color as a background, such as is the case with the screen shot of salsa2night below, it is important to realize that if it is blending with an image, that some consideration of cross-browser rendering must be taken into account.  Windows displays color differently than Mac, IE displays color differently than Firefox, which displays color differently than Safari&#8211;even when rendered on the same machine in the same OS.</p>
<p style="text-align: center"><img src="http://blog.fryewiles.com/wp-content/uploads/2007/10/websafe-color.jpg" alt="Salsa2Night landing page" /></p>
<p>Suppose that we have the following CSS declaration for an element on our page that contains an image that should blend in with a background color</p>
<p><code>#page {<br />
background: #30899E url(image.ext) no-repeat;<br />
}</code></p>
<p>The problem is not the hex value for the color, the discrepancy is in the value of the background color in the image itself.  Here, on XP, Firefox is not agreeing with IE 6 about the image color; however, the CSS color of #30899E is being displayed consistently.</p>
<p>One way around this problem is by using IE conditional comments (which are a saving grace all to themselves, but that&#8217;s another topic) to include a style declaration or linked file to fix the background color for IE.  These are also extremely useful for fixing other CSS, and sometimes Javascript, issues in IE that are inconsistent with other browsers.</p>
<p><code>&lt;!--[if IE]&gt;<br />
&lt;link rel="stylesheet" type="text/css" media="screen" title="FW" href="/css/ie/layout.css"&gt;&lt;/link&gt;<br />
&lt;![endif]--&gt;<br />
</code></p>
<p>or</p>
<p><code>&lt;!--[if IE]&gt;<br />
&lt;style&gt;<br />
#page {<br />
background-color: #258095 !important;<br />
}<br />
&lt;/style&gt;<br />
&lt;![endif]--&gt;<br />
</code></p>
<p>This, however, doesn&#8217;t necessarily create a new problem, but <em>does not</em> remedy the entire situation in that it does no good for Safari and other browsers.  Another, separate issue is that now you have two places to make modifications to every time you update the image instead of just one, but that&#8217;s really a different topic.  If you&#8217;re market only includes IE or Firefox, then, I suppose, you can wrap it up here.  However, when that day comes that you need to support more browsers, what then?   In general, web sites aim to reach as big of an audience as available, and should, as part of that goal, strive to provide as consistent an aesthetic experience as possible.  Getting down to the point: since there are no Safari, nor for that matter, Opera conditional comments, what are we to do?  We&#8217;ve fixed things for two out of the four big players in the browser market, but now we need a more general solution that doesn&#8217;t involve copious amounts CSS hacks and gimmicks.</p>
<p>That general way of handling this color dilemma is by using <em>web safe colors </em>for the flat colors in images that will be also be painted by a CSS background color such as in the following declaration.</p>
<p><code>#page {<br />
background: #003366 url(/images/my-image.ext) no-repeat;<br />
}<br />
</code></p>
<p>Design suites worth their salt already have web safe color palettes as part of their color picking tools, so differentiating between safe and potential mis-representable colors should be a snap.  The crux of the situation here is that these palettes were chosen and generated mathematically by design-challenged programmers (hey, I can admit it), and <em>not </em>by designers.  Complaints of an over abundance of highly saturated colors and not enough of a selection of muted colors are common.</p>
<p>Adapting oneself to design within these color constraints is somewhat note-worthy, but not necessary.  Enter method three: break it <em>twice</em>.</p>
<p>The general idea here is to have two images: the image that we&#8217;ve been dealing with all along, and another, 1&#215;1 px, that is filled with the background color that we want to fill the area with that we had been originally using a CSS hex value for.  The basic idea here is to have to div elements, on within the other.  The outer div, <em>page-background</em>, will contain the 1&#215;1 px image have it tile (repeat) in the X and Y directions.  The inner div, <em>page</em>, will contain the main image as it always has, except that it will have no background color defined with it.</p>
<p><code>&lt;style&gt;<br />
#page-background {<br />
background: url(/images/my-image-background.ext);<br />
}<br />
#page {<br />
background: url(/images/my-image.ext) no-repeat;<br />
}<br />
&lt;/style&gt;<br />
&lt;div id="page-background"&gt;<br />
&lt;div id="page"&gt;&lt;/div&gt;<br />
&lt;/div&gt;<br />
</code></p>
<p>Of course, height and width must be set on the <em>page </em>element to fit my-image and whatever content is to be included, but this is the general idea.  This works because of one reason: we&#8217;re exploiting the inconsistency in the rendering of each image.  If each of these images contain the same palette, then they will be rendered the same.  Again, instead of using a CSS color value, we&#8217;re tiling a very small image that contains that color under the main image so that <em>everything is displayed the same in all browsers</em>.</p>
<p>Each of these methods for addressing the image color issue has their own draw backs: the conditional comments only work in IE and force a division of code that has to be updated in two places; the web safe color palette is limiting factor on design; and the final, <em>break it twice</em> solution has the overhead of an additional image, albeit small, as well as the extra mark-up needed to stylize and include the extra div element, which is, again, small but there nonetheless.</p>
<p>Of all of these, I prefer the use of web safe colors as it is definitely superior as far as implementation is concerned; however, when push comes to shove, using the <em>twice broken</em> or <em>break it twice</em> method will get the job done and can be, theoretically, guaranteed to work in all browsers, forever and ever, amen.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.booleangate.org/development/html/now-is-the-palette-of-my-discontent/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
	</channel>
</rss>
