Categories
Uncategorized

Build Status Interfaces

Having a continuous integration system is nice, but what’s even nicer is if that system has a really clear way of telling you whether the build is working. Last.fm weren’t happy with build status messages on the command line and went the extra mile to set up these illuminated bears:

Last.fm\'s red, yellow and green \"build bears\"

Last.fm’s Adrian Woodhead writes:

These 3 bears sit in a prominent position and watch our developer’s every move. When things are good we have a green bear gently glowing and purring, when changes are being processed a yellow bear joins the party, and if the build gets broken the growling evil red bear makes an appearance. The developer who broke things usually goes a similar shade of red while frantically trying to fix whatever was broken while the others chortle in the background.

I’ve been meaning to get back into a little hardware hacking (something I haven’t done since I was a teen) and learn how to build computer-driven gizmos like Last.fm’s bears. In the meantime, I’ll have to satisfy myself by page-slapping the development team at b5 with these images created by Big Swinging Developer

You Broke the Build!

\"You broke the build!\" graphic

“Builds on My Machine…”

\"Builds on my machine\" graphic

Where’s the Build?

\"Where\'s the build?\" graphic

Categories
Uncategorized

Enumerating Enumerable: Enumerable#each_with_index

Enumerating Enumerable

Here’s number 11 in the Enumerating Enumerable series, in which I’m trying to outdo RubyDoc.org in their documentation of Ruby’s key Enumerable module. In this article, I cover the each_with_index method.

In case you missed the earlier articles, they’re listed and linked below:

  1. all?
  2. any?
  3. collect / map
  4. count
  5. cycle
  6. detect / find
  7. drop
  8. drop_while
  9. each_cons
  10. each_slice

Enumerable#each_with_index Quick Summary

Graphic representation of the \"each_with_index\" method in Ruby\'s \"Enumerable\" module

In the simplest possible terms Think of each_with_index as a version of each that includes an extra piece of information: a number representing the current iteration’s element’s position in the collection.
Ruby version 1.8 and 1.9
Expects An optional block to receive the values from each iteration.
Returns
  • The original collection, if used with a block.
  • An Enumerator object that outputs the collection’s items and indexes, if used without a block.
RubyDoc.org’s entry Enumerable#each_with_index

Enumerable#each_with_index and Arrays

When used with on an array and given a block, each_with_index iterates through the array, passing each item in the array and the number representing its order in the array to the block. Once again, I’ll use the “Justice League” example:

justice_league = ["Aquaman", "Batman", "Black Canary", \
                  "Flash", "Green Arrow", "Green Lantern", \
                  "Martian Manhunter", "Superman", \
                  "Vixen", "Wonder Woman"]
justice_league = ["Aquaman", "Batman", "Black Canary", "Flash", "Green Arrow",
"Green Lantern", "Martian Manhunter", "Superman", "Vixen", "Wonder Woman"]

justice_league.each_with_index {|member, index| puts "#{index}: #{member}"}
=> 0: Aquaman
1: Batman
2: Black Canary
3: Flash
4: Green Arrow
5: Green Lantern
6: Martian Manhunter
7: Superman
8: Vixen
9: Wonder Woman
=> ["Aquaman", "Batman", "Black Canary", "Flash", "Green Arrow", "Green Lantern",
"Martian Manhunter", "Superman", "Vixen", "Wonder Woman"]

Note that unlike the each_cons and each_slice, each_with_index doesn’t return nil, but the original array, just like each does. each_cons and each_slice are newer methods that were introduced in Ruby 1.9; perhaps Matz and company decided that it made more sense for “each” methods to return nil from now on. each and each_with_index have return the original array as they always have, since making changes to these methods might break a lot of existing Ruby code. Hooray for those little inconsistencies that creep into every programming language!

Enumerable#each_with_index and Hashes

When used with on a hash and given a block, each_with_index iterates through the hash, converting each item in the hash into a two-element array (where the first element is the key and the second element is the corresponding value), and then passing that array and the number representing its order in the original array to the block. Once again, I’ll use the “Enterprise Crew” example:

enterprise_crew = {:captain => "Picard",
                   :first_officer => "Riker",
                   :science_officer => "Data",
                   :tactical_officer => "Worf",
                   :chief_engineer => "LaForge",
                   :chief_medical_officer => "Crusher",
                   :ships_counselor => "Troi",
                   :annoying_ensign => "Crusher",
                   :attractive_ensign => "Ro",
                   :expendable_crew_member => "Smith"}
=> {:captain=>"Picard", :first_officer=>"Riker", :science_officer=>"Data",
:tactical_officer=>"Worf", :chief_engineer=>"LaForge",
:chief_medical_officer=>"Crusher", :ships_counselor=>"Troi",
:annoying_ensign=>"Crusher", :attractive_ensign=>"Ro",
:expendable_crew_member=>"Smith"}

enterprise_crew.each_with_index {|member, index| puts "#{index}: #{member}"}
=> 0: [:captain, "Picard"]
1: [:first_officer, "Riker"]
2: [:science_officer, "Data"]
3: [:tactical_officer, "Worf"]
4: [:chief_engineer, "LaForge"]
5: [:chief_medical_officer, "Crusher"]
6: [:ships_counselor, "Troi"]
7: [:annoying_ensign, "Crusher"]
8: [:attractive_ensign, "Ro"]
9: [:expendable_crew_member, "Smith"]
=> {:captain=>"Picard", :first_officer=>"Riker", :science_officer=>"Data",
:tactical_officer=>"Worf", :chief_engineer=>"LaForge",
:chief_medical_officer=>"Crusher", :ships_counselor=>"Troi",
:annoying_ensign=>"Crusher", :attractive_ensign=>"Ro",
:expendable_crew_member=>"Smith"}

Enumerable#each_with_index Oddities

Blocks with a Single Parameter

What happens if you use each_with_index with a block that has only one parameter? You’d think that the block would accept the item and index passed to it as a two-element array, with the item as the first element and the corresponding index as the second element, but that’s not the case:

# For each item in justice_league, this line will output the following:
# {second letter of member's name} : {first letter of member's name} 
justice_league.each_with_index {|member| puts "#{member[1]}: #{member[0]}"}
=> q: A
a: B
l: B
l: F
r: G
r: G
a: M
u: S
i: V
o: W
=> ["Aquaman", "Batman", "Black Canary", "Flash", "Green Arrow", "Green Lantern"
, "Martian Manhunter", "Superman", "Vixen", "Wonder Woman"]

When each_with_index passes an item and its index to a block that takes only one parameter, the item goes into the paramter, and the index is discarded. Simply put, in this case, each_with_index behaves just like each.

Without a Block

What happens if you use each_with_index without a block to create an Enumerator object that spits out the next item when its next method is called? This:

hero = justice_league.each_with_index
=> #<Enumerable::Enumerator:0x159cb98>

hero.next
=> "Aquaman"

hero.next
=> "Batman"

hero.next
=> "Black Canary"

Note that calling next only yields the next item in the collection; the index information is lost. In this case, each_with_index behaves just like each.

Categories
Uncategorized

RubyFringe was Profitable, People are Happy, and the Sky Didn’t Fall. What Now?”

Collage of images from the RubyFringe summary article at \"Rethink\"

Over at Rethink, the blog of Accordion City-based development shop Unspace, Pete Forde shares his thoughts on the RubyFringe conference in an articles titled RubyFringe was Profitable, People are Happy, and the Sky Didn’t Fall. What Now?”.

The article covers all kinds of things including:

  • A loving poke at RailsConf (“A 400 person conference doesn’t become better with 1600 people, but if you’ve already done the hard work, why not scale up?”). That’s a reference to RailsConf 2006 and 2007.
  • The number of attendees (something that I’m going to cover in an article very soon)
  • Why they might not do another RubyFringe (think of all the movie sequels you’ve ever seen)
  • Women and tech conferences
  • You can hold a conference without sponsors (well, Engine Yard helped foot the bill for a party)
  • Consider going with just a single track
  • Just as Obie said that you shouldn’t undercharge for your services, you shouldn’t undercharge for a conference. Charge what it costs, and deliver real value
  • “Great food is important, because nobody can focus for fifteen hours on cold boxed lunches.” And RubyFringe had great food.
  • Care about the details! “This cannot be overstated, and the key word here is care.”

Meghann Millard of Unspace
Meghann Millard, RubyFringe cat herder supreme.

Pete said it in his article, and I feel it bears repeating: Meghann did an amazing job herding cats for RubyFringe, and if you attended RubyFringe and have a little cash to spare, it might be a nice idea to send her some flowers (or an Amazon gift certificate) for all the work she put in. I owe her big-time for thinking of me when she was looking for a host for the Friday night opening events as well as an emergency host when FAILCamp needed one. Thank you, Meghann! I salute you with a filet mignon on a flaming sword!

As for Pete thanking me for the RubyFringe guides and notes from the conference: it was my pleasure. I believed in the event from the get-go and was only too happy to apply the Burning Man ethos to this event (“There are no spectators, only participants”). Besides, that’s what we in the Accordion City tech community do!

If you’re thinking about putting together a tech conference, you should steal as many ideas as you can from RubyFringe, and Pete’s article is a good starting-off point.

Categories
Uncategorized

“Rails to Victory”

Here’s a still from what I assume is a propaganda film from World War II titled Rails to Victory. If any of you are planning to do presentations covering the topic of Rails and are looking for some graphics for your slides, you might want to consider this one:

Opening shot from the film \"Rails to Victory\"
Click the photo to see a larger version.
Photo courtesy of Miss Fipi Lele.

Categories
Uncategorized

Take Hampton’s Ruby Survey!

\"Take Hampton\'s Ruby Survey\": Hampton Catlin pointing at his survey, projected on a screen
Photo by rcoder.
Click the photo to see the original on its Flickr page.

Hampton “HAML” Catlin of Unspace (you know, the development shop that put RubyFringe together) has created a survey that he’d like as many people who code in Ruby to take. It’s quick and painless, and he’ll share the data once he’s compiled it.

Categories
Uncategorized

They Know Their Market

Here’s a photo from a t-shirt stall at the San Diego Comic-Con, which took place this past weekend:

T-shirt sizes at San Diego ComicCon: XXL and XXXL
Photo courtesy of Miss Fipi Lele.

Categories
Uncategorized

Enumerating Enumerable: Enumerable#each_slice

Enumerating Enumerable

Ten installments already? That’s right, this is the tenth Enumerating Enumerable article. As I’m fond of repeating, this is my little contribution to the Ruby community: a series of articles where I attempt to do a better job at documenting Ruby’s Enumerable module than Ruby-Doc.org does, with pretty pictures and more in-depth examples!

In this article, I’m going to cover each_slice, which got introduced in Ruby 1.9.

If you missed any of the earlier articles, I’ve listed them all below:

  1. all?
  2. any?
  3. collect / map
  4. count
  5. cycle
  6. detect / find
  7. drop
  8. drop_while
  9. each_cons

Enumerable#each_slice Quick Summary

Graphic representation of the "each_slice" method in Ruby's "Enumerable" module

In the simplest possible terms Given a number n, split the array into n-element slices (if the number of elements in the array isn’t evenly divisible by n, just put the remaining elements in the last slice), then iterate through those slices.
Ruby version 1.9 only
Expects
  • A number n describing the size of the iteration slice.
  • An optional block to receive the values from each iteration.
Returns
  • nil, if used with a block.
  • An Enumerator object that outputs n-sized slices of the collection, if used without a block.
RubyDoc.org’s entry Enumerable#each_slice

Enumerable#each_slice and Arrays

When used on an array with a block, each_slice takes a numeric argument n and splits the array into slices of length n (if the number of elements in the array isn’t evenly divisible by n, the remaining elements are put into the last slice). each_slice then iterates through the set of slices, passing each slice to the block. After the final iteration, each_slice returns nil.

Since this is yet another case when an showing an example makes things very clear, I’ll do just that, using the same example data I used in the article on each_cons:

justice_league = ["Aquaman", "Batman", "Black Canary", 
                  "Flash", "Green Arrow", "Green Lantern", 
                  "Martian Manhunter", "Superman", 
                  "Vixen", "Wonder Woman"]
justice_league = ["Aquaman", "Batman", "Black Canary", "Flash", "Green Arrow",
"Green Lantern", "Martian Manhunter", "Superman", "Vixen", "Wonder Woman"]

justice_league.each_slice(3) {|team| p team}
=> ["Aquaman", "Batman", "Black Canary"]
["Flash", "Green Arrow", "Green Lantern"]
["Martian Manhunter", "Superman", "Vixen"]
["Wonder Woman"]
=> nil

When used on an array without a block, each_slice takes a numeric argument n and returns an Enumerator that outputs slices of the array when its next method is called. Here’s an example:

teams_of_3 = justice_league.each_slice(3)
=> #<Enumerable::Enumerator:0x007fc73baa9830>

teams_of_3.next
=> ["Aquaman", "Batman", "Black Canary"]

teams_of_3.next
=> ["Flash", "Green Arrow", "Green Lantern"]

teams_of_3.next
=> ["Martian Manhunter", "Superman", "Vixen"]

teams_of_3.next
=> ["Wonder Woman"]

teams_of_3.next
=> StopIteration: iteration reached at end...
# (I'm skipping the rest of the error message)

teams_of_3.rewind
=> #<Enumerable::Enumerator:0x007fc73baa9830>

teams_of_3.next
=> ["Aquaman", "Batman", "Black Canary"]

Enumerable#each_slice and Hashes

When used on an hash with a block, each_slice takes a numeric argument n and splits the hash into arrays of length n (if the number of elements in the array isn’t evenly divisible by n, the remaining elements are put into the last slice). Within these arrays, each hash element is represented as a two-element array, with the first element being the key and the second element being the corresponding value.

each_slice then iterates through the set of arrays, passing each array to the block. After the final iteration, each_slice returns nil.

Here’s an example, using the same example data I used in the article on each_cons:

enterprise_crew = {:captain => "Picard",
                   :first_officer => "Riker",
                   :science_officer => "Data",
                   :tactical_officer => "Worf",
                   :chief_engineer => "LaForge",
                   :chief_medical_officer => "Crusher",
                   :ships_counselor => "Troi",
                   :annoying_ensign => "Crusher",
                   :attractive_ensign => "Ro",
                   :expendable_crew_member => "Smith"}
=> {:captain=>"Picard", :first_officer=>"Riker", :science_officer=>"Data",
:tactical_officer=>"Worf", :chief_engineer=>"LaForge",
:chief_medical_officer=>"Crusher", :ships_counselor=>"Troi",
:annoying_ensign=>"Crusher", :attractive_ensign=>"Ro",
:expendable_crew_member=>"Smith"}
=> nil

enterprise_crew.each_slice(3) {|team| p team}
=> [[:captain, "Picard"], [:first_officer, "Riker"], [:science_officer, "Data"]]
[[:tactical_officer, "Worf"], [:chief_engineer, "LaForge"],[:chief_medical_officer, "Crusher"]]
[[:ships_counselor, "Troi"], [:annoying_ensign, "Crusher"], [:attractive_ensign,  "Ro"]]
[[:expendable_crew_member, "Smith"]]
=> nil

When used on a hash without a block, each_slice takes a numeric argument n and returns an Enumerator that outputs arrays when its next method is called. Here’s an example:

away_teams_of_3 = enterprise_crew.each_slice(3)
=> #<Enumerable::Enumerator:0x007fc73ba44c50>

away_teams_of_3.next
=> [[:captain, "Picard"], [:first_officer, "Riker"], [:science_officer, "Data"]]

away_teams_of_3.next
=> [[:tactical_officer, "Worf"], [:chief_engineer, "LaForge"], [:chief_medical_officer, "Crusher"]]

away_teams_of_3.next
=> [[:ships_counselor, "Troi"], [:annoying_ensign, "Crusher"], [:attractive_ensign, "Ro"]]

away_teams_of_3.next
=> [[:expendable_crew_member, "Smith"]]

away_teams_of_3.next
=> StopIteration: iteration reached at end...
# (I'm skipping the rest of the error message)

away_teams_of_3.rewind
=> #

away_teams_of_3.next
=> [[:captain, "Picard"], [:first_officer, "Riker"], [:science_officer, "Data"]]