OVH Cloud OVH Cloud

Qui êtes-vous ? Que faites-vous ?

105 réponses
Avatar
Pierre
Salut à tous,

Je me présente, utilisateur Windows et développeur occasionnel en VB
pour le boulot, principalement pour réaliser des interfaces utilisateur
avec des systèmes d’acquisition de mesures physiques ou des commandes de
machines. Pourquoi VB ? Pour rester dans la continuité de ce qui avait
déjà été réalisé auparavant, tout simplement, le choix ne s'est jamais posé.
Actuellement, je cherche à évoluer dans un autre langage et à essayer
d’intégrer de plus en plus Linux, que se soit pour une utilisation
personnelle ou professionnelle.

Renseignements pris, Python me semble être un langage en vogue et promis
à un bel avenir !
Je n’ai malheureusement pas trouvé (je n’ai peut être pas bien cherché)
beaucoup d’exemples d’applications écrites en Python. Pouvez-vous m’en
citer ?
J’aurais également désiré connaître votre profil de programmeur ? D’où
venez-vous, pourquoi et pour quelles tâches utilisez-vous Pyhton ?
Utilisez-vous un environnement de développement tel que Boa ?

Merci,
Pierre.

10 réponses

Avatar
luc
Bruno Desthuilliers wrote:

Des deux côtés ?


Les fausses vérités propagées au sujet de Python par les Rubyistes et
les fausses vérités propagées au sujet de Ruby par les Pythonistes. Des
deux cotés quoi :p

Faire le choix de Python parceque Ruby ne permettrait pas d'implémenter
des serveurs COM n'est pas un choix contestable (sauf qu'il me semble
bien avoir vu une lib le permettant mais je ne préfère pas trop
m'avancer la dessus, moins je touche à ces horreurs mieux je me porte).
Faire le choix de Python parcequ'il est soit-disant plus avancé que Ruby
qui n'a pas de lists comprehensions c'est juste un chouia ridicule.

--
Luc Heinrich

Avatar
Amaury Forgeot d'Arc
Bruno Desthuilliers wrote:

Des deux côtés ?


Les fausses vérités propagées au sujet de Python par les Rubyistes et
les fausses vérités propagées au sujet de Ruby par les Pythonistes. Des
deux cotés quoi :p

Faire le choix de Python parceque Ruby ne permettrait pas d'implémenter
des serveurs COM n'est pas un choix contestable (sauf qu'il me semble
bien avoir vu une lib le permettant mais je ne préfère pas trop
m'avancer la dessus, moins je touche à ces horreurs mieux je me porte).


Et tu as raison. COM est affreux quand on l'utilise à partir du C, c'est
pour cela qu'il faut l'utiliser à partir de Visual Basic ou de Python !

Faire le choix de Python parcequ'il est soit-disant plus avancé que Ruby
qui n'a pas de lists comprehensions c'est juste un chouia ridicule.


Ce qui m'a fait choisir python n'est pas uniquement la syntaxe du
langage ou le modèle objet (au début, je le comparais au Lisp. si si!
qui a juste un tout petit peu plus de parenthèses, et permet plus de
dynamisme)

Pour moi la force de python est son "pouvoir de représentation", sa
capacité d'intégrer des mécanismes externes dans le langage.
Exemples: pythonCOM, dont la syntaxe est la même que Visual Basic;
SoapPy, qui transforme naturellement des appels de fonction vers
XML-RPC; wxPython qui permet de dériver en Python des objets C++;
py.test pour écrire des tests unitaires sans aucune librairie...

Une fois que cette couche est installée, l'interface devient tellement
naturelle qu'on l'oublie!

Un regret sur ce sujet: le langage SQL résiste à l'assimilation...

--
Amaury Forgeot d'Arc


Avatar
Alex Marandon
Bruno Desthuilliers wrote:
Bruno Desthuilliers wrote:


o = plop() # Python
o = Plop.new # Ruby
my $o = plop->new; # Perl


Je ne sais pas pourquoi beaucoup de gens sont effrayes par les

caracteres rigolos de Perl, ils sont la pour nous aider. Quand on voit
%toto on sait que c'est un tableau associatif, @toto c'est une liste,
etc.


Dans un bloc de code suffisament court, et avec un bon nommage, ce genre
d'information n'apporte rien. Au contraire. D'une part, ces caractères
non alphanumériques se lisent difficilement (en tous cas pour moi, et je
pense pour la plupart des personnes appréciant une bonne littérature),


Ok, je ne vais pas epiloguer sur les caractères non alphanumériques,
quand on programme en Perl, c'est acquis, on n'hesite pas du tout la
dessus. En python il m'arrive de rajouter _list ou _map a des noms de
variables a des fins purement mnemotechniques.

et d'autre part ils limitent la généricité. En Python, certaines
interfaces "implicites" (séquence - ou même simplement itérable -,
tableau associatif, fichier, appelable, entre autres) sont très
couramment implémentées par une grande quantité de classes différentes.
Cela permet à du code écrit à l'époque de la 1.5.2 d'être encore
utilisable avec des types qui ne pouvaient même pas exister à l'époque.


C'est pareil en Perl. Les %, @ et $ renseignent juste sur une interface,
tu implemente ce que tu veux en dessous ("perldoc perltie" pour en
savoir plus).

D'ailleurs a ce propos, quitte a vouloir etre fool proof, Python
aurait pu forcer l'encapsulation des donnees membres,


Attention : encapsulation != data hiding.


Disons que le data hiding fait partie de l'encapsulation, non ?

ca me parait plus fondamental que l'indentation.


Ah bon ? Et pourquoi donc ? (attention, y a un piège).


Parce que ca permet de modifier la maniere dont ces donnees membres sont
calculees sans avoir a modifier le client? Je sais bien que dans le cas
de Python on est pas lie non plus, mais je trouve juste que c'est plus
simple en Ruby (voir paragraphe suivant).

La solution Ruby est sur ce point super elegante. Apres c'est sur que
en Python, on a vite fait de rediriger les access aux attributs vers
des methodes,


Tu ne comprends pas bien Python, je vois, puisque tu insistes sur la
dichotomie "données" vs "méthodes". En Python, tout est objet, et il n'y
a donc pas de différence *fondamentale* entre "données membres" et
méthodes - dans les deux cas, ce sont avant tout des attributs. Le fait
que les seconds soient appelables ne change rien de ce point de vue.

mais c'est moins elegant je trouve.


A première vue, oui. Quand on comprend le modèle objet de Python - et
entres autre le protocole Descripteur, qui est un des fondements dudit
modèle, et qui sert *entre autres* à implémenter les méthodes et les
propriétés, on se dit qu'entre ce petit peu d'élégance superficielle et
les applications pratiques, le choix est vite fait.


Non non, je sais bien que les methodes sont des objets aussi, qu'une
methode ou une fonction n'est jamais qu'un objet "callable", mes lacunes
doivent etre ailleurs. Ok voila comment je ferais:

#En Python:

class Foo:
def __init__(self):
self.bar = 42

class Foo2:
def __getattr__(self, name):
if name == "bar":
return self.calculateBar()
def calculateBar(self):
return 40 + 2

#Et en Ruby:

class Foo
attr_accessor :bar
def initialize()
@bar = 42
end
end

class Foo2
def initialize()
@bar = 42
end
def bar
return 40 + 2
end
end

En Python, il va falloir ajouter une condition pour chaque nouvel
attribut, ce n'est pas l'ideal (c'est pareil en Perl).

L'autre avantage de cette syntaxe, et là c'est moins subjectif, c'est
le fait qu'on puisse, de façon transparente, remplacer la classe par
n'importe quel objet appelable. Ca m'a déjà rendu service quand il a
fallu remplacer une classe par une fonction "factory" dans un
programme déjà conséquent.



Ah oui, bon point pour Python la.


Oui.


Par contre Perl n'est encore une fois pas en reste sur ce point, le nom
du constucteur est completement libre, j'ai choisi new() pour l'exemple.
Du coup, pour peu que ta factory soit dans le meme package (ce qui ne
veut pas dire dans le meme fichier), elle peut remplacer un constructeur
sans que le code client soit au courant.

Une application un poil
intégriste de ce principe fait que certains développeurs Java vont
t'expliquer qu'instancier directement une classe concrète dans le code
client, c'est Mal(tm) - parce que ça couple trop le code client à une
implémentation donnée. Morale, les dits développeurs créent
systématiquement des usines[1] (le premier qui ajoute "à gaz" a gagné) -
de même qu'ils créent systématiquement des accesseurs.


Oui, j'ai vu ca aussi, des series de paires interface + factory n'ayant
chacune qu'une seule implementation. Trois classes, pour en utiliser
qu'une seule au final, bonjour le bloat :-(




Avatar
Alex Marandon
Bruno Desthuilliers wrote:
Une méthode de 400 lignes en Python ? Allo, Houston, nous avons un
problème !-)


Oui, je suis traumatisé :(

Certes, mais dans ce cas pourquoi essayer quand meme d'empecher ca
avec l'identation forcee ?


Héritage historique. Dans la pratique, c'est effectivement discutable.
Heureusement, Python a suffisament de qualités pour que ce point de
détail (c'en est un dans la pratique - tu indentes toujours ton code
proprement et régulièrement, non ?) reste à sa place : un point de détail.


On est d'accord.

On voit bien que ca ne marche pas,


Oui, après 17 ans, et un succès grandissant malgré l'absence de toute
hype, il me semble évident que "ça ne marche pas".


Rhoo, fais moi dire ce que je n'ai pas dit.

J'ai rarement pu travailler sur du code PHP sans devoir commencer par le
réindenter, ajouter les accolades "manquantes" (ie: celles qui sont
facultatives d'après la syntaxe mais que tout développeur sérieux mettra
quand même), etc.


Ah oui, mais PHP c'est hors concours ;)


Avatar
Bruno Desthuilliers
(snip)
Un regret sur ce sujet: le langage SQL résiste à l'assimilation...


Tu a essayé SQLAlchemy ?

Avatar
Bruno Desthuilliers
Bonsoir !


du retard





Je préfère citer Bruno : "du retard sur quoi ? "



Pour moi, le choix est simple : plus de la moitié des programmes que
j'ai développé avec Python NE PEUVENT PAS l'être avec Ruby.



Ce qui n'est pas mon cas.




Avatar
Bruno Desthuilliers
Bruno Desthuilliers wrote:


(snip)



Ok, je ne vais pas epiloguer sur les caractères non alphanumériques,
quand on programme en Perl, c'est acquis, on n'hesite pas du tout la
dessus.


Désolé, j'ai essayé plusieurs fois d'apprendre Perl, je n'ai jamais pu
m'y faire. Idem en shell script et en PHP d'ailleurs.

En python il m'arrive de rajouter _list ou _map a des noms de
variables a des fins purement mnemotechniques.


Il m'arrive parfois d'avoir un 'map' dans un nom, mais c'est
généralement parce que ça logiquement partie du nom - pas pour me
souvenir que c'est un dict. En général, je me contente d'un pluriel pour
indiquer un collection.

et d'autre part ils limitent la généricité.
(snip)



C'est pareil en Perl. Les %, @ et $ renseignent juste sur une interface,
tu implemente ce que tu veux en dessous ("perldoc perltie" pour en
savoir plus).


Au temps pour moi alors. Ceci étant, je trouve toujours (à titre
personnel et totalement subjectif of course) que ça relève plus de
brouillage que l'information.


D'ailleurs a ce propos, quitte a vouloir etre fool proof, Python
aurait pu forcer l'encapsulation des donnees membres,


Attention : encapsulation != data hiding.



Disons que le data hiding fait partie de l'encapsulation, non ?


Disons que ça peut être utilisé dans cette optique. A la base, l'idée
générale (de l'encapsulation) est plutôt de coder en dur l'invariant et
d'encapsuler (dans une fonction, un objet, un module, tout ce que permet
le langage) ce qui varie. Ca fonctionne de pair avec le découplage -
disons que c'est le "comment-faire" du découplage. Dans cette optique,
le "masquage de données" est surtout un épiphénomène historique, dû
essentiellement à la façon d'implémenter des ADT en C et au modèle objet
de Smalltalk. Enfin, AMHA...


ca me parait plus fondamental que l'indentation.


Ah bon ? Et pourquoi donc ? (attention, y a un piège).



Parce que ca permet de modifier la maniere dont ces donnees membres sont
calculees sans avoir a modifier le client? Je sais bien que dans le cas
de Python on est pas lie non plus,


Donc, ce n'est pas fondamental ?-)

mais je trouve juste que c'est plus
simple en Ruby (voir paragraphe suivant).

La solution Ruby est sur ce point super elegante. Apres c'est sur que
en Python, on a vite fait de rediriger les access aux attributs vers
des methodes,


Tu ne comprends pas bien Python, je vois, puisque tu insistes sur la
dichotomie "données" vs "méthodes". En Python, tout est objet, et il n'y
a donc pas de différence *fondamentale* entre "données membres" et
méthodes - dans les deux cas, ce sont avant tout des attributs. Le fait
que les seconds soient appelables ne change rien de ce point de vue.


mais c'est moins elegant je trouve.


A première vue, oui. Quand on comprend le modèle objet de Python - et
entres autre le protocole Descripteur, qui est un des fondements dudit
modèle, et qui sert *entre autres* à implémenter les méthodes et les
propriétés, on se dit qu'entre ce petit peu d'élégance superficielle et
les applications pratiques, le choix est vite fait.


Non non, je sais bien que les methodes sont des objets aussi, qu'une
methode ou une fonction n'est jamais qu'un objet "callable", mes lacunes
doivent etre ailleurs.


Oui : le protocole descripteur.

Ok voila comment je ferais:

#En Python:

class Foo:
def __init__(self):
self.bar = 42

class Foo2:
def __getattr__(self, name):
if name == "bar":
return self.calculateBar()
def calculateBar(self):
return 40 + 2


class Foo(object):
def __init__(self, bar):
self.bar = bar

@apply
def bar():
def fget(self):
return self._bar * 2
def fset(self, bar):
self._bar = bar
return property(**locals())



En Python, il va falloir ajouter une condition pour chaque nouvel
attribut,


Bin non. Note que __getattr__, __getattribute__ et __setattr__ gardent
leur utilité, que ce soit pour automatiser la délégation (cas le plus
courant) ou pour personnaliser les règles de résolution d'attribut (plus
rare, mais parfois bien utile).


L'autre avantage de cette syntaxe, et là c'est moins subjectif, c'est
le fait qu'on puisse, de façon transparente, remplacer la classe par
n'importe quel objet appelable. Ca m'a déjà rendu service quand il a
fallu remplacer une classe par une fonction "factory" dans un
programme déjà conséquent.



Ah oui, bon point pour Python la.


Oui.



Par contre Perl n'est encore une fois pas en reste sur ce point, le nom
du constucteur est completement libre, j'ai choisi new() pour l'exemple.
Du coup, pour peu que ta factory soit dans le meme package (ce qui ne
veut pas dire dans le meme fichier), elle peut remplacer un constructeur
sans que le code client soit au courant.


Pas compris...

Par contre, et accessoirement, en Python, __init__ n'est pas le
constructeur, c'est l'initialiseur, qui est automatiquement appelé (s'il
existe) après le constructeur. Le constructeur s'appelle __new__, et son
implémentation par défaut se contente de retourner une nouvelle instance
de la classe. On est bien sûr libre de le personnaliser !-)


Une application un poil
intégriste de ce principe fait que certains développeurs Java vont
t'expliquer qu'instancier directement une classe concrète dans le code
client, c'est Mal(tm) - parce que ça couple trop le code client à une
implémentation donnée. Morale, les dits développeurs créent
systématiquement des usines[1] (le premier qui ajoute "à gaz" a gagné) -
de même qu'ils créent systématiquement des accesseurs.



Oui, j'ai vu ca aussi, des series de paires interface + factory n'ayant
chacune qu'une seule implementation. Trois classes, pour en utiliser
qu'une seule au final, bonjour le bloat :-(


Faut bien justifier les sommes extorquées aux grands comptes, n'est-ce
pas ?-)




Avatar
Bruno Desthuilliers
Bruno Desthuilliers wrote:

Une méthode de 400 lignes en Python ? Allo, Houston, nous avons un
problème !-)



Oui, je suis traumatisé :(


Certes, mais dans ce cas pourquoi essayer quand meme d'empecher ca
avec l'identation forcee ?


Héritage historique. Dans la pratique, c'est effectivement discutable.
Heureusement, Python a suffisament de qualités pour que ce point de
détail (c'en est un dans la pratique - tu indentes toujours ton code
proprement et régulièrement, non ?) reste à sa place : un point de détail.



On est d'accord.


On voit bien que ca ne marche pas,


Oui, après 17 ans, et un succès grandissant malgré l'absence de toute
hype, il me semble évident que "ça ne marche pas".



Rhoo, fais moi dire ce que je n'ai pas dit.


Si si, tu l'a dit !-)


J'ai rarement pu travailler sur du code PHP sans devoir commencer par le
réindenter, ajouter les accolades "manquantes" (ie: celles qui sont
facultatives d'après la syntaxe mais que tout développeur sérieux mettra
quand même), etc.



Ah oui, mais PHP c'est hors concours ;)


Bon, ok ----->[]



Avatar
NicolasP

class Foo(object):
def __init__(self, bar):
self.bar = bar

@apply
def bar():
def fget(self):
return self._bar * 2
def fset(self, bar):
self._bar = bar
return property(**locals())



Je ne suis pas un expert en Python et je ne comprends pas ce que fais cette classe.
Bruno, pourrais tu m'expliquer ce que ça fait et comment on l'utilise ?

Nicolas

Avatar
Eric Brunel
On Thu, 22 Feb 2007 08:44:28 +0100, NicolasP wrote:

class Foo(object):
def __init__(self, bar):
self.bar = bar
@apply
def bar():
def fget(self):
return self._bar * 2
def fset(self, bar):
self._bar = bar
return property(**locals())



Je ne suis pas un expert en Python et je ne comprends pas ce que fais
cette classe.
Bruno, pourrais tu m'expliquer ce que ça fait et comment on l'utilise ?


C'est un raccourci pour:

class Foo(object):
def __init__(self, bar):
self.bar = bar

def get_bar(self):
return self._bar * 2
def set_bar(self, bar):
self._bar = bar
bar = property(get_bar, set_bar)

Ca permet de créer un propriété dans la classe, qui se manipule comme un
attribut mais appelle des méthodes derrière: si x est une instance de Foo,
faire "x.bar = ..." appellera en fait set_bar (ou fset dans l'exemple de
Bruno) et lire la valeur de x.bar appellera get_bar (ou fget). Ca permet
d'éviter de créer des accesseurs partout "à la Java" pour des fois qu'on
ait besoin plus tard de transfomer un attribut "en dur" en attribut
calculé. En Python, un attribut est un attribut; si il a besoin de devenir
un attribut calculé plus tard, on le transformera en propriété.
--
python -c "print ''.join([chr(154 - ord(c)) for c in
'U(17zX(%,5.zmz5(17l8(%,5.Z*(93-965$l7+-'])"