0
def word_to_syllable(w,li=[]):
  if not w:
    return li
  pattern = """
          ########
           """
  pattern = re.sub("C","[^aeiou]",pattern)
  pattern = re.sub("V","[aeiou]",pattern)
  match = re.findall(pattern,w,re.VERBOSE)[0]
  #print(li)
  li.append(match)
  w = w[len(match):]
  return word_to_syllable(w,li)

This works okay for the first call, but then local variable li somehow doesn't get forgotten and new values are just appended to the old ones - instead of string, as name of the function suggests, being split to it's own list. Yeah, if I define my function without default argument and instead say it's empty list later in the call , everything's just fine, but I'm curious about what is exactly happening with this code above.

1 Answers1

2

Using a list as a default argument in Python will produce surprising results because it's mutable, so (w,li=[]) isn't what you want.

See here: "Least Astonishment" and the Mutable Default Argument

and here: http://www.deadlybloodyserious.com/2008/05/default-argument-blunders/

Short version is that default arguments are evaluated when the function is defined, not when the function is run like you'd expect.

Community
  • 1
  • 1
Christian Ternus
  • 8,406
  • 24
  • 39
  • Well, you can use it, and it will work, just maybe not quite as expected. – fjarri Oct 26 '13 at 01:59
  • @Bogdan Right, clarified. – Christian Ternus Oct 26 '13 at 01:59
  • Thanks for answer, and for the link. "As soon as you get to think into this way, then it completely makes sense: a function is an object being evaluated on its definition; default parameters are kind of "member data" and therefore their state may change from one call to the other - exactly as in any other object"(from the best answer there, great explanation!) – user2921960 Oct 26 '13 at 02:22