lunes, 29 de diciembre de 2008

Python con API de Windows

Una de las capacidades interesantes de programación de Python es el acceso a las funciones API de Windows. Esto se puede hacer con Pywin32. Para descargar esta extensión haga clic aquí.

Una excelente referencia es la de Mark Hammond, para acceder a los ejemplos y la explicación haga clic aquí.

sábado, 27 de diciembre de 2008

Programación orientada a objetos con Python

Este artículo no se trata de un análisis profundo de la programación orientada a objetos, sino simplemente de una simple y breve introducción, intentando dar un panorama inicial a aquellos que no han tenido contacto con (o nunca han entendido) la POO.

Supongamos que usamos un lenguaje procedural como Pascal para el siguiente ejemplo:


program personas;

type persona = record
nombre: string;
apellido: string;
edad: integer
end;

procedure inicializar(n, a: string; e: integer; var p: persona);
begin
p.nombre := n;
p.apellido := a;
p.edad := e
end;

function es_mayor(p: persona): boolean;
begin
return p.edad >= 18
end;

function nombre_completo(p: persona): string;
begin
return p.nombre + ” ” + p.apellido;
end;

var
p: persona;

begin
inicializar(”Juan”, “Perez”, 25, p);
write(nombre_completo(p));
if (es_mayor(p)) then
writeln (” es mayor de edad.”)
else
writeln (” es menor de edad.”)
end.

El programa es bastante sencillo. Primero declaramos un tipo persona que es un registro que contiene los campos nombre, apellido y edad. Luego definimos el procedimiento inicializar que toma el nombre, el apellido, la edad y la persona y asigna los primeros a los campos correspondientes de la última. Luego, un par de funciones (es_mayor y nombre_completo) toman una persona y realizan cálculos sobre los valores de sus campos.

En los programas procedurales hacemos esto todo el tiempo: definimos estructuras y tipos de datos y luego creamos procedimientos y funciones que toman como parámetros variables de estos tipos y realizan distintas operaciones sobre ellos. Dicho de otra manera: podemos ver a los programas procedurales como un conjunto de procedimientos y funciones que manipulan estructuras de datos pasadas como parámetros.

A continuación, un ejemplo de la versión orientada a objetos utilizando el lenguaje Python:


class Persona:

def __init__(self, nombre, apellido, edad):
self.nombre = nombre
self.apellido = apellido
self.edad = edad

def nombre_completo(self):
return self.nombre + ‘ ‘ + self.apellido

def es_mayor(self):
return self.edad >= 18

p = Persona(’Juan’, ‘Perez’, 25)

print p.nombre_completo(),

if p.es_mayor:
print “es mayor de edad.”
else:
print “es menor de edad.”

Como podemos apreciar, el constructor de la clase se declara como __init__, en tanto que la referencia al objeto actual se llama self (y debe aparecer como primer parámetro de todos los métodos de la clase, aunque no se utiliza en la invocación de los mismos).


REFERENCIAS ADICIONALES:

Programacion orientada a objetos en Python. http://blog.rvburke.com/2006/11/22/programacion-orientada-a-objetos-en-python/

Programacion orientada a objetos. http://blog.smaldone.com.ar/2006/10/27/programacion-orientada-a-objetos/

Programación de Threads con Python

¿QUE ES UN THREAD?
Aquí tienen una definición:

“Una hebra es una unidad básica de utilización de la CPU; comprende un ID de hebra, un contador de programa, un conjunto de registros y una pila. Comparte con otras hebras que pertenecen al mismo proceso la sección de código, la sección de datos y otros recursos del sistema operativo, como los archivos abiertos y las señales. Un proceso tradicional (o un proceso pesado) tiene una sola hebra de control. Si un proceso tiene, por lo contrario, múltiples hebras de control, puede realizar más de una tarea a la vez.” [Fundamentos de sistemas operativos (Septina edicion en Español), Autores: Silberschatz, Galván, Gagne ISBN: 84-481-4641-7 Editorial McGraw-Hill]

Esta es otra definición:

“En la mayoría de los sistemas operativos tradicionales, cada proceso tiene un espacio de direcciones y un único hilo de control. De hecho, esa es casi la definición de un proceso. Sin embargo, con frecuencia existen situaciones en donde se desea tener varios hilos de control que compartan un único espacio de direcciones, pero que ejecutan de manera quasi-paralela, como si fuera de hecho procesos independientes (excepto por el espacio de direcciones compartido)” [Sistemas Operativos Modernos Autor: Andrew S. Tanenbaum ISBN: 968-880-323-5 Editorial: Prentice Hall]

¿PARA QUÉ SIRVE?

“Los hilos se inventaron para permitir la combinación del paralelismo con la ejecución secuencial y el bloqueo de las llamadas al sistema” [Sistemas Operativos Modernos Autor: Andrew S. Tanenbaum ISBN: 968-880-323-5 Editorial: Prentice Hall]

¿CÓMO PROGRAMAR UNO EN PYTHON?

Bueno basta de citas y de libros, si están leyendo esto es por que quieren hacer hilos en python. Para esto tendremos que importar el paquete threading. Y luego crear una clase que herede de threading.Thread. Si queremos que esta clase tenga un constructor propio tendrá que invocar también al constructor de Thread. Esto lo hace invocando a threading.Thread.__init__(self).

Dentro de la clase rescribiremos el método run. Y dentro de el pondremos el código que queramos que ejecute nuestro hilo.

Luego instanciaremos un objeto con nuestra clase. Y para que empiece a ejecutar solo tendremos que invocar al método start de nuestro objeto.

Un ejemplo simple podría ser el de hilo.py

#!/usr/bin/python
# Nombre de Fichero : hilo.py
import threading
from time import sleep

class Hilo(threading.Thread):
def __init__(self, id):
threading.Thread.__init__(self)
self.id = id

def run(self):
sleep(3-self.id)
print "Yo soy %s la variable d tiene el valor %s"%(self.id,d)

d=1;
hilos = [Hilo(1),
Hilo(2),
Hilo(3)]

for h in hilos:
h.start()

fijemosnos que todos los hilos comparten la variable d.

A continuación un ejemplo de cómo se ejecutan dos programas secuenciales con hilos. Acá esta el código que hice espero que a alguien le sirva.

#!/usr/bin/python
# Nombre de Fichero : lote.py
import threading
from os import system
from time import sleep

class Trabajo(threading.Thread):
"""
Esta es la clase Trabajo. Los Trabajos se pueden ejecutar de 4 maneras
Que esperen a estar solos para ejecutarse.
Que esperen a estar solos para ejecutarse y no dejar ejecutar ningun otro hasta terminar.
Que no dejen ejecutar a ninguno otro hasta terminar.
Que se ejecuten sin restricciones mientras los otros lo dejen
"""
def __init__(self, id, cmd, entroSolo = False ,salgoSolo = False):
threading.Thread.__init__(self)
self.cmd = cmd
self.id = id
self.entroSolo = entroSolo
self.salgoSolo = salgoSolo

def run(self):
system(self.cmd)

print "lotePy 0.0.1"

tabajos = [Trabajo(1,"calc",True,True),
Trabajo(2,"Notepad",True),
Trabajo(3,"dir c:\\",True)]

for t in tabajos:
while (t.entroSolo) and (threading.activeCount() != 1):pass
t.start()
if (t.salgoSolo):
t.join()






Programación de Sockets con Python

Un socket nos permite comunicarnos con otras computadoras, de esa manera la informacón puede viajar libremente por todos lados. Mucha gente se aterroriza al enterarse que tiene que desarrollar alguna aplicación haciendo uso de sockets, pues el dia de hoy descubriremos que no es nada del otro mundo, este manual se enfoca solamente a sockets en Python, si alguna vez han trabajado con sockets en C se darán cuenta que en Python es mucho más fácil (que no lo es??), bueno, los puntos que trataremos en este tutorial son:
  • Estructura de un socket.
  • Algunos elementos del socket.
  • Programacion orientada a sockets.
  • Hola mundo del socket.
  • Un hola mundo real.
  • Un pequeño chat.
  • Sockets con clase.
  • Base de cliente telnet.
Existen tres dominios de comunicación para un socket:
  • a) El dominio de UNIX. (AF_UNIX)
  • b) El dominio de internet. (AF_INET)
  • c) El dominio NS.

El dominio de UNIX. (AF_UNIX)

Se utiliza para la comunicacón entre procesos del sistema.

El dominio de internet. (AF_INET)

Se utiliza en procesos que se estan comunicando atravéz de TCP(UDP)/IP, es el que veremos.

El dominio NS.

Se utilizaba sobre los procesos que se comunicaban sobre el protocolo de comunicación de Xerox.

Python solo soporta los dos primeros tipos de comunicacón, solamente trataremos con la familia AF_INET.

Estos son algunos elementos que pertenecen a los sockets:

SocketDescripcion
socketCrea un socket del tipo y familia especificada.
socket.acceptAcepta nuevas conexiones.
socket.connectConecta el socket a la dirección dada en el puerto dado.
socket.sendEnvia datos al socket especificado.
socket.recvRecive información.
Programación orientada a sockets.


No es muy complejo adaptarse a la manera en que trabajan los sockets, primero que nada se necesita una aplicacion que haga el trabajo de servidor, las principales cosas que hace un servidor son las siguientes:
  • Ser creado.
  • Ser asignado a una dirección y darle un puerto.
  • Esperar por nuevas conexiones.
  • Aceptar nuevas conexiones.
Eso es lo basico que hace un servidor, claro que tambien es importante que mande y reciva información.
Después se crean los clientes, lo que realizan los o el cliente es:
  • Ser creado.
  • Conectarse a una dirección y puerto dado.
Simple no, claro que tambien es importante que mande o reciba información.

Un hola mundo del socket??


Bueno, basta de tanta teoría, comenzemos con lo bueno.
Pues asi es, lo que haremos a continuación es como un hola mundo en los sockets, crearemos un servidor al cual nos vamos a conectar por medio de telnet.
Bueno, pues comencemos con código:

# hls.py
# Creamos un servidor al cual nos podremos conectar.

import socket

server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind(("", 8000))
server.listen(1)
server.accept()


Y ¿que es lo que estamos haciendo con esto?, pues es sencillo vamos a verlo por pasos:

import socket

Importamos el modulo de los sockets.

server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

Creamos el socket de la familia AF_INET y del tipo SOCK_STREAM.

server.bind(("", 8000))

Le asignamos una dirección y un puerto al servidor, por medio de una tupla (add, host).

server.listen(1)

Permite al servidor aceptar conexiones.

server.accept()

Acepta una nueva conexion.

Una vez que este Script es ejecutado nos damos cuenta que lo unico que hace es que abre una terminal, uno se pregunta, y esto de que me sirve, bueno, a continuación telneteamos al servidor que acabamos de crear:

Telnet localhost 8000

El cliente (Telnet) se conectará al servidor y este se cerrará, pues solamente le dijimos que aceptara una conexón.

Ahora un hola mundo

Bueno, si quieren un hola mundo mejor hecho hagamos lo siguiente:

# hlsd.py
# Creamos un servidor al cual nos podremos conectar y nos da la bienvenida.

import socket

server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind(("", 8000))
server.listen(5)
while 1:
add, port = server.accept()
add.send("hola mundo!!!")


Lo unico nuevo aqui es esto:

server.listen(5)
while 1:
add, port = server.accept()
add.send("hola mundo!!!")

Lo del socket.listen(5) nadamás se refiere a que ahora es capaz de retener 5 conexiones (no se refiere al total de conexiones, si no como que al total que hay en espera) antes de rechazar alguna, despues esta lo del ciclo infinito, (while 1:) bueno, asi es, nuestro nuevo servidor estara aceptando conexiones por siempre, y cuando alguien se conecta guardara la tupla que nos regresa el server.accept() en las variables de add y port respectivamente, despues le enviará un mensaje al cliente, el hola mundo.

Y que es lo grandioso de los sockets??

Para todos aquellos que estan comenzando a desesperarse porque no hemos hecho aplicaciones utiles, pues ahora vamos a realizar un tipo de chat, no es muy estetico, pero es un comienzo.
# servchat.py
# Creamos un servidor de chat.

import socket
import select

def accept_new_connection():

try:
global server
global desc
newsock, (remhost, remport) = server.accept()
server.settimeout(.1)
print "Se ha conectado %s:%s" % (str(remhost), str(remport))
desc.append(newsock)
except:
pass

def broadcast(msg, sock):

global desc
global server
host, port = sock.getpeername()
msg = "[%s:%s]: %s" % (str(host), str(port), str(msg))
for destsock in desc:
if destsock != sock and destsock != server:
destsock.send(msg)

def get_msg(sock):

try:
msg = sock.recv(1024)
sock.settimeout(.1)
return msg
except:
global desc
host, port = sock.getpeername()
print "[%s:%s] ha salido." % (str(host), str(port))
desc.remove(sock)
return None


global server
server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind(("", 8000))
server.listen(5)
global desc
desc = [server]
while 1:
accept_new_connection()
(sread, swrite, sexc) = select.select(desc, [], [])
for sock in sread:
if sock != server:
flag = get_msg(sock)
if flag:
broadcast(flag, sock)
Pues a mi parecer esto se puso interesante, como se acaban de dar cuenta hemos dado un gran paso, de unos simples Scripts que solo aceptaban conexiones y mandaban un mensaje, dimos un giro al realizar una aplicacion que maneje "usuarios" y los comunique, la verdad es que esa no es la unica manera de hacer un servidor de chat, bueno la base de uno, hay infinidad de maneras, tal vez esta incluso sea una pesima manera de realizarlo, pero funciona para nuestros propositos de este tutorial.

Muy bien, a la explicación:
# servchat.py
# Creamos un servidor de chat.

import socket
import select
Lo unico diferente aqui es que ahora incluimos el modulo de select, no se preocupen, será explicado en su debido momento.
global server
server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind(("", 8000))
server.listen(5)
global desc
desc = [server]
while 1:
accept_new_connection()
(sread, swrite, sexc) = select.select(desc, [], [])
for sock in sread:
if sock != server:
flag = get_msg(sock)
if flag:
broadcast(flag, sock)
Despues pasamos a las funciones, primero hay que entender lo que se espera realizar, muy bien, estamos creando variables globales (global), para que estas puedan ser modificadas en las funciones, despues creamos el servidor, asignandole una direccion y un puerto, despues hacemos el ciclo infinito el cual ya fue explicado, y ya adentro de ese ciclo aceptamos nuevas conexiones (accept_new_connection()), ahora sigue lo del select, como pueden ver le estamos mandando una lista donde se encuentran los sockets que se estan usando (incluyendo el server) lo unico que nos importa es saber cuando un socket se intenta comunicar con el servidor, es por eso que los otros dos parametros los dejamos vacios (select.select(desc, [], [])), el select nos devolvera los que se intentan comunicar, despues verificamos cada elemento que nos fue regresado (excluyendo al server (if sock != server:)) para saber que es lo que intenta hacer, despues recivimos el mensaje de cada socket que se comunicó (get_msg()) y lo mandamos a todos (broadcast()), dentro de la función de get_msg() también verifica que siga conectado ese cliente.
def accept_new_connection():

try:
global server
global desc
newsock, (remhost, remport) = server.accept()
server.settimeout(.1)
print "Se ha conectado %s:%s" % (str(remhost), str(remport))
desc.append(newsock)
except:
pass
Lo que esta haciendo esta función es utilizar las variables globales, para poderlas modificar, entonces lo que intenta es recivir una nueva conexion, pero solo lo hace por un periodo corto de tiempo (server.settimeout(.1)), si ese tiempo se acaba se pasa a la esepción la cual no hace nada, pero si en ese tiempo llega una nueva conexion entonces la acepta y guarda el nuevo socket en la lista (desc.append(newsock)).
def get_msg(sock):

try:
msg = sock.recv(1024)
sock.settimeout(.1)
return msg
except:
global desc
host, port = sock.getpeername()
print "[%s:%s] ha salido." % (str(host), str(port))
desc.remove(sock)
return None
En esta función intentamos recivir un mensaje (msg = sock.recv(1024)) del socket que pasamos como parametro, pero una véz más le dejamos un tiempo limite, si ese tiempo es excedido significa que el cliente se ha desconectado y lo quitamos de la lista, y devolvemos None, para que no entre a la condicional que tenemos en el programa principal.
Pero si nos manda un mensaje lo regresamos para que entre a la codicional en el programa principal, y ahi sera llamada la siguiente función:
def broadcast(msg, sock):

global desc
global server
host, port = sock.getpeername()
msg = "[%s:%s]: %s" % (str(host), str(port), str(msg))
for destsock in desc:
if destsock != sock and destsock != server:
destsock.send(msg)
lo que realiza esta función es utilizar las variables globales para asi mandar un "broadcast", el mensaje que recibe como parametro es lo que mandara a todos.


Los sockets tambien tienen clase.

Ahora veamos el ejemplo anterior pero orientado a objetos, esta vez no lo voy a explicar, pues la explicación ya esta en la página anterior, aqui esta el codigo:
# objchat.py
# Creamos un servidor de chat con clase.

import socket
import select

class objchat(object):

def __init__(self, host = "", port = 8000):

self.server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.server.bind((host, port))
self.server.listen(5)
self.desc = [self.server]
while 1:
self.accept_new_connection()
(self.sread, self.swrite, self.sexc) = select.select(self.desc, [], [])
for self.sock in self.sread:
if self.sock != self.server:
self.flag = self.get_msg(self.sock)
if self.flag:
self.broadcast(self.flag, self.sock)

def accept_new_connection(self):

try:
self.newsock, (self.remhost, self.remport) = self.server.accept()
self.server.settimeout(.1)
print "Se ha conectado %s:%s" % (str(self.remhost), str(self.remport))
self.desc.append(self.newsock)
except:
pass

def broadcast(self, msg, sock):

self.host, self.port = sock.getpeername()
msg = "[%s:%s]: %s" % (str(self.host), str(self.port), str(msg))
for self.destsock in self.desc:
if self.destsock != sock and self.destsock != self.server:
self.destsock.send(msg)

def get_msg(self, sock):

try:
self.msg = self.sock.recv(1024)
self.sock.settimeout(.1)
return self.msg
except:
self.host, self.port = self.sock.getpeername()
print "[%s:%s] ha salido." % (str(self.host), str(self.port))
self.desc.remove(self.sock)
return None

if __name__ == "__main__":
objchat()
Bueno, estas dos ultimas lineas sirven para que cuando este modulo sea importado no se ejecute el objchat(), pero si se esta ejecutando como programa pues que si se corra.


Que cliente telnet apareció??

Ha, pues es una especie de cliente telnet que hice, claro, no funciona como un cliente telnet real, solamente manda y recibe datos a un servidor, pero no es capaz de interactuar con una cuenta de shell, pero es excelente para los propositos de este manual, vamos a ver el codigo:
# objtel.py
# This is a Telnet class.

import sys
import socket
import select
import threading

class obj_tel(object):

print """
Telnet client made in Python.
By Juan Francisco Benavides Nanni.
------------------------------------
"""


def __init__(self):

self.client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
print "Give me the Host or IP address: ",
self.tmp = str(sys.stdin.readline())
self.host = ''
for self.i in self.tmp:
if self.i != '\n':
self.host += self.i
self.flag = 0
self.port = ''
while self.flag == 0:
print "\nGive me the port number: ",
self.tmp = str(sys.stdin.readline())
try:
self.port = int(self.tmp)
self.flag = 1
except ValueError:
print "\nPort number can't contain strings.\n"
try:
self.client.connect((self.host, self.port))
print "\nConnection successfully made.\n"
except:
print "\nCan't connect.\n"
sys.stdin.readline()
self.exit_client()
self.telnet()

def telnet(self):

self.opt = [self.client]
self.msg = ''
while 1:
(self.rlist, self.wlist, self.xlist) = select.select(self.opt,
[], [], .9)
if self.rlist != []:
print "%s" % (str(self.client.recv(1024)), )
else:
self.slp = threading.Thread(target = self.get_data)
self.slp.start()

def get_data(self):
self.tmp = str(sys.stdin.readline())
self.msg = ''
for self.i in self.tmp:
if self.i != '\n':
self.msg += self.i
self.client.send(self.msg)

def exit_client(self):
raise SystemExit

if __name__ == "__main__":
telnet = obj_tel()
Pues bueno, en este Script podemos ver que hay varias cositas nuevas, asi es que comenzemos con la explicación:

# objtel.py
# This is a Telnet class.

import sys
import socket
import select
import threading
Pues aqui estamos importando dos nuevos modulos que no habiamos visto antes, el de sys y el de threading, no es el objetivo de este tutorial el de explicar que es un thread, como tampoco lo era el de explicar en más detalle el uso del select, lo que nos importa aqui es que un thread nos sirve para crear un "hilo", por ejemplo, el programa principal se continuará ejecutando, pero tambien le dará recursos al "hilo" para que sea ejecutado por aparte, a grandes rasgos y para nuestros propositos lo dejaremos asi, muy bien, el modulo de sys lo incluimos para poder recivir input del teclado, pero se verá a su debido tiempo, continuemos:
class obj_tel(object):

print """
Telnet client made in Python.
------------------------------------
"""


def __init__(self):

self.client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
print "Give me the Host or IP address: ",
self.tmp = str(sys.stdin.readline())
self.host = ''
for self.i in self.tmp:
if self.i != '\n':
self.host += self.i
self.flag = 0
self.port = ''
while self.flag == 0:
print "\nGive me the port number: ",
self.tmp = str(sys.stdin.readline())
try:
self.port = int(self.tmp)
self.flag = 1
except ValueError:
print "\nPort number can't contain strings.\n"
try:
self.client.connect((self.host, self.port))
print "\nConnection successfully made.\n"
except:
print "\nCan't connect.\n"
sys.stdin.readline()
self.exit_client()
self.telnet()
Pues cuando el objeto es creado se imprimira un mensaje de bienvenida, y despues entrara al constructor, ya dentro del constructor lo primero es crear el socket, y despues le pedimos la dirección y el puerto al que desea conectarse el usuario, despues se intenta conectar y si no lo logra termina la aplicación, si si lo logra continua y llama al siguiente metodo:

    def telnet(self):

self.opt = [self.client]
self.msg = ''
while 1:
(self.rlist, self.wlist, self.xlist) = select.select(self.opt,
[], [], .9)
if self.rlist != []:
print "%s" % (str(self.client.recv(1024)), )
else:
self.slp = threading.Thread(target = self.get_data)
self.slp.start()
En este metodo lo que se hace es crear una lista con un solo elemento (el cliente) y verificar en el select.select si es que nos esta llegando un mensaje, pero esta vez hicimos uso de un cuarto parametro, y ese parametro nos sirve para darle un tiempo limite, despues verifica si nos llega mensaje, si nos llega pues lo imprimimos, pero si no nos llego mensaje intentamos mandar uno, es por eso que hacemos uso del thread, porque tal vez no se queria mandar un mensaje, y si lo pusieramos para que lo mandara asi normal, sin thread, se quedaria esperando a mandarlo, es por eso que se utiliza aqui, despues ya se ejecuta el thread (self.slp.start()).

    def get_data(self):
self.tmp = str(sys.stdin.readline())
self.msg = ''
for self.i in self.tmp:
if self.i != '\n':
self.msg += self.i
self.client.send(self.msg)
Como lo mencionamos aqui estamos intentando mandar datos al servidor, pero si no hay nada que mandar no hay problema, porque no se queda estancado en este metodo gracias al thread (como ya lo habiamos mencionado).

    def exit_client(self):
raise SystemExit
Lo unico que hace es que el programa se termine si necesidad de errores ni nada de eso.

if __name__ == "__main__":
telnet = obj_tel()
Eso ya lo vimos.


Ya para finalizar...

Pues asi es como trabajan los sockets, la verdad hay un sin fin de maneras de como trabajar con ellos, las cuales no fueron vistas aqui, pero espero pronto poder hacerle una actualización a este documento.



Fuente:
Autor. Juan Francisco Benavides Nanni
Contacto. elnanni@gmail.com
Pagina. Make Me a BlogJob.
Fecha. 17/02/2006


REFERENCIA ADICIONAL:

HOWTO de programación de Sockets. http://wiki.python.org/moin/HowTo/Sockets

Python para programación de celulares

Python para la Serie 60 permite a la comunidad de desarrolladores globales de Python correr fácilmente aplicaciones para los dispositivos basados en la Serie 60.

Finlandia – Nokia anunció el 11 de febrero del 2005 el lanzamiento de Python para la Plataforma Serie 60, permitiendo que la comunidad de desarrolladores de fuente abierta a nivel mundial que utiliza el lenguaje de programación Python pueda ejecutar comandos de Python y correr scripts de Python y aplicaciones en dispositivos basados en la Serie 60.

Disponible para descarga sin costo a través del sitio web de la comunidad de desarrollo global de Nokia, Forum Nokia (www.forum.nokia.com/python), Python para la Serie 60 es un paquete de software que se instala a un dispositivo basado en la plataforma Serie 60, permitiendo a los desarrolladores crear aplicaciones con el simple y consistente lenguaje de programación Python orientado a los objetos. Puede utilizarse para desarrollar comandos, scripts y aplicaciones para los dispositivos basados en la Serie 60.

“Python hará que el desarrollo de aplicaciones móviles sea fácil y accesible para programadores que están buscando un camino rápido y amistoso hacia los desarrolladores, para diseñar aplicaciones móviles,” señaló Lee Epting, Vicepresidente, Forum Nokia. “Las populares características de Python permitirán ahora que una nueva comunidad de desarrolladores libere el vasto potencial de los dispositivos basados en la Serie 60.”

Python para la Serie 60 está bien equipado para el desarrollo de aplicaciones prototipo y aplicaciones de concepto para dispositivos móviles basados en la Serie 60. Los desarrolladores pueden ejecutar comandos de Python usando una consola interactiva en un dispositivo basado en la Serie 60, accessible a través de un teclado o una conexión remota a una PC sobre Bluetooth.

Al utilizar Python para las Series 60, los desarrolladores pueden escribir aplicaciones para Python e instalarlas a un dispositivo con base en la Serie 60 y el dispositivo puede entonces correr estas aplicaciones desde el ambiente Python. Las aplicaciones de Python también pueden desarrollarse como aplicaciones independientes con la selección de un ícono en el menú de opciones. Al utilizar Python para la Serie 60, los desarrolladores también pueden ejecutar comandos y scripts de Python en los simuladores SDK de la Plataforma para Desarrolladores de la Serie 60.

El Python para los paquetes Serie 60, disponible para ser descargado, incluye un instalador Python (SIS), con muestras de scripts, notas de liberación, librerías adicionales y documentación en formato PDF, incluyendo “Cómo iniciar con Python,” “Programando con Python,” y “Referencia API para Python.” Adicionalmente, una mesa de discusión de Python para la Serie 60 en el sitio de Nokia ayuda a los editores y desarrolladores a navegar entre los scripts de desarrollo y aplicaciones en los disposivos basados en la Serie 60.

La Plataforma Serie 60, construida en el Sistema Operativo Symbian, es la plataforma líder para smartphones a nivel mundial, con millones de dispositivos en el mercado que están listos para el desarrollo de aplicaciones móviles de calidad. Se han dado licencias a algunos de los principales fabricantes de teléfonos en el mundo, incluyendo a LG Electronics, Lenovo, Nokia, Panasonic, Samsung, Sendo y Siemens.

Para poder descargar el emulador para PC haga clic aquí. Hay que precisar que los archivos a descargar son:

  • PythonForS60_1_4_5_SDK_2ndEdFP3.zip
  • S60-SDK-200634-3.1-Cpp-f.1090b.zip
  • Adicionalmente: strawberry-perl-5.10.0.3.exe

Para acceder a los cursos virtuales de Nokia haga clic aquí.

Para revisar código fuente de Python S60 de uno de los muchos autores haga clic aquí.

viernes, 26 de diciembre de 2008

Cómo publicar y compartir trabajos intelectuales

PRESENTACIONES
Existen muchos sitios para compartir trabajos intelectuales de estudiantes, como Presentaciones, Ensayos, Tesis, Monografías, Vídeos... Para los trabajos intelectuales textuales (Presentaciones, Ensayos, Tesis, Monografías) hemos elegido 3 sitios:

  • Slideshare.net para compartir trabajos hechos en PowerPoint;
  • Scribd.com para compartir trabajos hechos en MS. Word, Excel, PDF y PowerPoint, y
  • Zoho.com para compartir cualquier tipo de trabajo.

El procedimiento para la publicación de trabajos es prácticamente idéntico. Consta de tres pasos:

Sube 8 Publica 8 Comparte

Pero si quieres una explicación más detallada a continuación un excelente trabajo de Karina Crespo:

VIDEOS

Para la publicación de videos publícalo en aquellos sitios gratuitos que promueven el compartir y que más se frecuentan: Youtube, Google, Teachertube, Heywatch, etc. (Ver Video+).

El procedimiento para subir vídeos es similar al de subir presentaciones y documentos en cualquier formato.

  1. Entra a uno de los sitios más famosos como: Youtube, Teachertube o Google.
  2. Haz clic en el botón Upload y sigue las instrucciones. Estos sitios también te indican cómo subir vídeos desde tu mobil.

Para subir vídeos a Video.Google en español, haz clic aquí

Compartir/Embed

Una vez subido el vídeo, copia la dirección URL y envíala por correo electrónico a las personas para compartirlo. También puedes copiar el código "embed" y pegarlo en tus páginas web, blogs y wikis. Ver Integración de medios en materiales educativos.

AUDIO
  1. Guarda el audio con el formato MP3.
  2. Regístrate en uno de estos sitios dedicados a publicar y compartir audio: Mypodcast,Castpost, www.gcast.com, gabcast, www.espapod.com, podErato, www.castpost.com, y muchos + sitios.
  3. Sube los archivos y compártelos.
BLOGS

En este video se explica con todo detalle como publicar texto y video en su blog. Para crear su cuenta en www.blogger.com no se olvide de crear previamente una cuenta de correo electrónico en gmail. Con esa misma cuenta y contraseña podrá crear fácilmente su cuenta en Blogger. Los pasos son sencillos los mismos que se explican en la misma página.


jueves, 25 de diciembre de 2008

El mejor programa para hacer diagramas

En mi humilde opinión que posiblemente no sea compartida con todos, disponemos de un software libre que funciona en Window$ y GNU/Linux.

Para los usuarios de Window$, haga clic aquí para descargar este maravilloso programa: dia-setup-0.96.1-8.exe.

No se olvide de instalar previamente GTK+Runtime Environment la versión gtk 2B-2.10.6-1-setup.zip haciendo clic aquí.

Con el pueden hacer diagramas de flujo, diagramas UML, diagramas de redes y un largo etc.

En su paleta de herramientas simplemente escoger la librería que quiera usar.

miércoles, 17 de diciembre de 2008

Manejo de archivos con Python

Para poder escribir o leer archivos en Python se tiene que respetar lo que denomino la "ley del sandwich". Es decir:

  1. Abrir el archivo en modo escritura (w) o lectura (r)
  2. Operar con el archivo, ya sea escribir o leer
  3. Cerrar el archivo
Por ejemplo si quisieramos escribir dos líneas en el archivo prueba.txt, el código sería:

archivo=open("prueba.txt","w")
archivo.write("Esto es una prueba\nRealmente, lo es")
archivo.close()

Ahora si quisieramos añadir una línea más, el código sería:

archivo=open("prueba.txt","a")
archivo.write("\nEsto es otro texto adicional.")
archivo.close()

Finalmente podemos leer el contenido del archivo con este código:

archivo=open("prueba.txt","r")
print archivo.read()
archivo.close()

Si quisieramos leer una línea el código sería así:

archivo=open("prueba.txt","r")
print archivo.readline()
archivo.close()

También el contenido de un archivo lo podemos almacenar en una lista y proceder a leer línea línea:

archivo=open("prueba.txt","r")
lista=archivo.readlines()
for linea in lista:
print linea
archivo.close()

En fin, se pueden hacer maravillas.

martes, 16 de diciembre de 2008

Revista de Software Libre PAPIRUX


Ya está publicado el número 2 de la revista Papirux (Diciembre 2008)

En este número puede encontrar:

  • Wikimedia
  • Juego: Torus Trooper
  • Review: Blender
  • Review: Ubuntu Intrepid Ibex (8.10)
  • Comandos en GNU/Linux (I parte)
  • Reinicio de Emergencia: SysRq
Si desea descargar los archivos PDF de esta revista haga clic aquí.

sábado, 13 de diciembre de 2008

Programación Visual con Python

Si deseas programar con ventanas, menús, botones y otros. Tienes que descargar los siguientes programas:

  1. Python la versión 2.5.2
  2. PyCairo la versión 1.4.12-1
  3. PyGObject la versión 2.14.1-1.
  4. PyGTK la versión 2.12.1-2
  5. GTK + runtime la versión 2.12.9-2
Una vez descargado, procedemos a instalar en el orden indicado en la lista anterior.

Para comprobar si todo está bien, escribimos el siguiente código en la consola de comandos de Python:

import gtk

Si no te muestra ningún mensaje de error significa que haz instalado y configurado correctamente PyGTK.

Lo más interesante de programar con PyGTK es de que puedes programar y diseñar interfases de usuario multiplataforma; es decir se pueden ejecutar en Window$, GNU/Linux, MacOS entre otros.

A continuación un ejemplo que crea una ventana con una etiqueta, casillas de verificación, una caja de texto y un botón de comandos.

import pygtk
import gtk
window = gtk.Window(gtk.WINDOW_TOPLEVEL)
window.connect("destroy", gtk.main_quit)
box = gtk.VBox(False, 0)
window.add(box)
label = gtk.Label("Hola Mundo")
c1 = gtk.CheckButton(label="Uno")
c2 = gtk.CheckButton(label="Dos")
entry = gtk.Entry()
button = gtk.Button("Aceptar")
box.add(label)
box.add(c1)
box.add(c2)
box.add(entry)
box.add(button)
window.show_all()
gtk.main()

lunes, 8 de diciembre de 2008

Los 12 Mandamientos del código Python

Para una mejor codificación les recomiendo la Guía de estilo del código Python, escrita por Guido van Rossum, creador de Python, y Barry Warsaw y Modismos y Anti-Modismos en Python, de Moshe Zadka. Pero para aquellos demasiado vagos para leerlos, también les puede ser de utilidad estos 12 mandamientos del código Python de Command Line Warriors.

Guido, que te sacó de la tierra de Visual Basic, de la casa de la servidumbre, habló así:

Los nombres de los módulos deben estar en minúsculas - hola.py
Los nombres de las clases deben usar CamelCase
Los métodos y funciones deben usar minusculas_con_guion_bajo
Los métodos privados para uso interno comienzan con _guion_bajo
Los atributos de clase con __doble_guion_bajo
Las constantes en el primer nivel del código (las que no se encuentran dentro de una función o una clase) deben usar LETRASMAYUSCULAS. Usar demasiadas constantes puede hacer que tu código sea menos reutilizable.
Si una variable en una función o método es tan temporal que no puedes darle un nombre, utiliza i para la primera, j para la segunda, y k para la tercera.
Indenta con cuatro espacios por nivel. Sin tabuladores. Si rompes este mandamiento serás lapidado en la plaza del pueblo.
Las líneas no deberían tener nunca más de 80 caracteres. Divide las líneas usando una barra invertida. No necesitas hacer esto si hay paréntesis, llaves o corchetes.
Espacio después de una coma (huevos, verdes, con, jamon)
Espacio antes y después de un operador i = i + 1
Escribe cadenas de documentación para todos los módulos, funciones, clases y métodos públicos. Python es una comunidad internacional, así que utiliza el inglés para las cadenas de documentación, los nombres de los objetos y los comentarios.

Py TTS

Este es un pequeño programa de texto a voz (TTS o Text To Speech)  escrito en Python con el nombre de Py TTS. Py TTS permite escuchar textos leídos mediante el Speech API (SAPI) de Microsoft o guardar estos textos leídos en archivos de audio.

El único requisito es tener instalado el Speech API en el equipo, el cual viene incluido por defecto con Windows XP y Windows Vista.

No obstante si usas XP también te puede interesar buscar una voz más natural que la que se distribuye con SAPI 5.1, Microsoft Sam, que además de ser muy robotizada, es una voz inglesa. Windows Vista utiliza Microsoft Anna por defecto, que es más natural, pero también es inglesa.

Les recomiendo las voces de Loquendo y AT&T Natural Voices, que son increíblemente buenas (y caras).

Pueden probar que las voces instaladas funcionen correctamente en Inicio -> Panel de control -> Voz.

Para poder descargar este programa haga clic aquí.

Huevo de pascua en Python

Si quieres obtener el Zen de Python, en el Shell de Python (>>>) simplemente escribe:


import this

El Zen de Python

Hace mucho tiempo el entusiasta de Python Tim Peters plasmó de forma concisa los principios de diseño por los que guiarse al escribir en Python según el BDFL (Benevolent Dictator for Life o Dictador Benévolo de por Vida, en este caso Guido van Rossum, el creador de Python) en 20 aforismos, de los cuales sólo 19 han pasado a forma escrita.

Hermoso es mejor que feo.
Explícito es mejor que implícito.
Simple es mejor que complejo.
Complejo es mejor que complicado.
Plano es mejor que anidado.
Disperso es mejor que denso.
La legibilidad cuenta.
Los casos especiales no son suficientemente especiales como para romper las reglas.
Aunque lo pragmático gana a la pureza.
Los errores nunca deberían dejarse pasar silenciosamente.
A menos que se silencien explícitamente.
Cuando te enfrentes a la ambigüedad, rechaza la tentación de adivinar.
Debería haber una -- y preferiblemente sólo una -- manera obvia de hacerlo.
Aunque puede que no sea obvia a primera vista a menos que seas holandés. (NT: Guido van Rossum es holandés)
Ahora es mejor que nunca.
Aunque muchas veces nunca es mejor que *ahora mismo*.
Si la implementación es difícil de explicar, es una mala idea.
Si la implementación es sencilla de explicar, puede que sea una buena idea.
Los espacios de nombres son una gran idea -- ¡tengamos más de esas!

Python 3

Después de casi 3 años de trabajo el 3 de Diciembre del 2008 se ha liberado al fin Python 3.0, también conocido como Python 3000, la tan esperada nueva versión del que fuera nombrado lenguaje del año en Enero de 2008. Una versión que llevamos tiempo esperando y que romperá la compatibilidad hacia atrás en pos de mejorar aún más el lenguaje.

Efectivamente, el 3 de Diciembre se cerró el último bug de esta versión con la que ya podemos empezar a jugar, aunque no aconsejo comenzar a utilizarla indiscriminadamente hasta dentro de un par de meses, cuando las distintas librerías que pudieras necesitar se actualicen.

Si quieres saber más, puedes leer las novedades en What's New In Python 3.0. Y si quieres empezar a programar en este fantástico lenguaje, puedes descargarlo haciendo clic aquí.

Python con AutoCAD

Primero instalamos y descargamos PyWin32. Si quiere descargar haga clic aquí.


El código que escribirían en Python sería este:

from win32com.client import Dispatch
acad = Dispatch("AutoCAD.Application")
acad.Visible=1
doc = acad.ActiveDocument 
doc.Utility.Prompt("Hola desde Python\n")

Para crear líneas, círcunferencias se los dejo como investigación.

Python con Excel

Primero descargamos e instalamos la extensión PyWin32, para ello haga clic aquí.


En el IDLE de Python escriba y ejecute este primer código ejemplo:

from win32com.client import Dispatch
xlApp = Dispatch("Excel.Application")
xlApp.Visible = 1
xlApp.Workbooks.Add()
xlApp.ActiveSheet.Cells(1,1).Value = 'Bienvenido a Python'
xlApp.ActiveWorkbook.ActiveSheet.Cells(2,1).Value = 'Hola Mundo'

Si quieren un ejemplo más avanzado:

from win32com.client import Dispatch
mensaje=raw_input("Escribe un mensaje:")
xlApp = Dispatch("Excel.Application")
xlApp.Visible = 1
xlApp.Workbooks.Add()
xlApp.ActiveSheet.Cells(1,1).Value = 10.75
xlApp.ActiveWorkbook.ActiveSheet.Cells(2,1).Value = 12.25
xlApp.ActiveWorkbook.ActiveSheet.Cells(3,1).Formula = "=A1+A2"
xlApp.ActiveWorkbook.ActiveSheet.Cells(4,1).Formula = "=NOW()"
xlApp.ActiveWorkbook.ActiveSheet.Cells(5,1).Formula = "=SUM(A1:A2)"
xlApp.ActiveSheet.Cells(1,1).Font.Size = 14
xlApp.ActiveWorkbook.ActiveSheet.Cells(2,1).Font.Bold=1
xlApp.ActiveSheet.Cells(6,1).Value = mensaje
xlApp.ActiveWorkbook.ActiveSheet.Cells(1,1).EntireColumn.Autofit()



Python con MySQL

Esta prueba se hizo en la plataforma Windows XP Version 2002 Service Pack 2. Los usuarios de linux deben revisar una entrada anterior del mes de Abril 2008 donde expliqué como instalar Apache+PHP+MySQL+PhpMyAdmin, después de ello instalar el DB API para Python con la siguiente orden


$ apt-get install python-mysqldb

Continuando para los usuarios de M$ Windows:

Primero: Descargar la herramienta Appserv que nos permitirá una instalación sencilla de MySQL además de disponer de un gestor de base de datos gráfico como PhpMyAdmin. Para el ejemplo que se explica a continuación descargué la versión AppServ 2.5.10. Para descargar estar herramienta tan útil haga clic aquí.

Segundo: Instalar AppServ, en el proceso de instalación les pedirá una contraseña para el usuario root de MySQL, en mi caso la contraseña que le asigné fue admin.

Tercero: Crear una base de datos, para ello entrar al administrador de base de datos PhpMyAdmin. Para ello en un navegador como Mozilla FireFox, Opera o Chrome Google en la barra de dirección digitar: http://localhost

Hacer clic en el enlace: phpMyAdmin Database Manager Version 2.10.3

Digitar el usuario: root
La contraseña: admin

En la caja de texto, crear nueva base de datos digitar prueba y hacer clic en el botón Crear.

Luego, proceda a crear una tabla con el nombre usuario e indiquele el número de campos por ejemplo 2, con los campos usucod de tipo VarChar con tamaño 5 y usunom de tipo VarChar con tamaño 30

Por último inserte dos o más registros, para ello haga clic en el enlace Insertar.

Cuarto: Instalar el DB API para Python. Para descargar esta extensión haga clic aquí.

Quinto: Finalmente en el IDLE de python digite el siguiente código y corra el programa:

import MySQLdb
db=MySQLdb.connect(host='localhost',user='root',passwd='admin',db='prueba')
cursor=db.cursor()
sql='SELECT * FROM usuario'
cursor.execute(sql)
resultado=cursor.fetchall()
print 'Datos de Usuarios'
for registro in resultado:
    print registro[0],'->',registro[1]