You are on page 1of 12

Taller de Python "Episodio 1"

por Moleman (AKA Hctor Monlen) Bienvenidos a este taller de Python. En unos cuantos artculos espero ensearos a programar en este lenguaje que personalmente me apasiona, y espero que dentro de poco a vosotros tambin. No me enrollo ms y vamos al grano!!!
Si no lo tenis, podis descargaros las fuentes para compi lar (para Unix & Linux en general y para Mac OS X) de: http://www.python.org/ftp/python/2.4/Python-2.4.tgz Para sistemas Windows hay un setup aqu: http://www.python.org/ftp/python/2.4/python-2.4.msi Y aqu un instalador para Mac OS X (si no queris compi larlo): http://ftp.cwi.nl/jack/python/mac/MacPython-OSX-2.3-1.dmg (recomendado leerse antes la documentacin del instalador en http://homepages.cwi.nl/~jack/macpython/download.html )

Bien, el primer paso es descargarse el intrprete de Python si es que no lo tenis ya. Por si no lo sabis Python es un lenguaje interpretado, es decir, lo que se programa es un script que luego se le pasa al intrprete que lo ejecutar. Esto permite hacer rpidas modificaciones del programa al no tener que compilar cada vez, como ocurre por ejemplo con el lenguaje C. (Los que sepis algo de C notareis que la sintaxis se pare ce bastante. No es una coincidencia ) Los Linux-Users deberais tener el intrprete instalado por defecto. Podris comprobar si lo tenis simplemente ejecutando en una consola: Shadowland:~$ python Python 2.3.2 (#2, Oct 6 2003, 08:02:06) [GCC 3.3.2 20030908 (Debian prerelease)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> El ">>>" es el prompt del intrprete esperando a que una orden sea introducida. Ms adelante veremos esto en ms detalle. Para salir simplemente pulsad Ctrl+D.

Existen en Python los siguientes operadores aritmticos (por orden de prioridad, de 1 a 4):

3/68

Taller de Python "Episodio 1"


Los operadores lgicos son, por orden de prioridad: >>> 5==5 True >>> 2*3+(4-3)/((4-5)**3) 5 >>> Espero que vayis comprendiendo como funciona. Los va lores True y False son valores que representan verdadero y falso respectivamente. En Python es lo ms parecido que hay a datos booleanos (esto debera ir en el punto de los tipos de datos, pero no tiene mayor complicacin). Existen ms tipos de operadores, pero supongo que es mejor ms adelante cuando salga una ocasin de usarlos, ya que su complejidad es bastante ms elevada, como por ejemplo los operadores >> y << que desplazan a la dere cha o izquierda los bits del valor que se les pasa tanto co mo se les indique.

Los operadores de comparacin tiene todos la misma prio ridad y son:

En Python, una variable se declara solamente cuando va a ser usada. No hay que declararlas al principio como en el tpico programa de C. As mismo, el tipo de dato que contendr la variable tam poco se declara y el intrprete lo toma dinmicamente segn el valor que se le pasa a la variable. La prioridad conjunta de todos ellos se define de mayor a menor, as: >>> a=5 >>> print a 5 >>> Como vemos, hemos asignado el valor entero 5 a la variable. Si hacemos: Hay que tener cuidado con las operaciones que aniden mu chos operadores de distintos tipos, ya que el orden de pre ferencia puede hacer que la operacin no salga como de biera. Para paliar el problema mientras cogis prctica, siempre podis usar los parntesis como separadores de operacin, verbi gratia: 2*3+(4-3)/((4-5)**3) Os pondr unos ejemplos de este tipo de operaciones: Shadowland:~$ python Python 2.3.4 (#2, Sep 24 2004, 08:39:09) [GCC 3.3.4 (Debian 1:3.3.4-12)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> 2+3 5 >>> 4-2 2 >>> 5*2 10 >>> 2**3 8 >>> 4>5 False 4/68 >>> b=5.0 >>> print b 5.0 >>> Lo que estamos haciendo es asignar un valor flotante (de cimal) a la variable.(es importante notar que el decimal se representa con punto y no con coma) En ningn caso hemos declarado el tipo de dato que con tendr, aunque SI que hay que asignarle un valor antes de usar una variable o Python dar error. >>> print pruebaerror Traceback (most recent call last): File "<stdin>", line 1, in ? NameError: name 'pruebaerror' is not defined >>> Python es case sensitive por lo que diferencia entre maysculas y minsculas. Tambin hay que tener en cuen ta unas reglas para los nombres de las variables: 1. Slo se pueden usar dgitos, letras y el carcter de subrayado. El espacio no est permitido, as como ca racteres extraos.

1. 2. 3.

Aritmticos Comparacin Lgicos

Taller de Python "Episodio 1"


2. No pueden usarse las palabras reservadas de Python: and, assert, break, class, continue, def, del, elif, else, except, exec, finally, for, from, glo bal, if, import, in, is, lambda, not, or, pass, print, raise, return, try, while y yield. Veamos ahora algunos tipos de datos: El resultado es verdadero porque la H va antes que la J. Veamos otro ejemplo: >>> 'Hola'<'hola' True >>> Que ha pasado aqu? Por qu dice que es verdadero? Muy sencillo. Realmente Python compara basndose en el cdigo ASCII y la 'H' tiene un cdigo "inferior" a la 'h'. Por eso el resultado da True. Ms adelante le meteremos mano a tratamientos avanza dos sobre los datos, pero por el momento con esto nos basta.

En Python existen los enteros y los flotantes, como ya he mos visto. As mismo se pueden usar los valores booleanos True y False como ya comentamos antes. Existe tambin el tipo de datos cadena . A diferencia del C, donde las cadenas son vectores de caracteres, en Python hasta un nico carcter se considera una cadena. (internamente son vectores, pero a nosotros nos da igual por el momento. Por algo el Python es de alto nivel ) Un ejemplo: >>> mi_cadena='hola mundo' >>> print mi_cadena hola mundo >>> Como podemos ver, las cadenas se delimitan con comillas, da igual si son simples o dobles, aunque si se quieren mostrar cadenas en el texto, es conveniente delimitar la cadena con dobles y mostrar las simples: >>> mi_cadena="'hola mundo'" >>> print mi_cadena 'hola mundo' >>> Las cadenas son muy sufridas (ya lo veremos ms adelan te) y permiten muchos tipos de operaciones con ellas. A modo de abreboca, dos operaciones bsicas con cadenas son la concatenacin (con el signo + ) >>> 'abcd'+'efgh' 'abcdefgh' >>> que sera como una suma entre cadenas, y la repeticin (con el signo * ) >>> 'a'*10 'aaaaaaaaaa' >>> que repite la cadena tantas veces como se le indique. Tambin se pueden hacer comparaciones entre cadenas. Python las analiza "alfabticamente" para compararlas: >>> 'hola'<'jajeji' True >>>

Bien, vamos a escribir nuestro primer programa en Python. Hasta ahora hemos estado trasteando con el intrprete, pero ya es hora de ponernos serios. Que no os asuste, ya que este tema lo explicaremos en base al programa, y a algunas modificaciones que le iremos introduciendo, al tiempo que veremos en la prctica muchos conceptos del tema anterior. Adems este mismo programa nos servir para explicar temas de los artculos siguientes, como tra tamiento de cadenas y listas, sockets,... Bueno, primero hay que explicar que hace el programa, y luego iremos desglosando lnea a lnea segn vayamos viendo como funciona. Este programa bsicamente se conecta a Google para rea lizar la bsqueda que le pongas y te pasa el resultado de bidamente formateado y slo mostrando el nmero de re sultados que se le indique. Complicado? Puede, pero slo debido a que an no sabis que hace cada cosa. Tranquilos y tiempo al tiempo. Adems es un programa que podis usar sin problemas y es un ejemplo tan bueno como cualquier otro, y desde lue go mucho mejor que el tpico "hola mundo" que se suele hacer, verdad?

Los programas se pueden ejecutar en cualquier sistema, tanto Windows, como Linux. En Windows bastar con hacer doble click sobre l (podis crear el programa con el notepad o con el entorno idle del intrprete, o con cualquier editor que no formatee el texto como por ejemplo el Word del Office. Debis guardar el programa como .py . Os recomiendo el notepad), con un inconveniente: no veris el resultado porque cuando el programa termine, la ventana de shell se cerrar.

5/68

Taller de Python "Episodio 1"


Esto se soluciona ejecutando el programa desde una ven tana de comandos: 1. En Windows 9x, escribiendo: python programa.py 2. En Windows 2000 o XP, escribiendo simplemente: programa.py O bien aadiendo una pausa al final del programa si estis empeados en ejecutarlo con doble click, pero esto ya lo explicare ms adelante. Es decir, de momento usad la ven tana de comandos. En Linux, se puede ejecutar de dos formas: 1. Como en Windows, desde una shell escribiendo: python programa.py 2 . Po n i e n d o e n l a p r i m e r a l n e a d e l p r o g r a m a : #!/usr/bin/env python Esta lnea se encarga de buscar el intrprete en el siste ma y puede ejecutarse el script como si fuera un progra ma normal y corriente en consola, es decir: ./progra ma.py (tenis que darle permisos de ejecucin, que no se os ol vide) Bien, vamos a ejecutarlo a ver que pasa (yo usare en las pruebas, el primer mtodo en Linux, pero por nada en parti cular, aunque el segundo mtodo es mejor y recomendable): Shadowland:~/python$ ./google.py Busqueda: hackxcrack Numero de resultados: 5 http://www.<b>hackxcrack</b>.com/phpBB2/index.php http://dragonjar.nolimites.net/HTM/DragoN.php?subaction=showfull&amp; http://www.forohxc.com/Docs/Seguridad/ http://www.forohxc.com/Docs/Seguridad/ http://www.hackemate.com.ar/ezines/<b>hackxcrack</b>/ Shadowland:~/python$ CABECERA= ' <b>...</b> \n<br><font color=#008000>' FIN= ' ' NUM_RESULTADOS= 10 MAX_RESULTADOS= 50 def formateaQuery(query): from string import join a = query.split() return join(a, '+') def google(query=None, n=None): if n is None: n = NUM_RESULTADOS if query is None: print "No se ha efectuado bsqueda" return - 1 bsqueda = run (query,n) if bsqueda == -2: print 'Tu bsqueda para %s no ha arrojado resultados.' % (query.replace('+',' ')) return elif bsqueda == -1: print 'No se ha podido efectuar la conexin' return for x in bsqueda: print x def run(query,n): try: conn = httplib.HTTPConnection(URL) conn.request ("GET", COD_BUSQUEDA + formateaQuery(query)) r = conn.getresponse() except: print 'No se ha podido efectuar la conexin' return -1 if r.reason == 'OK': data = r.read() else: return -1 conn.close() aux = data.split(CABECERA) aux.pop(0) if len(aux) == 0: return -2 bsqueda = [] i=0 while n != 0 and i < MAX_RESULTADOS: try: a = aux[i].split(FIN,2)[0] if a != '': busqueda.append('http://'+a) n -= 1 except: pass i += 1 return bsqueda query=raw_input('Bsqueda: ') n=int(raw_input('Numero de resultados: ')) google(query,n)

Como podis ver, para ejecutarlo simplemente tenemos que teclear python y el nombre del programa. El programa nos pide que introduzcamos la bsqueda y luego el numero de resultados que queremos ver. Fcil, verdad? Y despus nos muestra los resultados de nuestra bsqueda. Enfermera! Guantes y bistur que vamos a proceder a la autopsia... paso por paso. Cdigo del programa: #!/usr/bin/env python import httplib URL= 'www.google.com' COD_BUSQUEDA= '/search?num=100&q=' 6/68

Taller de Python "Episodio 1"


ms exactos, la variable es de tipo cadena, porque raw_input() lee cualquier cosa que se le pase como una cadena de texto. Tambin podis observar la funcin int(). Esta funcin transforma en tipo entero el valor que se le pase. Es decir, si por ejemplo se le pasa una cadena de nmeros, lo transformara en un numero entero. En nuestro programa: n=int(raw_input()) lo que significa que (de dentro a fuera), primero se ejecuta el raw_input() con el que se obtiene una cadena y luego se transforma en un entero que se almacena en la variable n. Una forma ms clara seria: C o m o p o d e m o s o b s e r v a r, l l a m a m o s a l a f u n c i n raw_input() y almacenamos el resultado en una variable: query=raw_input() raw_input() permite el paso de parmetros en forma de cadena. Para los que conocen otros lenguajes, en especial C, sabrn que para mostrar un mensaje solicitando datos, primero se llama a la funcin de mostrar el mensaje y lue go se llama a la funcin que lee los datos. En C sera as: printf("Dame el dato:"); scanf("%c",&dato); Cuya traduccin directa al Python sera: print 'Dame el dato:' dato=raw_input() Pero (siempre hay un pero) esto no lo hace nadie. Es un desperdicio de la potencia de Python y de recursos del in trprete. La forma ms correcta de hacerlo sera: dato=raw_input('Dame el dato:') Como podis ver, raw_input() permite introducir el mensa je a mostrar por pantalla dentro de si mismo, lo cual acor ta y clarifica el cdigo, sin contar con que es mucho ms elegante. Adems posee la potencia de los lenguajes de alto nivel. Lee cualquier cantidad de datos, a diferencia de por ejem plo, el C, donde para leer una cadena habra que declarar un vector de caracteres y luego con un getchar() y un bu cle ir leyendo. Podris observar tambin que no declaramos que tipo de variable usamos para contener los datos recibidos de raw_input(). Python lo hace automticamente, y para ser n=raw_input() aux=int(n) n=aux Bien, ya sabemos como introducir datos. Ahora veremos como mostrar datos.

Lectura de datos desde el teclado


En Python, la funcin predefinida que se encarga de recibir datos del teclado es raw_input(). Esta funcin detiene la ejecucin del programa en espera de que el usuario introduzca datos por el teclado hasta re cibir un retorno de carro. Veamos nuestro programa de ejemplo: query=raw_input('Bsqueda: ') n=int(raw_input('Numero de resultados: '))

Mostrar datos por pantalla


Veamos otros trozos de nuestro programa: print 'No se ha podido print 'No se ha podido efectuar la efectuar conexin'la conexin' ..... ..... print x print x ..... ..... print 'Tu bsqueda para %s no ha arrojado resultados.' % (query.replace('+',' ')) print 'Tu bsqueda para %s no ha arrojado resultados.' % (query.replace('+',' ')) La funcin que muestra datos por pantalla, como ya ha bris deducido es print. Como veis, lo que se va a impri mir se debe introducir entre comillas, ya que es una cade na. Si no se hace as Python dar error. Y "x? No est entre comillas? No, porque x no es una cadena, sino una variable previa mente declarada y con un valor almacenado. Si a print le pasamos un parmetro sin comillas, lo interpreta como una variable y muestra el contenido de dicha variable por pantalla. De ah que si se escribe un texto sin poner las co millas de error. Python lo interpretara como una variable e intentar mostrar su valor por pantalla, pero como dicha variable no existir (a no ser que haya una coincidencia muy extraa), dar error: print hola Traceback (most recent call last): File "<stdin>", line 1, in ? NameError: name 'hola' is not defined Como veis Python se queja de que la variable "hola" no existe. Error nuestro ya que lo que queramos hacer era

7/68

Taller de Python "Episodio 1"


mostrar la cadena 'hola' por pantalla, pero no pusimos las comillas. print tambin permite el paso de varios parmetros as como operar con las cadenas dentro de l. Los parmetros van separados por comas. La coma hace que se consideren por separados y a efectos de impresin aparece como una pulsacin de la tecla espacio en pantalla. Como dijo alguien una vez, "se hace camino al andar..." Probemos el print: (usaremos de nuevo el intrprete ya que es ms rpido que editar un programa) >>> a=12 >>> b='hola que tal...' >>> print 'probando',a,'\n',b,'\n\n' probando 12 hola que tal... >>> Hemos creado dos variables, "a" y "b" y les hemos metido un entero y una cadena respectivamente. Despus hemos usado print para imprimir un mensaje, unos cuantos intros (la \n es el intro) y los contenidos de las variables. Sencillo, verdad? print tambin permite usar la concatenacin y la repeticin (teniendo en cuenta que son operaciones dispo nibles SLO para cadenas): >>> print 'probando otra vez'+b*5 probando otra vezhola que tal...hola que tal...hola que tal...hola que tal...hola que tal... >>> Hemos imprimido una cadena y luego una cadena conteni da en una variable repetida cinco veces, usando el "*". El "+" hace que se imprima junto. Si os fijis no aparece un espacio entre "vez" y "hola". Como ya dije antes, la coma de separacin imprime un espacio. Si quisiramos que usando la concatenacin (+) apareciera un espacio entre "vez" y hola" tendramos que ponerlo explcitamente den tro de la cadena, tal que as: "probando otra vez " (veis el espacio?) Pero fijaos que todo son cadenas, incluyendo lo que con tiene la variable. Si intentramos imprimir tambin la variable "a" de esta forma: >>> print 'probando otra vez'+a+b*5 Traceback (most recent call last): File "<stdin>", line 1, in ? TypeError: cannot concatenate 'str' and 'int' objects Pero ya tenemos ah otra vez el maldito espacio. Y si no lo queremos? Fcil, usaremos la funcin str() >>> print 'probando otra vez'+str(a)+b*5 probando otra vez12hola que tal...hola que tal...hola que tal...hola que tal...hola que tal... >>> Ya no salen espacios!!! str() convierte a cadena cualquier cosa que se le pase co mo parmetro (tened en cuenta y recordad de ahora en adelante que un parmetro puede ser tanto explcito, po niendo los datos a pelo, como variables, donde lo que se convierte es su contenido). En este caso, convierte el con tenido de "a" en una cadena, o sea, convierte el entero 12 en la cadena de texto '12'. Es como el inverso de la funcin int() que hemos mencionado antes. Slo nos queda explicar una ltima forma de usar la funcin print: las cadenas de formato. Las cadenas de formato son una forma de poder represen tar valores de variables dentro de una cadena sin tener que hacer uso de lo antes explicado, aunque todo es com plementario y podis usar lo que queris a la hora de im primir por pantalla. En nuestro programa:
print 'Tu bsqueda para %s no ha arrojado resultados.' % (query.replace('+',' ')) print 'Tu bsqueda para %s no ha arrojado resultados.' % (query.replace('+',' '))

Python nos avisa que no puede usarse la concatenacin con enteros y cadenas. La forma correcta sera: >>> print 'probando otra vez',a,b*5 probando otra vez 12 hola que tal...hola que tal...hola que tal...hola que tal...hola que tal... >>>

Un ejemplo simple de formato: >>> a=134 >>> b=12.5 >>> c='hola caracola' >>> print 'El valor de a es %d, el de b %f y el de c %s' %(a,b,c) El valor de a es 134, el de b 12.500000 y el de c hola caracola >>> Aqu podemos ver los tres tipos ms comunes (hay otros) de indicadores de cadenas de formato: %d, %f y %s. El primero sirve para enteros, el segundo para flotantes y el tercero para cadenas. Tenemos tres variables, una con un entero, otra con un flotante y la tercera con una cadena. Se meten los carac teres de formato dentro de la cadena a imprimir y luego se hace uso del operador % para imprimir por orden los

8/68

Taller de Python "Episodio 1"


parmetros que se le pasen, en este caso las tres variables (si slo se pasa un parmetro los parntesis son opciona les). En nuestro programa lo que le pasamos a la cadena de formato %s es la variable query formateada (como la for mateamos lo veremos en el siguiente articulo junto con muchas otras formas de tratamiento). Bueno, espero haberme explicado bien ya que ahora pasa remos al siguiente punto del tema: el control de flujo del programa. Veamos un ejemplo en nuestro programa: if r.reason == 'OK': data = r.read() else: Como podemos ver primero va el if seguido de la condicin a evaluar, en este caso si el contenido de "reason" es igual a la cadena 'OK' y finalizando con los dos puntos (aqu es cuando tenis que recordar todos los operadores que ex p l i c a m o s a l p r i n c i p i o d e l a r t i c u l o , e s d e c i r, l o s d e comparacin, lgicos y dems) Despus lo que hacemos es tabular las instrucciones que queremos que vayan dentro del if (en este caso slo una) y cuando finalicemos las tabulaciones el if habr finalizado. Bien, con lo que sabemos hasta ahora podramos hacer programas ms o menos complejos pero serian lineales, ejecutados de arriba a abajo, sin posibilidad de elegir que ejecutar y que no. Esto se solventa con las instrucciones de control de flujo, es decir, los condicionales y los bucles. Un apunte ms antes de meternos en materia. En Python las instrucciones se separan con intros, es decir, que a di ferencia de otros lenguajes de programacin, como por ejemplo el C que separa las instrucciones con punto y co ma y puedes llegar a escribir el programa en una sola lnea (cosas ms raras se ven), en Python es obligatorio separar las instrucciones con intros. Tambin hay otra obligacin que tiene que ver con los bucles y condiciones, y que aho ra veremos. Entremos en tema... Os pondr otro ejemplo ms simple y clarificador. Que pa sa si intentamos dividir entre cero? Que no tiene solucin, y si intentamos hacerlo en un lenguaje de programacin, el que sea, dar error. En python: Shadowland:~$ python Python 2.3.4 (#2, Sep 24 2004, 08:39:09) [GCC 3.3.4 (Debian 1:3.3.4-12)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> 7/0 Traceback (most recent call last): File "<stdin>", line 1, in ? ZeroDivisionError: integer division or modulo by zero

if...elif...else
La estructura if permite introducir condiciones en la ejecucin del cdigo del programa. Su sintaxis es: if condicin: instruccin instruccin instruccin ... [continua el programa] Analicemos brevemente la teora. Como vemos la sintaxis es simple. Primero va el if con su condicin y finaliza con dos puntos (los dos puntos son importantes. Si no se po nen Python dar error). A continuacin vienen las instruc ciones que se ejecutaran SI la condicin es verdadera. En caso contrario no se ejecutaran. Y como sabemos que es lo que va dentro del if y lo que no? Fcil, es la otra "obligacin" del Python: las tabulaciones. Python reconoce las nuevas instrucciones mediante los in tros y adems usa las tabulaciones para diferenciar si es tas estn dentro o fuera de un bucle, una condicin, una funcin,....

Si intentamos dividir un numero entre cero da error. Bien, supongamos que tenemos este trozo de cdigo: a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) print a/b Sencillo, y si lo ejecutamos nos pide dos nmeros y divide el primero entre el segundo. Pero que pasara si el segun do numero fuera un cero. Que nos dara error como arriba. Como solucionarlo? Dicindole al python que si el segundo numero es un cero, que no ejecute la divisin, as: a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) if b!=0: print a/b As el programa slo ejecutara la divisin si el segundo nu mero es distinto (el operador != ) de cero. Fcil. Pasemos a la segunda parte del condicional: else El programa de divisin funciona pero no es muy eficaz y mucho menos elocuente. Si, evita la divisin entre cero pero no nos permite mostrar un mensaje diciendo que la divisin entre cero no esta permitida. Veamos por que:

9/68

Taller de Python "Episodio 1"


Si le aadimos a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) if b!=0: print a/b print 'La divisin por cero no esta permitida Aunque la divisin sea correcta y el if se ejecute porque el segundo numero no sea cero, el print del final se ejecutara igual. Esto se podra solucionar as: a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) if b!=0: print a/b if b==0: print 'La divisin por cero no esta permitida' Es correcto pero ni es elegante, ni eficiente. Python tiene que evaluar dos condiciones cuando no es necesario. Para eso existe el else: a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) if b!=0: print a/b else: print 'La divisin por cero no esta permitida' El else lo que hace es darle una segunda opcin, o mejor dicho una opcin por defecto, es decir, que si el if no es verdadero, se ejecuta el else. Si el if es verdadero el else no se ejecuta ni se procesa ni nada. consume menos re cursos, es ms bonito y elegante, etc, etc... Si lo traducimos a lenguaje humano bsicamente seria co mo si hiciramos: SI b DISTINTO_DE 0 HAZ: ...... SINO HAZ: .... La sintaxis del else es sencilla: if: .... else: instruccin instruccin .... [continua programa] Que nos queda? Que es ese elif que has puesto antes en el titulo del apartado? Tranquilos, que ahora voy a ello. Pero si es como un if!!!! Evala una condicin y si es ver dadera ejecuta el cdigo de dentro!!! FALSO! O s l o e x p l i c a r e c o n n u e s t r o p r o g ra m a d e d i v i s i n . Imaginemos que por una extrao y retorcido motivo de la fsica cuntica del universo (pedazo de frase sin sentido verdad? ), queremos que nuestro programa de divisin adems de impedir la divisin entre cero tambin impida la divisin cuando los dos nmeros son iguales (muy extrao pero es un ejemplo, as que no os quejis). Como lo haramos? Vamos a cambiar la estructuracin de la condicin pero es el mismo programa: a=int(raw_input('Dame un numero a dividir:')) a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) b=int(raw_input('Dame el divisor:')) if b==0: if b==0: print 'La divisin por no esta permitida' print 'La divisin por cero no cero esta permitida' else: else: if a==b: if a==b: print 'Los dos nmeros son iguales y no vamos a dividirlos' print 'Los dos nmeros son iguales y no vamos a dividirlos' else: else: print a/b print a/b Esto es lo que se conoce como if anidados, pero es horrible a la vista aunque no os lo creis. El cdigo funciona y se lee ms o menos bien pero es porque hay pocas condicio nes anidadas unas dentro de otras, pero ahora imaginaos 50 if unos dentro de otros. Tendiendo en cuenta que hay que tabular ms cada vez que se crea un nuevo if al final no se podra leer de la lnea tan larga que saldra slo a base de tabulaciones. Solucin: elif Sintaxis de elif: if condicin: ... elif condicin: .... elif condicin: .... else: ... Pueden ponerse tantos elif como se necesiten. elif equivale a las instrucciones else if unidas en uno. Veamos ahora el pro grama de la divisin hecho con elif: Veamos nuestro programa google.py: if bsqueda if == -2: bsqueda == -2: print 'Tu bsqueda para %s no ha % (query.replace('+',' ')) print 'Tu bsqueda para %s noarrojado ha arrojadoresultados.' resultados.' % (query.replace('+',' ')) return return elif bsqueda == -1: elif bsqueda == -1: print 'No se print ha podido efectuar la conexin' 'No se ha podido efectuar la conexin' return return

10/68

Taller de Python "Episodio 1"


a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) if b==0: print 'La divisin por cero no esta permitida' elif a==b: print 'Los dos nmeros son iguales y no vamos a dividirlos' else: print a/b Bastante ms legible y claro. El else con el if dentro de el se ha transformado en un elif y nos ahorramos tabulacio nes y ganamos en claridad de cdigo y en optimizacin. Un apunte extra: elif nos facilita enormemente la creacin de mens de seleccin. Os lo dejo como ejercicio, que si no os malacostumbrais Pasemos a la siguiente estructura de control: el bucle #contador.py i=0 while i<10: print i i=i+1 Shadowland:~/python$ python contador.py 0 1 2 3 4 5 6 7 8 9 Shadowland:~/python$ El programa crea una variable i con valor igual a cero y luego entra en el while el cual se ejecuta siempre que i sea menor que 10. Dentro del while hay un print que nos muestra el valor de i por pantalla y una instruccin i=i+1 que lo que hace es sumar 1 a la variable (incrementa la variable).

while
Como podemos hacer que una parte de nuestro cdigo se ejecute continuamente hasta que nosotros queramos? Usando un bucle, y eso es lo que es el while. Su sintaxis es: while condicin: instruccin instruccin ...... [continua programa] Veamos un ejemplo en nuestro programa google.py: while n != 0 and i < MAX_RESULTADOS: try: a = aux[i].split(FIN,2)[0] if a != '': busqueda.append('http://'+a) n -= 1 except: pass i += 1 Vale es un poco complejo al principio pero no demasiado. Paso por paso. Cuando python llega al while evala la condicin y si es cierta ejecuta todo lo del bucle y vuelve al while para vol ver a evaluar y seguir haciendo hasta que la condicin sea falsa. En este caso la condicin es que la variable n sea distinta de cero (n!=0) Y (and) que la variable i sea m e n o r q u e l a va r i a b l e M A X _ R E S U LTA D O S (i<MAX_RESULTADOS). Mientras sea verdadero, el while se ejecutara una y otra vez. Un ejemplo ms simple: un contador. Si creamos este programa y lo ejecutamos:

NOTA
el i=i+1 se puede sustituir (y se hace de normal) por i+=1 (podis verlo en el trozo de google.py). Esta contraccin tambin funciona con multiplicaciones, divisiones, restas,.... siempre y cuando la variable origen y la destino sean la misma (en este caso si, porque la variable i se usa como parte de la suma y al mismo tiempo como lugar donde almacenar el nuevo resultado).
Por que metemos el incremento? Porque si no aumentamos el valor de i, al valer en un principio cero, el while siempre seria verdadero y tendramos un bucle infinito (es decir, la pantalla inundada de nmeros sin parar nunca ) As como esta el programa podemos ver como la variable i se va incrementando uno a uno gracias al print y ver que finaliza cuando llega a 9 (si recordis while i<10). Cuando i llega a valer 10 el while ya no es verdadero y finaliza, y como no hay nada ms despus, finaliza el programa. Sencillo? Espero que si, y que lo vayis comprendiendo to do, ya que al final del articulo os pondr un ejercicio y es pero que posteis en el foro todas vuestras dudas y si os animis, el resultado del ejercicio y que problemas os ha dado Bueno, bueno, que esto se acaba. Nos quedan dos estruc turas ms y un ultimo punto y finalizamos. Creo que no se ha hecho muy largo, no? Y sin ms prembulos, la estructura

11/68

Taller de Python "Episodio 1"


for ... in ...
El problema del bucle while es que siempre tiene que tener un incremento o algo que haga que la condicin sea falsa para poder pararlo cuando nos interese, y aunque en mu chas ocasiones lo usaremos, en otras no es tan recomen dable. Para esas ocasiones existe el bucle for-in (PARA CADA elemento EN conjunto HACER). El bucle for-in es autoincremental, es decir que no hace falta ponerle un incremento como al while (lo que tambin tiene sus pros y sus contras, pero eso se ve con la prctica y la prueba-error), y su sintaxis es: for variable in serie: instruccin instruccin .... [continua programa] Veamos el ejemplo en nuestro google.py: for x in bsqueda: print x Simple y claro. Para cada valor de la variable x en el con j u n t o b s q u e d a i m p r i m e e n p a n t a l l a e l va l o r d e x . Nuevamente observamos que en python las variables no tienen que ser declaradas hasta que vayan a usarse. En google.py la lista "bsqueda" existe ya y se ha formateado y se han hecho operaciones con ella, pero la variable x no existe y se crea exclusivamente para ser usada por el for, ya que el for-in necesita una variable que sea la que se "incrementa", y aqu es la "x" Otro ejemplo en un programa simple. Vamos a cambiar nuestro antiguo contador hecho con un while por un conta dor hecho con un for-in: #contador2.py for i in range(0,10): print i Ejecutmoslo: Shadowland:~/python$ python contador2.py 0 1 2 3 4 5 6 7 8 9 Shadowland:~/python$ primer valor, y tampoco aparece el incremento de i porque el for-in la autoincrementa. Y que es ese range(0,10) que ha puesto ah? Existe una funcin que se usa mucho en un for-in cuando tratas con rango de nmeros: es la funcin range(). range() lo que hace es crear un "conjunto" de valores con los nmeros que haya entre un valor inicial y un valor final menos uno. Es decir, que si ponemos range(0,10) estamos creando un conjunto con los valores 0 al 9 (el 10 no se usa porque el ultimo valor no lo coge. Recordad: valor final menos uno), que es lo que usara el for-in para asignar e incrementar a la variable i. Difcil? Espero que no, aunque la dialctica no es lo mio Bueno, slo nos queda una estructura por tratar. En un principio pens en no incluirla ya que os podra confundir un poco pero bueno, estis para aprender, as que:

try ... except


Esta estructura se utiliza para la condiciones de error. Estoy loco? No, veamos... Es como un if slo que no se le indica una condicin para que se ejecute, sino que python ejecutara el try y no har caso del except a no ser que python de un en la ejecucin de las instrucciones dentro del try. Veamos su sintaxis y luego veremos un par de ejemplos: try: instruccin instruccin ..... except: instruccin instruccin .... [continua el programa] En nuestro google.py: try: conn = httplib.HTTPConnection(URL) conn.request ("GET", COD_BUSQUEDA + formateaQuery(query)) r = conn.getresponse() except: print 'No se ha podido efectuar la conexin' return -1 El programa intentara crear una conexin a Google y si fa lla entonces se ejecuta el except avisndonos de ello. Un ejemplo sencillo, y sin sockets que los veremos en otro

Hace lo mismo pero podis ver que el programa ya no de clara i=0 antes ya que el for-in declara la i y le asigna si

articulo (tiempo al tiempo). Volvamos a nuestro programa de divisin (versin if-else sin elif). Tenamos:

12/68

Taller de Python "Episodio 1"


a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) if b!=0: print a/b else: print 'La divisin por cero no esta permitida' Con try y except quedara as: a=int(raw_input('Dame un numero a dividir:')) b=int(raw_input('Dame el divisor:')) try: print a/b except: print 'La divisin por cero no esta permitida' La salida de este programa, que hace la raz cuadrada de 9, seria 3.0 (con decimales porque la funcin sqrt transfor ma el dato a flotante si no lo era). La segunda forma sirve para importar todas las funciones disponibles en el modulo en cuestin. Se usa cuando sabes que vas a usar muchas funciones del modulo y es extre madamente largo definirlas todas una a una con el primer mtodo, o cuando sabes que vas a usar funciones pero no sabes cuantas y as te ahorras tener que modificar el pro grama una y otra vez aadiendo funciones al import. La tercera forma es similar a la segunda con una pequea diferencia. En vez de importar todas las funciones presen tes en el modulo, lo que hace es (al menos eso creo por que no lo he encontrado en ningn sitio) crear una especie de PATH de bsqueda de forma que si llamas a una funcin que no esta por defecto en python, este la busca en las li breras que hayas importado, aunque hay que especificr selo as: Si hacemos import math para usar la funcin sqrt() tendremos que usarla as math.sqrt() Como veis, esta forma difiere un poco de las otras dos en la forma de utilizacin. Cual usar? Pues la que queris siempre que os sintis cmodos. Evidentemente si slo vais a usar una funcin externa, el primer mtodo es el idneo, pero si vais a usar varias, depender de que mto do os guste ms. Yo suelo usar el segundo y el tercero segn mi experiencia y comodidad. Vosotros mismos Como hacer una relacin de mdulos y funciones seria de masiado largo... no lo haremos. No obstante en la ayuda de Python, bajo el epgrafe Library Reference, encontrareis los mdulos principales y las funciones que contiene cada uno. Adems os invito a preguntarme en el foro cualquier duda que tengis. Y con esto y un bizcocho, hasta el prximo articulo a las ocho Y como colofn os voy a poner un ejercicio para que prac tiquis y veis que os da error y que no, etc, etc... Tambin os invito a que me preguntis las dudas que ten gis acerca del ejercicio, y del resto del articulo, y si no me estropea los artculos posteriores (que si no pierdo be neficios ) os contestare gustoso. Ejercicio: Hay una mxima que dice: Los programadores estn en conflicto constante con el Universo. Los programadores intentando crear mayores y mejores programas a prueba de idiotas y el Universo creando mayores y mejores idiotas.

Cuando debemos usar try-except? Cuando sepamos que python puede darnos un error y as ahorrarnos una condicin que puede ser difcil de escribir, adems de inne cesaria. En este caso, si sabemos que python da error cuando se divide por cero, porque usar un if para compro bar si el divisor es cero? Nosotros los intentamos igual con el try y si resulta que hemos introducido un cero como di visor y python se queja, entonces se ejecutara el except y en vez de fallar el programa, se ejecutara lo que haya den tro del except, en este caso el print avisndonos de que estamos dividiendo por cero. Copiado y archivado? Eso espero Y hemos llegado al ultimo punto de este Quick & Dirty Python Article n1

Python posee mltiples mdulos importables con funciones que nos facilitan la tarea de programar. Hemos visto algu nas que vienen por defecto como int(), str(), range(),... pero muchas otras tienen que ser importadas para ser usadas, como por ejemplo la funcin de raz cuadrada sqrt() Esta funcin esta presente en el modulo math que es una librera de funciones matemticas. Otras funciones que po see son por ejemplo: seno, coseno, tangente, etc... Hay tres formas de importar funciones en python: 1. from modulo import funcin 2. from modulo import * 3. import modulo La primera forma sirve para importar una funcin concreta de un modulo. Veamos un programa que hace raz cuadra da: from math import sqrt print sqrt(9)

13/68

Taller de Python "Episodio 1"


Mi antiguo profesor me deca: "Un programa slo es un buen programa si su numero de errores tiende a ce ro. De aqu deducimos que Microsoft no hace buenos programas..." Dejando de lado la evidente fobia que tenia mi profesor hacia la empresa americana que todos conocemos y ama mos / odiamos, tenia razn. Nunca podis saber quien va a acabar usando un programa escrito por vosotros. Aunque lo escribis para uso propio, alguna vez se lo dejareis a un amigo, y ah se acabo el uso propio. De ah a verlo en la mula o en una web del estilo de Softonic o similar hay un paso.

ejercicio.py

#!/usr/bin/env python import math opcin=0 while opcin!=6: print 'Calculadora de prueba v1.0 (by Moleman)\n' print '1. Sumar' print '2. Restar' print '3. Multiplicar' print '4. Divisin entera' print '5. Raz cuadrada' print '6. Salir' opcin=int(raw_input('Escoge el numero de opcin: ')) if opcin==1: a=int(raw_input('\nPrimer numero: ')) b=int(raw_input('\nSegundo numero: ')) print '\nResultado:',a+b,'\n\n' elif opcin==2: a=int(raw_input('\nPrimer numero: ')) b=int(raw_input('\nSegundo numero: ')) print '\nResultado:',a-b,'\n\n' elif opcin==3: a=int(raw_input('\nPrimer numero: ')) b=int(raw_input('\nSegundo numero: ')) print '\nResultado:',a*b,'\n\n' elif opcin==4: a=int(raw_input('\nPrimer numero: ')) b=int(raw_input('\nSegundo numero: ')) print '\nResultado:',a/b,'\n\n' elif opcin==5: a=int(raw_input('\nNumero: ')) print '\nResultado:',math.sqrt(a),'\n\n' elif opcin==6: print '\nGracias por volar con aerolneas Moleman... estooo, por usar la Calculadora v1.0\n\n' else: print '\nOpcion incorrecta. Vuelve a probar...\n\n'

Bien, el ejercicio consiste en coger el programa que os voy a poner y modificarlo para evitar que falle de ninguna ma nera, ya sea por introducir datos invlidos o por cualquier otra razn. Y as adems practicareis todo lo visto. Mejoradlo todo lo que podis. El programa funciona perfec tamente pero se puede conseguir que falle muy fcilmen te. Para los ms observadores, si, lo reconozco. Es una calculadora! Pero bueno, tarde o temprano tenia que apa recer verdad? Adems slo es un ejercicio para practicar y si contis con el google.py creo que podrais disculpar me, no? Pues eso es todo. Espero que hayis disfrutado con el arti culo y que continuis. En la siguiente revista ms. PD: se me olvidaba. Los comentarios en el cdigo se po nen as #esto es un comentario con el smbolo almohadilla " # " delante. Saludos...

Agradecimientos a HpN, HxC y a mi mujer por soportarme continuamente (va por ti Marta)

14/68

You might also like