Ce diaporama a bien été signalé.
Nous utilisons votre profil LinkedIn et vos données d’activité pour vous proposer des publicités personnalisées et pertinentes. Vous pouvez changer vos préférences de publicités à tout moment.

Python Worst Practices

82 729 vues

Publié le

This is a joke. DO NOT USE ANYTHING YOU SEE IN THESE SLIDES.

  • If you are looking for customer-oriented academic and research paper writing service try ⇒⇒⇒ WRITE-MY-PAPER.net ⇐⇐⇐ liked them A LOTTT Really nice solutions for the last-day papers
       Répondre 
    Voulez-vous vraiment ?  Oui  Non
    Votre message apparaîtra ici
  • Writing good research paper is quite easy and very difficult simultaneously. It depends on the individual skill set also. You can get help from research paper writing. Check out, please ⇒ www.HelpWriting.net ⇐
       Répondre 
    Voulez-vous vraiment ?  Oui  Non
    Votre message apparaîtra ici
  • Puma Toto selaku Bandar Togel Online Terpercaya dan Agen Togel Online Terpercaya yang dapat membantu Anda dalam kemenangan permainan taruhan togel online, dengan minimal deposit hanya 10rb rupiah dan juga bonus new member sebesar 10% dan juga banyak event dan lomba yang di adakan oleh Puma Toto. Proses deposit dan withdraw (penarikan dana) tercepat di segala bandar togel online terpercaya, yakni hanya maximal 1 menit. Mari bergabung bersama dengan Puma Toto dengan keuntungan dan server taruhan togel online terbaik di seluruh Nusantara. Dengan 25 permainan, Puma Toto bekerjasama dengan 25 Negara resmi yang mengeluarkan permainan taruhan togel online. Di antaranya: Togel Singapore, Togel Sgp, Togel Hongkong, Togel Sydney, Togel Brazillia4D, Togel Virginia Night, Togel Penang4D, Togel Vietnam4D, Togel Korea4D, Togel Tokyo Mega, Togel Tokyo4D, Togel Germany4D, Togel Mongolia4D, Togel Tibetian4D, Togel UK4D, Togel Mexico4D, Togel Psco, Togel Oregon1, Togel Oregon2, Togel Oregon3, Togel Swiss4D, Togel Greece, Togel Texas Morning, Togel Spain4D, Togel Carolina, Togel Bangkok4D. Yuk, bergabung bersama dengan Agen Togel Online Terpercaya dan juga Bandar Togel Terpercaya dan terbaik di seluruh Nusantara. Daftarkan diri Anda bersama Puma Toto #agentogelterpercaya #caramaintogel #prediksitogelakurat #prediksiangkajitu #togelsingapore #togelsgp #togelhk #togelhongkong #togelonline #togelterbaik #togelterpercaya #juditogelonline #togelonlineterpercaya
       Répondre 
    Voulez-vous vraiment ?  Oui  Non
    Votre message apparaîtra ici
  • Works For Teens! Hey, I'm only 18 and I thought I was going to have small boobs forever. After using your book for about 2 weeks, I started seeing results! I then used it for another month and I managed to get my breasts up to a C cup (with padding). I'm so pleased and I'm getting a lot more attention from boys now! Thanks you ✱✱✱ https://t.cn/A6Li7BTH
       Répondre 
    Voulez-vous vraiment ?  Oui  Non
    Votre message apparaîtra ici
  • PumaToto | Agen Togel Terpercaya PumaToto merupakan Togel Online | Togel Terpercaya dengan Prediksi Togel Akurat | Prediksi Angka Jitu Bagi kalian yang suka bermain Togel Singapore | Togel HK bisa untuk bergabung dengan PumaToto Cara Main Togel | Cara Pasang Togel | Pasang Togel Online di PumaToto, dengan Discount dan Hadiah Menarik Tentunya Daftarkan diri Anda bersama PumaToto https://caramaintogel.com/
       Répondre 
    Voulez-vous vraiment ?  Oui  Non
    Votre message apparaîtra ici

Python Worst Practices

  1. 1. Python Worst Practices Daniel Greenfeld
  2. 2. Daniel Greenfeld @pydannyI do cartwheels Daniel Greenfeld (@pydanny) Pythonista at Cartwheel Djangonaut at Revsys Co-lead of Django Packages & Open Comparison Learned Python at NASA Fiancé of Audrey Roy
  3. 3. Daniel Greenfeld @pydanny Talk Format Each section will have three components:• At least one ‘Python Worst Practice’ slide• At least one ‘Fixed Python Practice’ slide• A side-by-side comparison slide These slides are already online!
  4. 4. Daniel Greenfeld @pydanny Warning! Don’t use the‘Python Worst Practices’ examples in your code*You may be hunted down and killed *Sometimes these are caught by various code checking tools
  5. 5. Daniel Greenfeld @pydanny Advice! Do consider using the‘Fixed Python Practices’ examples in your code You may get complimented
  6. 6. Fundamentals
  7. 7. Daniel Greenfeld @pydanny Python Worst Practiceobject = MyObject()map = Map()zip = 90213 # common US developer mistakeid = 34 # I still fight this oneI’m guilty • I still use ‘id’ when I shouldn’t • I admit I have a problem • That gives me license to pick on others
  8. 8. Daniel Greenfeld @pydanny Fixed Python Practiceobj = MyObject() # necessary abbreviationobject_ = MyObject() # Underscore so we dont overwritemap_obj = Map() # combine name w/necessary abbreviationmap_ = Map()zip_code = 90213 # Explicit name with US focuspostal_code = 90213 # i18n explicit namezip_ = 90213pk = 34 # pk is often synonymous with idid_ = 34
  9. 9. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practiceobject = MyObject() obj = MyObject() # Use a necessary abbreviationmap = Map() object_ = MyObject() # Use underscore so we dont overwritezip = 90213 # common US developer mistakeid = 34 # I still fight this one map_obj = Map() # combine name with necessary abbreviation map_ = Map() zip_code = 90213 # Explicit name with US focus postal_code = 90213 # International explicit name zip_ = 90213 pk = 34 # pk is often synonymous with id id_ = 34
  10. 10. Daniel Greenfeld @pydannyPython Worst Practice Flipping the booleans true = 0 false = 1 True = False Usually done to support an API
  11. 11. Daniel Greenfeld @pydanny This sort of APIdef crazy_posting_api(value): """ If a value is supplied successfully return ‘0’. Otherwise return ‘1’ """ if value: return 0 return 1
  12. 12. Daniel Greenfeld @pydannyFixed Python Practiceclass CrazyApiConsumer(object): def __init__(self, value): self.value = value def post(self): # fix booleans in/around the return statement response = crazy_posting_api(self.value) return not bool(response)cac1 = CrazyApiConsumer("hello")print(cac1.post())cac2 = CrazyApiConsumer("")print(cac2.post())
  13. 13. Daniel Greenfeld @pydannySide-by-side comparisonWorst Practice Fixed Practicetrue = 0 class CrazyApiConsumer(object):false = 1True = False def __init__(self, value): self.value = value def post(self): # fix booleans in/around the return statement response = crazy_posting_api(self.value) return not bool(response) cac1 = CrazyApiConsumer("hello") print(cac1.post()) cac2 = CrazyApiConsumer("") print(cac2.post())
  14. 14. Daniel Greenfeld @pydannyPython Worst Practice Identifying variable types with prefixes strColor = "green" boolActive = False intPythonYears = 20 dtPythonFirstUsed = "04/20/2011" Mixing case doesn’t help either
  15. 15. Daniel Greenfeld @pydannyPython Worst PracticeConserving pixels by removing the vowelsclr = "green"ctv = FalsepythnYrs = 20pthnFrstSd = "04/20/2011"
  16. 16. Daniel Greenfeld @pydannyPython Worst Practice c = "green" a = False p = 20 t = "04/20/2011"
  17. 17. Daniel Greenfeld @pydannyFixed Python Practice color = "green" active = False python_years = 20 python_first_used = "04/20/2011"Python assumes we are all consenting adults • Infer from naming schemes the type/purpose • Don’t be constrained by type
  18. 18. Daniel Greenfeld @pydannyFixed Python Practicecolor = "green"active = Falsepython_years = 20python_first_used = "04/20/2011" The pixel shortage is over. Use reasonably long variable names.
  19. 19. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practice c = "green" a = False color = "green" p = 20 t = "04/20/2011" active = False python_years = 20 python_first_used = "04/20/2011" clr = "green" ctv = False pythnYrs = 20 pthnFrstSd = "04/20/2011"strColor = "green"boolActive = FalseintPythonYears = 20dtPythonFirstUsed = "04/20/2011"
  20. 20. Daniel Greenfeld @pydanny Python Worst Practice Don’t use enumeratefoo = [1, 2, 3]for i, item in zip(range(len(foo)), foo): print i, item
  21. 21. Daniel Greenfeld @pydannyFixed Python Practice Use enumeratefoo = [1, 2, 3]for i, item in enumerate(foo): print i, item • Memorize the Python built-ins • Makes your code easier to read • Proven code
  22. 22. Daniel Greenfeld @pydannySide-by-side comparisonWorst Practice Fixed Practicefoo = [1, 2, 3] foo = [1, 2, 3]zip(range(len(foo)), foo): for i, item in enumerate(foo): print i, item print i, item
  23. 23. Python Worst Practice Present using Different Fonts Dark Text Dire Backgr#nds
  24. 24. Daniel Greenfeld @pydannyPython Worst Practice Present using High Contrast Easy-to-read fonts All devices off All programs off
  25. 25. Daniel Greenfeld @pydannySide-by-side comparisonWorst Practice Fixed Practice Present using Present using Different Fonts High Contrast Dark Text Easy-to-read fonts Dire Backgr#nds All devices off All programs off
  26. 26. Classes
  27. 27. Daniel Greenfeld @pydannyPython Worst PracticeImplementing Java-style getters and setters import logging log = logging.getLogger() class JavaStyle: """ Quiz: what else am I doing wrong here? """ def __init__(self): self.name = "" def get_name(self): return self.name def set_name(self, name): log.debug("Setting the name to %s" % name) if isinstance(name, str): self.name = name else: raise TypeError() if __name__ == "__main__": j = JavaStyle() j.set_name("pydanny did this back in 2006!") print(j.get_name())
  28. 28. Daniel Greenfeld @pydannyFixed Python Practice Python properties! import logging log = logging.getLogger() class PythonStyle(object): def __init__(self): self._name = "" Accessor @property def name(self): return self._name Mutator @name.setter def name(self, value): """ Because name is probably a string well assume that we can infer the type from the variable name""" log.debug("Setting the name to %s" % value) self._name = value if __name__ == "__main__": p = PythonStyle() p.name = "pydanny doing it the right way" print(p.name)
  29. 29. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practiceimport logging import logginglog = logging.getLogger() log = logging.getLogger()class JavaStyle: class PythonStyle(object): """ Quiz: what else am I doing wrong here? """ def __init__(self): def __init__(self): self._name = "" self.name = "" @property def get_name(self): def name(self): return self.name return self._name def set_name(self, name): @name.setter log.debug("Setting the name to %s" % name) def name(self, value): if isinstance(name, str): """ Because name is probably a string well assume that we can self.name = name infer the type from the variable name""" else: log.debug("Setting the name to %s" % value) raise TypeError() self._name = valueif __name__ == "__main__": if __name__ == "__main__": j = JavaStyle() p = PythonStyle() j.set_name("pydanny did thisp.namein 2006!") doing it the right way" back = "pydanny print(j.get_name()) print(p.name)
  30. 30. Daniel Greenfeld @pydanny Python Worst Practice Using property setters as action methods!class WebService(object): @property def connect(self): self.proxy = xmlrpc.Server("http://service.xml")if __name__ == __main__: ws = WebService() ws.connect A.K.A.Trying to make your Python code look like Ruby
  31. 31. Daniel Greenfeld @pydanny Fixed Python Practice Methods please!class WebService(object): def connect(self): self.proxy = xmlrpc.Server("http://service.xml")if __name__ == __main__: ws = WebService() ws.connect()
  32. 32. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practiceclass WebService(object): class WebService(object): @property def connect(self): def connect(self): self.proxy = xmlrpc.Server("http://service.xml") self.proxy = xmlrpc.Server("http://service.xml")if __name__ == __main__: if __name__ == __main__: ws = WebService() ws.connect ws = WebService() ws.connect()
  33. 33. Exceptions
  34. 34. Daniel Greenfeld @pydannyPython Worst Practice Passing Generic Exceptions silently try: do_akshun(value) except: pass• Ignorance is not bliss• You have no idea what your system is doing• Arguably better to not have this in your code
  35. 35. Daniel Greenfeld @pydanny Fixed Python Practice Use specific exceptions and/or loggingclass AkshunDoesNotDo(Exception): """ Custom exceptions makes for maintainable code """ passtry: do_akshun(value)except AttributeError as e: log.info("Can I get attribution for these slides?") do_bakup_akshun(vlue)except Exception as e: log.debug(str(e)) raise AkshunDoesNotDo(e)
  36. 36. Daniel Greenfeld @pydannySide-by-side comparisonWorst Practice Fixed Practicetry: class AkshunDoesNotDo(Exception): do_akshun(value) """ Custom exceptions makes for maintainable code """except: pass pass try: do_akshun(value) except AttributeError as e: log.info("Can I get attribution for these slides?") do_bakup_akshun(vlue) except Exception as e: log.debug(str(e)) raise AkshunDoesNotDo(e)
  37. 37. Getting controversial
  38. 38. Daniel Greenfeld @pydanny Python Worst Practice Using exec for dynamic importsimports = "from {0} import {1}".format("random", "randrange")exec(imports)print(randrange(10)) • Hard to debug • Security risk • Sets bad precedents
  39. 39. Daniel Greenfeld @pydannyFixed Python Practice Using importlib for dynamic imports import importlib funstuff = importlib.import_module(random) print(funstuff.randrange(10))• importlib is in the standard library• Really explicit• Direct tie into the Python machinery
  40. 40. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practiceimports = "from {0} import {1}".format("random", "randrange") import importlibexec(imports) funstuff = importlib.import_module(random)print(randrange(10)) print(funstuff.randrange(10))
  41. 41. Daniel Greenfeld @pydanny Python Worst Practice Generally using lambdasswap = lambda a, x, y: lambda f = a.__setitem__: (f(x, (a[x], a[y])), f(y, a[x][0]), f(x, a[x][1]))() • Too many characters on one line • Lambdas by design does not have docstrings • Does not necessarily mean less characters • I can’t get this sample to work!
  42. 42. Daniel Greenfeld @pydanny Fixed Python Practice def swap(a, x, y): """ Swap two position values in a list """ a[x],a[y] = a[y],a[x]• Doc strings that show up nicely in help/Sphinx• Easier to read• In Python, functions are first class objects• Whenever possible avoid using lambdas
  43. 43. Daniel Greenfeld @pydanny Side-by-side comparisonWorst Practice Fixed Practiceswap = lambda a, x, y: def swap(a, x, y): lambda f = a.__setitem__: """ Swap two position values in a list """ (f(x, (a[x], a[y])), a[x],a[y] = a[y],a[x] f(y, a[x][0]), f(x, a[x][1]))()
  44. 44. Daniel Greenfeld @pydannyPython Worst Practice Configuring your project with XML<pydanny-ml> <do action="call_view">com.pydanny.nextSlide</do> <global name="spam" value="eggs" /></pydanny-ml>• You can’t convince me that XML is the better way• You are forcing me to learn a new language
  45. 45. Daniel Greenfeld @pydannyFixed Python Practice ? Use Python for configuration! spam = "eggs" actions = [ (call_view, com.pydanny.nextSlide) ] • Is this the right way? • This allows conditional logic • Iterators • i.e. “Magic Configuration”
  46. 46. Daniel Greenfeld @pydannyPython Worst Practice ‘Magical configuration code’ INSTALLED_APPS += [p for p in os.listdir(BASE) if os.path.isdir(p)] MIDDLEWARE_CLASSES = [...] def callback(arg, dirname, fnames): if middleware.py in fnames: m = %s.middleware % os.path.split(dirname)[-1] MIDDLEWARE_CLASSES.append(m) urlpatterns = patterns(, ...) for app in settings.INSTALLED_APPS: if not app.startswith(django): p = url(^%s/ % app, include(%s.urls) % app) urlpatterns += patterns(, p) Ugh. http://www.slideshare.net/jacobian/the-best-and-worst-of-django
  47. 47. Daniel Greenfeld @pydanny Fixed Python Practice urlpatterns = patterns("",PREREQ_APPS = [ # Django url(r"^$", homepage, name="home"), "django.contrib.admin", url(r"^accounts/", include("accounts.urls")), "django.contrib.auth", url(r"^admin/", include(admin.site.urls)), "django.contrib.contenttypes", url(r"^about/", include("about.urls")), "django.contrib.sessions", url(r"^profiles/", include("profiles.urls")), "django.contrib.sites", url(r"^notices/", include("notification.urls")), "django.contrib.messages", ... "django.contrib.humanize", MIDDLEWARE_CLASSES = [ ) "django.contrib.flatpages", "django.middleware.common.CommonMiddleware", "django.contrib.sessions.middleware.SessionMiddleware", # external "django.middleware.csrf.CsrfViewMiddleware", "notification", # must be first "django.contrib.auth.middleware.AuthenticationMiddleware", "staticfiles", "reversion.middleware.RevisionMiddleware", "uni_form", "django.contrib.messages.middleware.MessageMiddleware", ... ... ] ]Explicit is better This isn’t that much typing, is it? then Implicit
  48. 48. Daniel Greenfeld @pydanny Fixed Python Practice urlpatterns = patterns("",PREREQ_APPS = [ # Django url(r"^$", homepage, name="home"), "django.contrib.admin", url(r"^accounts/", include("accounts.urls")), "django.contrib.auth", url(r"^admin/", include(admin.site.urls)), "django.contrib.contenttypes", url(r"^about/", include("about.urls")), "django.contrib.sessions", url(r"^profiles/", include("profiles.urls")), "django.contrib.sites", url(r"^notices/", include("notification.urls")), "django.contrib.messages", ... "django.contrib.humanize", MIDDLEWARE_CLASSES = [ ) "django.contrib.flatpages", "django.middleware.common.CommonMiddleware", "django.contrib.sessions.middleware.SessionMiddleware", # external "django.middleware.csrf.CsrfViewMiddleware", "notification", # must be first "django.contrib.auth.middleware.AuthenticationMiddleware", "staticfiles", "reversion.middleware.RevisionMiddleware", "uni_form", "django.contrib.messages.middleware.MessageMiddleware", ... ... ] ] Python’s design is predicated on the proposition that code is more often read than written. http://www.slideshare.net/jacobian/the-best-and-worst-of-django/44
  49. 49. Daniel Greenfeld @pydanny Fixed Python Practice Use a config filespam = "eggs"[actions]call_view = com.pydanny.nextSlide Read up on config parserhttp://docs.python.org/library/configparser.html
  50. 50. Daniel Greenfeld @pydannySide-by-side comparisonWorst Practice Fixed PracticeXML simple python fileslogic heavy python config (.cfg) files
  51. 51. Documentation
  52. 52. Daniel Greenfeld @pydanny Python Worst Practice Bad docstringsclass Pythonista(): # Old style class! """ This class represents a Python programmer """ def code(self): """Write some code """ code, inspiration = Code(), Inspiration() for hour in Effort(): try: code += hour + inspiraion except CurseWorthyBug: ... • Do really obvious objects require doc strings? • Complex methods require more than docstrings!
  53. 53. Daniel Greenfeld @pydanny Fixed Python Practice class Pythonista(object): def code(self): """ Writes code following these steps 1. Create a space for coding 2. Get some inspiration 3. Loop through some hours of effort Spend a 4. Write some codefew minutes 5. Pull out hair cause of bugs """documenting code = Code() the critical inspiration = Inspiration() for hour in Effort(): stuff, okay? try: code += hour + inspiraion except CurseWorthyBug: ...
  54. 54. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practiceclass Pythonista(): # Old style class! class Pythonista(object): """ This class represents a Python programmer """ def code(self): def code(self): """ Writes code following these steps """Write some code """ 1. Create a space for coding code, inspiration = Code(), Inspiration() 2. Get some inspiration for hour in Effort(): 3. Loop through some hours of effort try: 4. Write some code code += hour + inspiraion 5. Pull out hair cause of bugs except CurseWorthyBug: """ ... code = Code() inspiration = Inspiration() for hour in Effort(): try: code += hour + inspiraion except CurseWorthyBug: ...
  55. 55. Daniel Greenfeld @pydanny Python Worst Practice Using a wiki for project documentation “Wikis are where project documentation goes to die” Jacob Kaplan-Moss• Generally not version controlled• Backups? Mirrors?• Editing via the web? Ugh.• No pull requests - smaller group of contributors
  56. 56. Daniel Greenfeld @pydannyFixed Python Practice• Use Restructured Text• Use Sphinx• Host on http://readthedocs.org
  57. 57. Daniel Greenfeld @pydannySide-by-side comparisonWorst Practice Fixed Practice
  58. 58. Daniel Greenfeld @pydannyPython Worst Practice >>> import that The Anti-Zen of Python, by Daniel Greenfeld Ugly is better than beautiful. Implicit is better than explicit. Complicated is better than complex. Complex is better than simple. Nested is better than flat. Dense is better than sparse. Line code counts. Special cases are special enough to break the rules. Although purity beats practicality. Errors should always pass silently. Spelchek iz fur loosers. In the face of explicity, succumb to the temptation to guess. There should be many ways to do it. Because only a tiny minority of us are Dutch. Later is the best time to fix something. If the implementation is hard to explain, its a good sell. If the implementation is easy to explain, it wont take enough time to do. Namespaces are too hard, just use import *! http://pypi.python.org/pypi/that
  59. 59. Daniel Greenfeld @pydannyFixed Python Practice >>> import this The Zen of Python, by Tim Peters Beautiful is better than ugly. Explicit is better than implicit. Simple is better than complex. Complex is better than complicated. Flat is better than nested. Sparse is better than dense. Readability counts. Special cases arent special enough to break the rules. Although practicality beats purity. Errors should never pass silently. Unless explicitly silenced. In the face of ambiguity, refuse the temptation to guess. There should be one-- and preferably only one --obvious way to do it. Although that way may not be obvious at first unless youre Dutch. Now is better than never. Although never is often better than *right* now. If the implementation is hard to explain, its a bad idea. If the implementation is easy to explain, it may be a good idea. Namespaces are one honking great idea -- lets do more of those! Core Python
  60. 60. Daniel Greenfeld @pydanny Side-by-side comparison Worst Practice Fixed Practice >>> import this>>> import that The Zen of Python, by Tim PetersThe Anti-Zen of Python, by Daniel Greenfeld Beautiful is better than ugly.Ugly is better than beautiful. Explicit is better than implicit.Implicit is better than explicit. Simple is better than complex.Complicated is better than complex. Complex is better than complicated.Complex is better than simple. Flat is better than nested.Nested is better than flat. Sparse is better than dense.Dense is better than sparse. Readability counts.Line code counts. Special cases arent special enough to break the rules.Special cases are special enough to break the rules. Although practicality beats purity.Although purity beats practicality. Errors should never pass silently.Errors should always pass silently. Unless explicitly silenced.Spelchek iz fur loosers. In the face of ambiguity, refuse the temptation to guess.In the face of explicity, succumb to the temptation to guess. There should be one-- and preferably only one --obvious way to do it.There should be many ways to do it. Although that way may not be obvious at first unless youre Dutch.Because only a tiny minority of us are Dutch. Now is better than never.Later is the best time to fix something. Although never is often better than *right* now.If the implementation is hard to explain, its a good sell. If the implementation is hard to explain, its a bad idea.If the implementation is easy to explain, it wont take enough time to do. If the implementation is easy to explain, it may be a good idea.Namespaces are too hard, just use import *! Namespaces are one honking great idea -- lets do more of those!
  61. 61. Questions?

×