Alexander Beletsky's development blog

My profession is engineering

7 Weeks With Python

During my CS101 class I first time meet Python. That’s not completely true, since I played a bit Python before, but I had a chance to see Python in action only during this course. In short, that was really pleasant meet up and I hope it will grown up to prolonged and mutual relationships. I will share some ‘likes’ and ‘dislikes’ about Python, which I would think you find interesting.

What I liked in Python…

Python is very well known language with great reputation and community around it. Big companies, including Google, using python to build enterprise level applications. Hackers love Python cause it combines both simplicity and power. You can do any kind of application development including desktop and web applications. All the time is being compared to Ruby, which is for me ends up to something like this only.

No IDE development

You don’t need any kind of fancy IDE to start up with Python. Sure, IDE is something that makes development more efficient, so if you going to do a lot of programming with Python including debugging you should probably pick one. But for now, I’m totally happy with Sublime Text 2 as IDE.

Sublime Text 2 for Python

Easy to learn

If you know some OO language like C++ or Java, it will be quick jump to Python. Python is object-oriented language but with support of different paradigms as procedural and even functional programming. The basic concepts of variables, conditions and control flow are the same as you get used to. Of course, you spend sometime to know the fundaments - like, how to compare things, how to calculate length of string or list, how to put element into dictionary. Sometimes, I still refer to documentation, but in general all that things are easy to remember with practice.

Interpretation and dynamic typing

Python is interpretator. You never mention the type of object as you declare it or use it. You might apply different operations on object, it would be evaluated on runtime. There are different opinions (holy wars) on Static vs. Dynamic, but as for me with Dynamic languages the overall development velocity is higher. First of all, you don’t spend any time for compilation, which in case of big solutions could be really high. Second, as you are only to able to check results as code executed (even if you just misspell variable name you will know about it only if this code section is evaluated), you are more focused on unit tests and TDD to catch up obvious issues, which in general makes development faster.

Built in types

Python has complete built-in types system. For numbers you can use different types, as int, float, long, complex. The type is evaluated on runtime,

            i = 0               # integer
            j = 1.0             # float
            x = complex(1, -1)  # complex
        

Strings are everything inside the ” quotes,

            str = "I'm string"
        

Btw, during the course I got conclusion that list is the most flexible data structure. Everything you need, you can build upon lists. Lists are nicely handled with Python,

            l = [ 1, 2, 'three', [4, 5], [[6, 7], 8]   
        

Lists are non-optimal for searches, so if you do a lot of searches you might consider using dictionary,

            d = { 'one': 1, 'two': 2, 'three': [3] }
        

Each type has it’s own set of methods. Strings including common operations as concatenation, trimming, substring found etc. For list and dictionaries there are bunch of useful stuff as getting iterators, pushing and poping of elements.

Syntax and Code styles

Syntax and Code styles are commonly another topic of holy war. Fortunately, Python leaves very few room for that. First of all - no semicolons. Second, Python uses indentation as part of language syntax. So, poorly indented code would simply won’t work.

            def my_method_name(arg1, arg2):
                return arg1 < arg2              # right
                
            def my_method_name(arg1, arg2):
            return arg1 < arg                   # won't work!
            
            def my_method(arg1, arg2):
                if arg1 < arg2:
                    return arg1 + arg2          # right
            
                if arg1 == arg2:
                print arg2                      # won't work!
        

Basically, everything that is after “:” have to be indented. This is for if, while, for etc. Using tab instead of curvy braces (or any other symbol or term) is really nice idea, allowing to keep code in the same format and ‘forcing’ one and solid code guidelines along the projects and teams.

What I disliked in Python…

There are no perfect things, moreover perfect languages. Developers have their own habits and opinions on different things. In Python I see several things that makes me little uncomfortable about.

Naming consistency

It sounds like Python adopts C code styles for naming of methods and variables, like longes_cycle or def make_it_work(). But in reality a lot of methods are violating those rules. For instance some methods of dictionary type: fromkeys(), iteritems(), setdefault(). In the same time dict contains the method: has_key().

That’s very annoying. Especially if you don’t have any IDE with names suggesting, it makes it really hard to remember.

Booleans and None

Almost the same as in topic above. Having the C-style (with a lower first symbol) language designers decided to have a special cases.

            a = True        # why not true ?
            b = False       # why not false ?
            x = None        # none ?
        

So, in code which is in general lower case, those True/False/None looking really strange.

            def proc3(input_list):
                if len(input_list) == 0:
                    return None

                for i in range(0, len(input_list)):
                    for j in range(0, len(input_list)):
                        if input_list[i] == input_list[j] and i != j:
                            return False
                return True
        

OO but not OO

Being OO language, Python still relies on some procedural concepts. The good example is calculation of string length. I would expect, that string corresponding method len() or something, but instead we are having ‘global’ function that does that.

            s = "I'm string"
            print len(s)        # why not s.len() ?
        

len() is overloaded for other types, it would work for list and dictionaries as well,

            l = [1, 2, 3]
            d = { 1: 1, 2: 2, 3: 3 }
            
            print len(l)
            print len(d)
        

In the same manner, if you what to get reverse iterator for collection, I would assume there corresponding method that returns that iterator. Bad guess,

            l = [1, 2, 3]
            for e in reverse(l):    # why l.reverse()
                print e
        

__init__() method

Trying out classes in Python first you need to understand is how to construct an object. Python has constructor, that look like that,

            class MyClass:
                def __init__(self, a, b):
                    self.a = a
                    self.b = b
        

I could understand it would be init or _init or constructor, but I will probably never understand __init__ with 2 underscores before and after. It’s ugly.

Conclusions

I’m about to enroll to next Udactity courses, so my Python journey continues. I hope to get more in language and standard library.