Stories
Slash Boxes
Comments
NOTE: use Perl; is on undef hiatus. You can read content, but you can't post it. More info will be forthcoming forthcomingly.

All the Perl that's Practical to Extract and Report

use Perl Log In

Log In

[ Create a new account ]

ferreira (5993)

ferreira
  (email not shown publicly)
http://www.ferreira.triang.net/

Just another Brazilian Perl hacker.

Journal of ferreira (5993)

Tuesday November 14, 2006
08:47 AM

Who's magic?

[ #31603 ]

My kid asked me to think of a number between 1 and 60 and to point out which of five cards the number showed at. And then he "divined" my number. I thought for a moment and then I proposed another guessing game for him: tell me your number between 1 and 60 and then I "divined" the cards the number should show off. My guesses proved to be flawless to the amusement of him and his sister.

The really good part was when I explained (very mildly) how the cards were built by representing the numbers in binary and assigning each card a position and the numbers which had a bit 1 in that position. I managed to do it without fuss and without letting them realize I was actually lecturing on something.

They enjoyed the decomposition algorithm I taught them - decomposing 28 to 16 + 8 + 4 or 13 to 8 + 4 + 1. All very simple with ordinary mathematics a young kid can handle easily. All of a sudden, the "magical" trick turned out to be a simple mathematic problem at their reach.

The real trick was building the cards - not really a trick after the rationale was found, but boring and error-prone to do by hand. So I wrote this:

#!/usr/bin/perl

use strict;
use warnings;

my %cards = (
    1 => [],
    2 => [],
    4 => [],
    8 => [],
    16 => []
);
my @keys = sort { $a <=> $b } keys %cards;

sub add_number {
    my $n = shift;
    for my $k (@keys) {
         last if $k>$n;

         push @{$cards{$k}}, $n if $n & $k;
    }
}

sub show {
    for my $k (@keys) {
         my @numbers = @{$cards{$k}};
         last unless @numbers; # don't show empty cards

         printf "%3.d:". (" %3.d" x @numbers) . "(%d)\n", $k, @numbers, scalar @numbers;
    }
    print "\n";
}

for my $i (1..63) {
    add_number($i);
}

    show();

That was instructive after all.

The Fine Print: The following comments are owned by whoever posted them. We are not responsible for them in any way.
 Full
 Abbreviated
 Hidden
More | Login | Reply
Loading... please wait.