Anagram

Alex Martelli aleax at aleax.it
Wed Jan 23 08:30:54 EST 2002


"Nikolai Kirsebom" <nikolai.kirsebom at siemens.no> wrote in message
news:3c4e8efc.1036790726 at news.mch.sni.de...
> Just for fun !!
>
> Friend of mine who used to work with lisp (and is a bit interested in
> Python) asked me how compact I could write a program to evaluate the
> number of possible combinations a set of characters (string) can be
> written in - handling two identical characters as different
> characters.
>
> Example:
> "ab" --> yields 2 ("ab", "ba")
> "abc" --> yields 6
> "aa" --> yields 2

I.e., the factorial of len(thestring).


> My Python answer shown below.   Better solutions ?


Most compact with core Python only (not necessarily best,
but pretty fast):

import operator
def f(s): return reduce(operator.mul, range(2,1+len(s)), 1)


Fastest for long strings (needs gmpy extension installed):

import gmpy
def f(s): return gmpy.fac(len(s))


Simplest (easiest to understand):

def f(s):
    result = 1
    for i in range(2, 1+len(s)):
        result = result * i
    return result


Closest to the textbook definition of factorial (lousy otherwise;
needs Python 2.2, or from __future__ import nested_scopes in 2.1):

def f(s)
    def fact(n):
        if n<2: return 1
        else: return n*fact(n-1)
    return fact(len(s))


> Does anyone (here) know how this could be done in Perl ?

I believe it would be something like, e.g. for the "simplest" above:

sub f {
    my $s = $_[0];
    my $result = 1;
    for(my $i = 2; $i < 1+length($s); $i++) {
        $result = $result * $i;
    }
    return $result;
}

or, no doubt, a zillion other ways (TMTOWTDI, I believe).


Alex






More information about the Python-list mailing list