Funciones generadoras
4.3 Ecuaciones de recurrencia lineales
One of the disadvantages of the Python programming language is it is not suited for fast and memory intensive tasks.
53. Why is not all memory freed when Python exits?
Objects referenced from the global namespaces of Python modules are not always de- allocated when Python exits. This may happen if there are circular references. There are also certain bits of memory that are allocated by the C library that are impossible to free (e.g. a tool like the one Purify will complain about these). Python is, however, aggressive about cleaning up memory on exit and does try to destroy every single object.
If you want to force Python to delete certain things on de-allocation, you can use the at exit module to register one or more exit functions to handle those deletions.
54. Which of the languages does Python resemble in its class syntax? C++ is the appropriate language that Python resemble in its class syntax. 55. Who created the Python programming language?
Python programming language was created by Guido van Rossum.
======================================================= ===
1 line: Output print 'Hello, world!'
2 lines: Input, assignment
name = raw_input('What is your name?\n') print 'Hi, %s.' % name
3 lines: For loop, built-in enumerate function, new style formatting friends = ['john', 'pat', 'gary', 'michael']
for i, name in enumerate(friends):
print "iteration {iteration} is {name}".format(iteration=i, name=name) 4 lines: Fibonacci, tuple assignment
parents, babies = (1, 1) while babies < 100:
print 'This generation has {0} babies'.format(babies) parents, babies = (babies, parents + babies)
5 lines: Functions def greet(name): print 'Hello', name greet('Jack')
greet('Jill') greet('Bob')
6 lines: Import, regular expressions import re
for test_string in ['555-1212', 'ILL-EGAL']: if re.match(r'^\d{3}-\d{4}$', test_string):
print test_string, 'is a valid US local phone number' else:
print test_string, 'rejected'
7 lines: Dictionaries, generator expressions prices = {'apple': 0.40, 'banana': 0.50} my_purchase = {
'apple': 1, 'banana': 6}
grocery_bill = sum(prices[fruit] * my_purchase[fruit] for fruit in my_purchase)
print 'I owe the grocer $%.2f' % grocery_bill
8 lines: Command line arguments, exception handling # This program adds up integers in the command line import sys
try:
total = sum(int(arg) for arg in sys.argv[1:]) print 'sum =', total
except ValueError:
print 'Please supply integer arguments' 9 lines: Opening files
# indent your Python code to put into an email import glob
# glob supports Unix style pathname extensions python_files = glob.glob('*.py')
for file_name in sorted(python_files): print ' ---' + file_name
with open(file_name) as f: for line in f:
print ' ' + line.rstrip() print
10 lines: Time, conditionals, from..import, for..else from time import localtime
activities = {8: 'Sleeping', 9: 'Commuting', 17: 'Working', 18: 'Commuting', 20: 'Eating', 22: 'Resting' } time_now = localtime() hour = time_now.tm_hour
for activity_time in sorted(activities.keys()): if hour < activity_time:
print activities[activity_time] break
print 'Unknown, AFK or sleeping!' 11 lines: Triple-quoted strings, while loop REFRAIN = '''
%d bottles of beer on the wall, %d bottles of beer,
take one down, pass it around, %d bottles of beer on the wall! '''
bottles_of_beer = 99 while bottles_of_beer > 1:
print REFRAIN % (bottles_of_beer, bottles_of_beer, bottles_of_beer - 1)
bottles_of_beer -= 1 12 lines: Classes
class BankAccount(object):
def __init__(self, initial_balance=0): self.balance = initial_balance def deposit(self, amount): self.balance += amount def withdraw(self, amount): self.balance -= amount def overdrawn(self): return self.balance < 0 my_account = BankAccount(15) my_account.withdraw(5) print my_account.balance
13 lines: Unit testing with unittest import unittest def median(pool): copy = sorted(pool) size = len(copy) if size % 2 == 1: return copy[(size - 1) / 2] else:
return (copy[size/2 - 1] + copy[size/2]) / 2 class TestMedian(unittest.TestCase):
def testMedian(self):
self.failUnlessEqual(median([2, 9, 9, 7, 9, 2, 4, 5, 8]), 7) if __name__ == '__main__':
unittest.main()
14 lines: Doctest-based testing def median(pool):
'''Statistical median to demonstrate doctest. >>> median([2, 9, 9, 7, 9, 2, 4, 5, 8]) 7 ''' copy = sorted(pool) size = len(copy) if size % 2 == 1: return copy[(size - 1) / 2] else:
return (copy[size/2 - 1] + copy[size/2]) / 2 if __name__ == '__main__':
import doctest doctest.testmod() 15 lines: itertools
from itertools import groupby lines = '''
This is the first paragraph. This is the second. '''.splitlines()
# Use itertools.groupby and bool to return groups of # consecutive lines that either have content or don't. for has_chars, frags in groupby(lines, bool):
if has_chars:
print ' '.join(frags) # PRINTS:
# This is the first paragraph. # This is the second.
16 lines: csv module, tuple unpacking, cmp() built-in import csv
# write stocks data as comma-separated values
writer = csv.writer(open('stocks.csv', 'wb', buffering=0)) writer.writerows([
('GOOG', 'Google, Inc.', 505.24, 0.47, 0.09), ('YHOO', 'Yahoo! Inc.', 27.38, 0.33, 1.22),
('CNET', 'CNET Networks, Inc.', 8.62, -0.13, -1.49) ])
# read stocks data, print status messages stocks = csv.reader(open('stocks.csv', 'rb'))
status_labels = {-1: 'down', 0: 'unchanged', 1: 'up'} for ticker, name, price, change, pct in stocks: status = status_labels[cmp(float(change), 0.0)] print '%s is %s (%s%%)' % (name, status, pct) 18 lines: 8-Queens Problem (recursion)
BOARD_SIZE = 8
def under_attack(col, queens): left = right = col
for r, c in reversed(queens): left, right = left - 1, right + 1 if c in (left, col, right):
return True return False def solve(n): if n == 0: return [[]]
smaller_solutions = solve(n - 1) return [solution+[(n,i+1)] for i in xrange(BOARD_SIZE) for solution in smaller_solutions if not under_attack(i+1, solution)] for answer in solve(BOARD_SIZE):
print answer
20 lines: Prime numbers sieve w/fancy generators import itertools
def iter_primes():
# an iterator of all numbers between 2 and +infinity numbers = itertools.count(2)
# generate primes forever while True:
# get the first number from the iterator (always a prime) prime = numbers.next()
yield prime
# this code iteratively builds up a chain of # filters...slightly tricky, but ponder it a bit
numbers = itertools.ifilter(prime.__rmod__, numbers) for p in iter_primes():
if p > 1000: break print p
21 lines: XML/HTML parsing (using Python 2.5 or third-party library) dinner_recipe = '''<html><body><table> <tr><th>amt</th><th>unit</th><th>item</th></tr> <tr><td>24</td><td>slices</td><td>baguette</td></tr> <tr><td>2+</td><td>tbsp</td><td>olive oil</td></tr> <tr><td>1</td><td>cup</td><td>tomatoes</td></tr> <tr><td>1</td><td>jar</td><td>pesto</td></tr> </table></body></html>'''
# In Python 2.5 or from http://effbot.org/zone/element-index.htm import xml.etree.ElementTree as etree
tree = etree.fromstring(dinner_recipe)
# For invalid HTML use http://effbot.org/zone/element-soup.htm # import ElementSoup, StringIO
# tree = ElementSoup.parse(StringIO.StringIO(dinner_recipe)) pantry = set(['olive oil', 'pesto'])
for ingredient in tree.getiterator('tr'): amt, unit, item = ingredient
if item.tag == "td" and item.text not in pantry: print "%s: %s %s" % (item.text, amt.text, unit.text) 28 lines: 8-Queens Problem (define your own exceptions) BOARD_SIZE = 8
class BailOut(Exception): pass
def validate(queens):
left = right = col = queens[-1] for r in reversed(queens[:-1]): left, right = left-1, right+1 if r in (left, col, right): raise BailOut def add_queen(queens): for i in range(BOARD_SIZE): test_queens = queens + [i] try: validate(test_queens) if len(test_queens) == BOARD_SIZE: return test_queens else: return add_queen(test_queens) except BailOut: pass raise BailOut queens = add_queen([]) print queens
print "\n".join(". "*q + "Q " + ". "*(BOARD_SIZE-q-1) for q in queens)
33 lines: "Guess the Number" Game (edited) from http://inventwithpython.com import random
guesses_made = 0
name = raw_input('Hello! What is your name?\n') number = random.randint(1, 20)
print 'Well, {0}, I am thinking of a number between 1 and 20.'.format(name) while guesses_made < 6:
guess = int(raw_input('Take a guess: ')) guesses_made += 1
if guess < number:
print 'Your guess is too low.' if guess > number:
print 'Your guess is too high.' if guess == number:
break
if guess == number:
print 'Good job, {0}! You guessed my number in {1} guesses!'.format(name, guesses_made)
else:
======================================================= ========
Here is a set of small scripts, which demonstrate some features of Python programming.
# this is the first comment #! python
# integer variables SPAM = 1 #! python
print "Hello, Python"
#! python # string variable
STRING = "# This is not a comment." print STRING #! python # integer arith a=4 print a b=12+5 print b c=b%a print c #! python # trailing comma i = 256*256
print 'The value of i is', i #! python
# Fibonacci series:
# the sum of two elements defines the next a, b = 0, 1
while b < 200: print b, a, b = b, a+b
#! python
# input and operator if
x = int(raw_input("Please enter an integer: ")) if x < 0:
x = 0
print 'Negative changed to zero' elif x == 0:
print 'Zero' elif x == 1: print 'Single' else:
print 'More'
#! python # operator for:
# Measure some strings:
a = ['cat', 'window', 'defenestrate'] for x in a: print x, len(x) #! python # range function print range(10) print range(5, 10) print range(0, 10, 3)
a = ['Mary', 'had', 'a', 'little', 'lamb'] for i in range(len(a)): print i, a[i] #! python # break operator # prime numbers for n in range(2, 1000): for x in range(2, n): if n % x == 0: print n, 'equals', x, '*', n/x break else:
# loop fell through without finding a factor print n, 'is a prime number'
#! python
#pass statement does nothing.
#It can be used when a statement is required syntactically but the program requires no action. For example:
while True:
pass # Busy-wait for keyboard interrupt
#! python
# Defining Functions
def fib(n): # write Fibonacci series up to n """Print a Fibonacci series up to n.""" a, b = 0, 1
while b < n: print b, a, b = b, a+b
# Now call the function we just defined: fib(2000)
! python
# function that returns a list of the numbers of the Fibonacci series def fib2(n): # return Fibonacci series up to n
"""Return a list containing the Fibonacci series up to n.""" result = []
a, b = 0, 1 while b < n:
result.append(b) # see below a, b = b, a+b
return result
#=================================== f100 = fib2(100) # call it
print f100 # write the result #! python
# work with strings
# Strings can be concatenated (glued together) with the + operator, and repeated with *: word = 'Help' + 'A'
print word
print '<' + word*5 + '>'
# Two string literals next to each other are automatically concatenated; # the first line above could also have been written "word = 'Help' 'A'"; # this only works with two literals, not with arbitrary string expressions: st='str' 'ing' # <- This is ok
print st
st='str'.strip() + 'ing' # <- This is ok print st
# Strings can be subscripted (indexed); like in C, the first character of a string # has subscript (index) 0. There is no separate character type; a character is # simply a string of size one. Like in Icon, substrings can be specified with # the slice notation: two indices separated by a colon.
print word[4] print word[0:2] print word[2:4]
# Slice indices have useful defaults; an omitted first index defaults to zero, # an omitted second index defaults to the size of the string being sliced. print word[:2] # The first two characters
print word[2:] # All but the first two characters
# Python strings cannot be changed. Assigning to an indexed position in the string results in an error:
# However, creating a new string with the combined content is easy and efficient: print 'x' + word[1:]
# Here's a useful invariant of slice operations: s[:i] + s[i:] equals s. print word[:2] + word[2:]
print word[:3] + word[3:]
# Degenerate slice indices are handled gracefully: an index that is too large is replaced # by the string size, an upper bound smaller than the lower bound returns an empty string. print word[1:100]
print word[10:] print word[2:1]
# Indices may be negative numbers, to start counting from the right. For example: print word[-1] # The last character
print word[-2] # The last-but-one character print word[-2:] # The last two characters print word[:-2] # All but the last two characters
# But note that -0 is really the same as 0, so it does not count from the right! print word[-0] # (since -0 equals 0)
# Out-of-range negative slice indices are truncated, but don't try this for single-element (non-slice) indices:
print word[-100:]
# print word[-10] # error
#The best way to remember how slices work is to think of the indices as pointing between characters,
#with the left edge of the first character numbered 0. Then the right edge of the last character
#of a string of n characters has index n, for example: # +---+---+---+---+---+ # | H | e | l | p | A | # +---+---+---+---+---+ # 0 1 2 3 4 5 #-5 -4 -3 -2 -1 s = 'supercalifragilisticexpialidocious' print s print len(s) #! python
# Default Argument Values
def ask_ok(prompt, retries=4, complaint='Yes or no, please!'): while True:
ok = raw_input(prompt)
if ok in ('y', 'ye', 'yes'): return True
if ok in ('n', 'no', 'nop', 'nope'): return False retries = retries - 1
print complaint #====================================================== ======== i = 5 def f(arg=i): print arg i = 6 f() #====================================================== ======== z=ask_ok('really quit???') if z==False : print "bad" #! python # Lambda Forms def make_incrementor(n): return lambda x: x + n #================================== f = make_incrementor(42) print f(0) print f(1) print f(15) //======================================================= ============================ // //======================================================= ============================ #! python # speed test nn=10000000 i=0; s=0; print "beginning..." while i #! python
# raw input of strings only! st = raw_input("")
print st
st=st*3 # triple the string print st #! python # math import math print math.cos(math.pi / 4.0) print math.log(1024, 2) #! python # random import random
print random.choice(['apple', 'pear', 'banana'])
print random.sample(xrange(100), 10) # sampling without replacement print random.random() # random float
print random.randrange(6) # random integer chosen from range(6) #! python
def perm(l):
# Compute the list of all permutations of l if len(l) <= 1:
return [l]
r = [] # here is new list with all permutations! for i in range(len(l)): s = l[:i] + l[i+1:] p = perm(s) for x in p: r.append(l[i:i+1] + x) return r #============================================== a=[1,2,3] print perm(a) #! python a=2+3j b=2-3j print a*a print a*b print a.real print b.imag #! python while True: try:
x = int(raw_input("Please enter a number: ")) break
except ValueError:
#! python
import string, sys try:
f = open('myfile.txt') s = f.readline() i = int(string.strip(s))
except IOError, (errno, strerror):
print "I/O error(%s): %s" % (errno, strerror) except ValueError:
print "Could not convert data to an integer." except:
print "Unexpected error:", sys.exc_info()[0] raise
#! python # work with lists
a = ['spam', 'eggs', 100, 1234] print " list a=",a
# list indices start at 0, print 'a[0]=', a[0] print 'a[3]=', a[3] print 'a[-2]=', a[-2]
# lists can be sliced, concatenated and so on: print "a[1:-1]=", a[1:-1]
print a[:2] + ['bacon', 2*2] print 3*a[:3] + ['Boe!']
# possible to change individual elements of a list: a[2] = a[2] + 23
print "changing a[2]=", a
#Assignment to slices is also possible, and this can even change the size of the list: # Replace some items:
a[0:2] = [1, 12] print a # Remove some: a[0:2] = [] print a # Insert some:
a[1:1] = ['bletch', 'xyzzy'] print a
a[:0] = a # Insert (a copy of) itself at the beginning print a
# possible to nest lists (create lists containing other lists) q = [2, 3]
p = [1, q, 4]
print " nest list=", p print 'length =', len(p) print p[1] print p[1][0] p[1].append('xtra') print p print q #! python
# more work with lists
a = [66.6, 333, 333, 1, 1234.5]
print a.count(333), a.count(66.6), a.count('x') a.insert(2, -1) print a a.append(333) print a print a.index(333) a.remove(333) print a a.reverse() print a a.sort() print a #! python
# huge list making nn=1000000 a = []
i=0 while i #! python
# Using Lists as Stacks stack = [3, 4, 5] stack.append(6) stack.append(7) print stack x=stack.pop() print "popped ",x print stack x=stack.pop()
print "popped ",x x=stack.pop() print "popped ",x print stack #! python
# Using Lists as Queues
queue = ["Eric", "John", "Michael"]
queue.append("Terry") # Terry arrives queue.append("Graham") # Graham arrives print queue s=queue.pop(0) print s s=queue.pop(0) print s print queue #! python
# The del statement
a = [-1, 1, 66.6, 333, 333, 1234.5] del a[0] print a del a[2:4] print a #! python # filter of sequence
def f(x): return x % 2 != 0 and x % 3 != 0 res=filter(f, range(2, 25))
print res
#! python
# map of sequence def cube(x): return x*x*x res=map(cube, range(1, 11)) print res
#! python
# reduce(func, sequence)" returns a single value constructed by
# calling the binary function func on the first two items of the sequence, # then on the result and the next item, and so on
def add(x,y): return x+y r=reduce(add, range(1, 11)) print r # 55
#! python
# A tuple consists of a number of values separated by commas t = 12345, 54321, 'hello!' # tuple packing
print t
(12345, 54321, 'hello!') # Tuples may be nested: u = t, (1, 2, 3, 4, 5)
print u # ((12345, 54321, 'hello!'), (1, 2, 3, 4, 5))
#! python
# Dictionaries are sometimes as ``associative memories'' or ``associative arrays'' tel = {'jack': 4098, 'sape': 4139}
tel['guido'] = 4127 print tel print tel['jack'] del tel['sape'] tel['irv'] = 4127 print tel print tel.keys() x=tel.has_key('guido') print x
# The dict() constructor builds dictionaries directly from lists
# of key-value pairs stored as tuples. When the pairs form a pattern, # list comprehensions can compactly specify the key-value list. d=dict([('sape', 4139), ('guido', 4127), ('jack', 4098)])
print d
vec=[1,2,3,4,5]
dd=dict([(x, x**2) for x in vec]) # use a list comprehension print dd
#! python
# Standard Module sys import sys print sys.path sys.path.append('c:\temp') print sys.path print sys.version print sys.platform print sys.maxint #! python #====================================================== =
# dir() is used to find out which names a module defines import sys
print dir(sys)
# Without arguments, dir() lists the names you have defined currentl #! python
# convert any value to a string: pass it to the repr() or str() s = 'Hello, world.' print str(s) print repr(s) print str(0.1) print repr(0.1) x = 10 * 3.25 y = 200 * 200
s = 'The value of x is ' + repr(x) + ', and y is ' + repr(y) + '...' print s
# The repr() of a string adds string quotes and backslashes: hello = 'hello, world\n'
hellos = repr(hello)
print hellos # 'hello, world\n'
# The argument to repr() may be any Python object: print repr((x, y, ('spam', 'eggs')))
# reverse quotes are convenient in interactive sessions: print `x, y, ('spam', 'eggs')`
#! python
# two ways to write a table of squares and cubes: for x in range(1, 11):
print repr(x).rjust(2), repr(x*x).rjust(3), # Note trailing comma on previous line print repr(x*x*x).rjust(4) print '=================================================' for x in range(1,11): print '%2d %3d %4d' % (x, x*x, x*x*x) #! python
# output results from running "python demo.py one two three" # at the command line:
import sys
print sys.argv[] # ['demo.py', 'one', 'two', 'three']
#! python
# String Pattern Matching - regular expression import re
r=re.findall(r'\bf[a-z]*', 'which foot or hand fell fastest') print r # ['foot', 'fell', 'fastest']
s=re.sub(r'(\b[a-z]+) \1', r'\1', 'cat in the the hat') print s # 'cat in the hat'
# dates are easily constructed and formatted from datetime import date
now = date.today() print now
datetime.date(2003, 12, 2)
print now.strftime("%m-%d-%y or %d%b %Y is a %A on the %d day of %B") # dates support calendar arithmetic
birthday = date(1964, 7, 31) age = now - birthday
print age.days # 14368
#! python
# Internet Access import urllib2
for line in urllib2.urlopen('http://tycho.usno.navy.mil/cgi-bin/timer.pl'): if 'EST' in line: # look for Eastern Standard Time
print line import smtplib server = smtplib.SMTP('localhost') server.sendmail('[email protected]', '[email protected]', """To: [email protected] From: [email protected] Beware the Ides of March. """)
server.quit()
# work with files #open file for write
f=open('c:/TEMP/workpy.txt','w') print f
f.write("aaaaaaaaaaaaaaaaaaa\n") f.write("bbbbbbbbbbbbbb");
# work with files #open file for read
f=open('c:/TEMP/workpy.txt','r') # line reading
s=f.readline() print s
f.close()
# work with files #open file for read
f=open('c:/TEMP/workpy.txt','r') # pieces reading
s1=f.read(5) print s1
s2=f.read(19) print s2 s2=f.read(25) print s2 f.close()
# work with files #open file for read
f=open('c:/TEMP/workpy.txt','r') # pieces reading s1=f.read(5) print s1 print f.tell() s2=f.read(19) print s2 print f.tell() s2=f.read(25) print s2 print f.tell() f.close()
# work with files # seek
f=open('c:/TEMP/workpy.txt','r+') f.write('0123456789abcdef')
f.seek(5) # Go to the 6th byte in the file print f.read(1)
f.seek(-3, 2) # Go to the 3rd byte before the end print f.read(1)
#! python
# The glob module provides a function for making file lists from # directory wildcard searches:
import glob s=glob.glob('*.*')