Older blog entries for jarod (starting at number 104)

Text Munger (ou nem tudo é como deveria ser)

Tudo começou quando eu esbarrei nesse link . O texto contém 15 exercícios de programação, entre eles o que eu me propus a fazer, o text munger.

O exercício consiste no seguinte: dado um texto qualquer, o text munger deve retornar o texto com as palavras desse texto modificadas da seguinte forma: ao invés da palavra original, teremos a primeira letra da palavra original, o resto da palavra (com exceção da última letra) embaralhado seguido da última letra da palavra.

Dentre as várias soluções disponíveis no ruby quiz, a solução em destaque, de Gordon Thiesfeld, usa a expressão regular \b para dividir as palavras. Expressões regulares são iguais em qualquer linguagem, certo? Bom, quase certo. O b funciona da mesma forma no ruby, perl e php, mas funciona de forma diferente no python. Ou não funciona. Na verdade, não sei se é um bug da implementação ou algo assim.

Eu poderia usar outra regex para dividir as palavras e as pontuações, mas já que o fato do \b não funcionar tinha me deixado frustrado com as regex (e eu não queria pensar muito nelas, pra mim o \b deveria funcionar), parti para outra solução. Descobri o shlex, um analisador léxico simples, que para o que eu precisava, funcionava muito bem.

Minha solução para o problema:


import sys
import shlex

from random import shuffle

def munge(text):
    t = shlex.shlex(text, posix=False)
    t.quotes = "'"
    s = [munge_word(word) for word in t]
    print(" ".join(s))

def munge_word(aword):
    s = list(aword)
    first = s.pop(0)
    try:
      last = s.pop()
    except IndexError:
        return aword
    shuffle(s)
    return first + ''.join(s) + last

try:
  s = open(sys.argv[1]).read()
  munge(s)
except IndexError:
  print("Usage: munge.py file")
 

Observe que a solução não está 100% igual a proposta em ruby. Devido a junção em (" ".join(s)), acabam aparecendo uns espaços em branco que não existiam no texto original.
Existe ainda uma solução em smalltalk proposta pelo Rodrigo Cacilhas no kodumaro. E você gosta de exercícios assim? Sabe porque o \b na implementação de regex do python não funciona como eu esperava? (ou serão minhas expectativas que estão erradas?). Os comentários estão aí para vocês!

Syndicated 2008-06-30 14:42:20 (Updated 2008-06-30 18:12:01) from devlog

Comparação de versões

Para um software, dizer que a versão 0.2 é maior que a 0.1 é moleza, mas como dizer que a versão 0.2.2 é maior que a 0.2?

Esse é um tipo de comparação que pode ser necessário feita. Talvez você tenha alguma parte do seu código que tenha uma implementação diferente e melhor para acima da versão x. O b2evolution usa isso, por exemplo, para habilitar o modo TRADITIONAL no Mysql quando o debug está ativado apenas a partir do MySQL 5.0.2. E usa também para habililtar alguns espertezas disponíveis apenas no PHP 5.1.

Em Python, a comparação pode ser feita usando o pkg_resources:

>>> from pkg_resources import parse_version
>>>
>>> parse_version("0.10") > parse_version("0.9")
True

>>> True
True
>>> parse_version("0.2.2") > parse_version("0.2")
True

>>> parse_version("0.1.2") > parse_version("0.2")
False

>>> parse_version("0.2.2") > parse_version("0.2")
True
>>>

Em PHP, usa-se a função version_compare

(Dica do pkg_resources retirada de http://lucumr.pocoo.org/cogitations/2008/06/19/%E2%80%A6-and-010-follows-09/)

Syndicated 2008-06-25 15:01:47 from devlog

Comparação de versões

Para um software, dizer que a versão 0.2 é maior que a 0.1 é moleza, mas como dizer que a versão 0.2.2 é maior que a 0.2?

Esse é um tipo de comparação que pode ser necessário feita. Talvez você tenha alguma parte do seu código que tenha uma implementação diferente e melhor para acima da versão x. O b2evolution usa isso, por exemplo, para habilitar o modo TRADITIONAL no Mysql quando o debug está ativado apenas a partir do MySQL 5.0.2. E usa também para habililtar alguns espertezas disponíveis apenas no PHP 5.1.

Em Python, a comparação pode ser feita usando o pkg_resources:

>>> from pkg_resources import parse_version
>>>
>>> parse_version("0.10") > parse_version("0.9")
True

>>> True
True
>>> parse_version("0.2.2") > parse_version("0.2")
True

>>> parse_version("0.1.2") > parse_version("0.2")
False

>>> parse_version("0.2.2") > parse_version("0.2")
True
>>>

Em PHP, usa-se a função version_compare

(Dica do pkg_resources retirada de http://lucumr.pocoo.org/cogitations/2008/06/19/%E2%80%A6-and-010-follows-09/)

Syndicated 2008-06-25 15:00:47 from devlog

Shell Script engraçadinho e (quase) inútil

Se você não tiver o comando beep, no debian e derivados: aptitude install beep.

;)


beep -f 288 -l 800 -r 3 -d 50
beep -f 230 -l 800 -r 1 -d 50
beep -f 341,3 -l 300 -r 1 -d 50
beep -f 288 -l 1000 -r 1 -d 50
beep -f 230 -l 800 -r 1 -d 50
beep -f 341,3 -l 300 -r 1 -d 50
beep -f 288 -l 1300 -r 1 -d 50
 

Syndicated 2008-06-23 18:59:14 from devlog

Firebug e console.dir

Pois é, hoje eu descobri que é possível dar um 'dir' nos objetos no Firebug.. Função muito útil :)

Syndicated 2008-06-20 18:41:13 from devlog

Wordle

http://wordle.net/gallery/waltercruz

Wordle - devlog
Wordle

Wordle é um brinquedo para gerar “nuvens de palavras” a partir do texto que você informa. As nuvens dão mais proeminência a palavras que aparecem mais frequentemente no texto fonte. (da página do wordle)

Seguindo o exemplo do Ned Batchelder eu gerei uma imagem no wordle a partir dos títulos de todos os posts no devlog. Divertido ;)

Confiram a imagem maior em: http://wordle.net/gallery/waltercruz

Syndicated 2008-06-13 22:28:10 (Updated 2008-06-13 22:29:34) from devlog

9 Jun 2008 (updated 10 Jun 2008 at 21:11 UTC) »

PostgreSQL 8.4 Avançando

O Postgres OnLine Journal publicou uma pequena lista dos das coisas que estão por vir no PostgreSQL 8.4. Algumas delas:

  • Replicação embutida: master/slave, via log shipping. Há uma grande discussão na lista pg-hackers sobre isso.
  • Suporte a funções de tabela no padrão ANSI SQL 2003: Você pode ler mais sobre na discussão relacionada na lista. Permitirá a escrita de funções que possam ser manipuladas como tabela de uma forma mais sucinta.
  • Estatísticas de funções - que com certeza vai facilitar a vida de quem programa muito no banco de dados.

Para mais novidades, vejam o post original.

Syndicated 2008-06-09 21:36:40 (Updated 2008-06-10 15:27:10) from devlog

Open Events

http://open-events.appspot.com/

OK, ok, está todo mundo brincando com o Google App Engine, e eu também. Dêem uma conferida! http://open-events.appspot.com/ e baixem o fonte em http://hg.assembla.com/open_events_calendar .

A idéia é manter atualizado o calendário de eventos de software livre no Brasil e adicionar na interface web informações extras.

Idéias, sugestões, críticas, são todos bem vindos!

Syndicated 2008-06-02 20:10:48 from devlog

2 Jun 2008 (updated 2 Jun 2008 at 21:12 UTC) »

Mercurial na web com apache e fastcgi

Um efeito interessante do padrão WSGI é que ele pode tornar a vida dos sysadmins mais fácil. Por exemplo, publicar uma aplicação web em Python, com WSGI consiste apenas de:

  1. Descobrir como instanciar essa aplicação (específico de aplicação pra aplicação)
  2. Transformá-la em um cliente/middleware WSGI
  3. Publicá-la, usando a forma desejada.

Abaixo, segue um exemplo de uma publicação do mercurial, no apache, usando fastcgi.

#!/usr/bin/env python2.5
#
# An example CGI script to export multiple hgweb repos, edit as necessary
import site
import sys
site.addpackage('/home/usuario/lib/python2.5/site-packages/','easy-install.pth',set(sys.path))

# enable importing on demand to reduce startup time
from mercurial import demandimport; demandimport.enable()

# If you'd like to serve pages with UTF-8 instead of your default
# locale charset, you can do so by uncommenting the following lines.
# Note that this will cause your .hgrc files to be interpreted in
# UTF-8 and all your repo files to be displayed using UTF-8.
#
#import os
#os.environ["HGENCODING"] = "UTF-8"

from mercurial.hgweb.hgwebdir_mod import hgwebdir
import mercurial.hgweb.wsgicgi as wsgicgi
from flup.server.fcgi import WSGIServer

application = hgwebdir('hgweb.config')
WSGIServer(application, debug = True).run()

E o hgweb.config:

[paths]
repositorio1 = /home/usuario/hg/repositorio1
repositorio2 = /home/usuario/hg/repositorio2

Compare com o deploy de Pylons via fastcgi, por exemplo. Depois de termos instanciado a aplicação (e isso varia de framework ou aplicativo), a forma de executar como fastcgi no apache é a mesma, usando o flup. E isso serviria para qualquer aplicação que disponibilizasse uma 'saída' WSGI. Prático não?

Syndicated 2008-06-01 23:39:25 (Updated 2008-06-02 13:06:54) from devlog

95 older entries...

New Advogato Features

New HTML Parser: The long-awaited libxml2 based HTML parser code is live. It needs further work but already handles most markup better than the original parser.

Keep up with the latest Advogato features by reading the Advogato status blog.

If you're a C programmer with some spare time, take a look at the mod_virgule project page and help us with one of the tasks on the ToDo list!