Simon Green

Posted on

# Power to the vowels

## Weekly Challenge 254

Each week Mohammad S. Anwar sends out The Weekly Challenge, a chance for all of us to come up with solutions to two weekly tasks. My solutions are written in Python first, and then converted to Perl. It's a great way for us all to practice some coding.

You are given a positive integer, `\$n`.

Write a script to return true if the given integer is a power of three otherwise return false.

### My solution

There are two things to consider when doing this task.

• Floating point math is not always going to give you the result you want. Julia Evans makes an excellent blog post about why 0.1 + 0.2 is not 0.3.
• Python sometimes treats the cube root of a negative number as a complex number. I can't seem to find a better reference than this Stack Exchange post.

With that in mind, we know we can get the approximate cube root by applying the function n (1รท3), written as `n ** (1/3)` in code. I do this, round the number to the nearest integer, and then check if that number cubed is the original number.

To get around the negative number issue, I take the absolute value.

``````def three_power(n: int) -> bool:
i = round(abs(n) ** (1/3))
return i ** 3 == abs(n)
``````

### Examples

``````\$ ./ch-1.py 27
true

\$ ./ch-1.py 0
true

\$ ./ch-1.py 6
false

\$ ./ch-1.py -8
true
``````

You are given a string, `\$s`.

Write a script to reverse all the vowels (`a`, `e`, `i`, `o`, `u`) in the given string.

### My solution

This is one of those tasks where the Python and Perl versions are slightly different. This is because in Python strings are immutable (i.e. cannot be changed). This has the upside that strings are iterable.

The first thing I do is convert the string to lower case, and extract all the vowels into a list.

``````def reverse_vowels(s: str) -> str:
s = s.lower()
vowel_list = [c for c in s if c in 'aeiou']
``````

I then loop through each letter of the string. If the letter is a vowel, I pop the last value off the `vowel_list` list and add it to the `new_string` variable. If it isn't, I add the character as is.

``````    new_string = ''
for c in s:
if c in 'aeiou':
new_string += vowel_list.pop()
else:
new_string += c
``````

Finally I return the string with the first letter capitalized.

``````    return new_string.capitalize()
``````

As I mentioned, the Perl code is slightly different. For this code, I loop through each position in the string. If the letter at that position is a vowel, then I replace it. `substr` can be used as a l-value in Perl

``````for my \$pos ( 0 .. length(\$s) - 1 ) {
if ( substr( \$s, \$pos, 1 ) =~ /[aeiou]/ ) {
substr( \$s, \$pos, 1 ) = pop(@vowel_list);
}
}
``````

### Examples

``````\$ ./ch-2.py Raku
Ruka

\$ ./ch-2.py Perl
Perl

\$ ./ch-2.py Julia
Jaliu

\$ ./ch-2.py Uiua
Auiu
``````