Interestingly, the Perl 5 and Perl 6 solutions to Challenge 24 task 1 in the Perl Weekly Challenge are identical.
This week’s Perl Weekly Challenge, problem 1, reads:
The numbers formed by adding one to the products of the smallest primes are called the Euclid Numbers (see wiki). Write a script that finds the smallest Euclid Number that is not prime. This challenge was proposed by Laurent Rosenfeld.
The first Euclid numbers are 3, 7, and 31. These are computed as follows:
We’ll take the first three prime numbers – 2, 3, and 5.
The corresponding Euclid number is the prime number multiplied by all the smaller prime numbers, with 1 added to it.
So the first one, 3, is just 2 (nothing to multiply it against) plus 1.
The second one is 3 * 2 plus 1, or 7.
The third one is 5 * 3 *2 + 1, which is 31.
How do you do this in code? Continue reading
This week’s (week 10) Perl Request Challenge, challenge 1, was:
Write a script to encode/decode Roman numerals. For example, given Roman numeral CCXLVI, it should return 246. Similarly, for decimal number 39, it should return XXXIX. Checkout wikipedia page for more informaiton.
For this blog, I’m going to talk about converting a decimal to a Roman numeral.
To start with, I read the Wikipedia page referenced in the challenge, and realized there were several different systems for writing Roman numerals – it wasn’t as standardized as I thought! That said, I stuck with the style used in the description of the challenge, specifically “subtractive” notation. Essentially, the symbols are written from the largest value to the smallest value, left to right, with no more than 3 of any symbol used. When four of a symbol would normally be used (for instance, IIII to mean 4), instead it would be written as IV, meaning one less than 4 (you see this because the smaller number is before the bigger number).
So that’s what I’ll talk about below – the part of the code that converts an integer to a Roman number.
The Perl Weekly Challenge for week 9 includes an optional third challenge – essentially, use the Sparkpost service’s API to send an email. Sparkpost is a service that allows sending emails via an HTTP interface, just by posting a JSON form response.
I’ve noticed people have not known how to solve these API-usage challenges, so I will share my method of solving them, using Perl 6.
If you understand “big O” notation, skip on down to the “Solving Week 5 Problem 2” heading.
I’m going to discuss this using Perl 6, but I think an intermediate Perl 5 user will be able to figure out what the code does and how it would be able to be implemented in Perl 5.
“Big O” Notation
Most students of computer science have been exposed to “big O” notation. Essentially, algorithms can be classified by performance. N represents the size of the data being processed, while O() is shorthand for “execution time on the order of …”
I love Perl – and the perl interpreter always impresses me. Today, I decided to try a few languages to see how they compare.
How well does the language do nothing? I decided to test this out on my fairly speedy Macbook Pro. All tests were executed multiple times and the best result was used for this post, to account for various caching speedups.
do-nothing$ touch nothing.c do-nothing$ time clang nothing.c Undefined symbols for architecture x86_64: "_main", referenced from: implicit entry/start for main executable ld: symbol(s) not found for architecture x86_64 clang: error: linker command failed with exit code 1 (use -v to see invocation) real 0m0.041s user 0m0.017s sys 0m0.017s
So, C can spit out an error that will probably not make sense to people new to the language (it’s missing a main function, although usually you’ll define main without a leading underscore – for reasons I won’t get into here). But it was fairly quick – about 40ms (I repeated this several times to account for caching).
Next I tried Java (using the
do-nothing$ touch nothing.java do-nothing$ time javac nothing.java real 0m0.759s user 0m1.323s sys 0m0.105s
Java doesn’t throw any errors, but it takes over 750ms to compile nothing (in a somewhat satisfyingly mathematically pure way, it literally produces nothing – no output files are created). When I ran javac with the -verbose option (how a Unix workstation company would think long options with a single hypen are okay is beyond me, but I digress), it spits out some timing information. It takes 23ms to parse nothing and roughly 290ms to do the compilation. I can only assume the other 450ms or so are going to compiler startup overhead.
How about Ruby?
do-nothing$ touch nothing.rb do-nothing$ time ruby nothing.rb real 0m0.073s user 0m0.053s sys 0m0.010s do-nothing$
It takes 73ms to do nothing, but it does properly do nothing.
How about Python (v2)?
do-nothing:t$ touch nothing.py do-nothing:t$ time python nothing.py real 0m0.018s user 0m0.009s sys 0m0.007s
Python does nothing pretty darn well – 18ms!
Now, my language of choice, Perl 5:
do-nothing$ touch nothing.pl do-nothing$ time perl nothing.pl real 0m0.006s user 0m0.002s sys 0m0.003s do-nothing$
Brilliant – it does nothing very quickly compared to other languages – 6ms.
That said, my old version (Christmas) of the Rokudo-based Perl 6 takes roughly 250ms – not all that good. I’m not sure how the newer versions do. It’s certainly a powerful new language (you should think of Perl 5 and Perl 6 as distinct language – both are being actively developed with new features, optimizations, bug fixes, etc, added to both continually, with no plans to discontinue development on either).
So, It think, in conclusion:
- C isn’t good for nothing
- Java can’t do nothing quickly
- Perl 6 can do nothing, but not too quickly
- Ruby seems okay for nothing, while Python 2 is pretty darn good at nothing
- Perl 5 is good for nothing!
(Yes, this post is 90% jest – startup time of the tools is important, but is almost always a dumb reason to pick a language)