Page 3 of 4

Egypt 1st meeting results

Last Friday was the date for the 1st EgyPy meeting. Few people showed up. We discussed the release of IronPython 2 Alpha 3, IronRuby, Microsoft support for dynamic languages & DLR. Also, Dody showed us Havana, our CMS which we built using C# & IronPython 1.1. Havana is different because

  1. Havana is not strictly a CMS. It's a content management framework with a helper interface.
  2. It supports uploading of content in zipped files
  3. Command-line interface: So you can type "zip *.jpg" and get all your .jpg images compressed in a zip file!!!
  4. It supports IronPython scripting: It's not just for designers

We discussed how Havana uses IronPython & the chances of integrating DLR with it. Writing a workflow DSL in IronRuby will be very nice [:D]

1st Egypy (Egyptian Python Users Group) meeting

What: 1st Egypy (Egyptian Python Users Group) meeting Where: Cilantro Cafe in Mesaha Square, Dokki, Cairo, Egypt When: Friday, 27th of July, 2007, 6:00 PM Why:

  1. For the community members to know each other.
  2. To define the activities for the next months
  3. Share experience with Python
  4. Have fun :)

If you don't know the place, it's here For any questions, you can contact me.

Python community in Egypt

I am planning to start a Python community in Egypt. Python is a high-level dynamic programming language which values programmers' productivity over machine performance.

You can register here (dead link) & find the Python forum

Silverkey Demo Day II - an insider's report

Update 16/7/2007: A version of my presentation in PowerPoint 2003 format is attached with this post. The demos are attached with the original one here (dead link)

For audience opinons, see Korayem (dead link) or Ahmad Shreef. To know how we got the idea of the demo day, read Dody's story. (dead link)

The Idea

The idea of the 2nd demo day started after MIX 07. We were very excited about the new technologies: Silverlight, Jasper & DLR. We got more excited after we used these technologies in our own products. We chose topics 7 weeks before the demo day. At that time we already started using Jasper in one of our projects & was thinking about porting another one to the DLR, which was using IronPython 1.1.

I'm using Python since 2004 & I have presented it to a lot of my friends. I have presented it also at an internal demo day, which yielded this post. This was a good chance to present Python to the egyptian developers community. Dody suggested that it should be a comparison between static & dynamic languages. I was very worried about this, because it's hard to control it.

Preparation

We started preparing for demo day 2 one week before the end of May. Everybody had his topics. Taher, Ayman & Dody started looking for the suitable place. The rest of us worked on reading everything we can find about the new technologies, using them (in Silverkey applications, if possible), making the presentations ready, etc. Some changes happened to the topics & materials. Some people declined, for several reasons. We have been rehearsing the sessions daily for 2 weeks before the demo day.

The Day

I arrived at the place at 8:10 AM. I was wearing a 3-peaces suite (& it was about 40-something °C). People were telling a lot of jokes about me, including Dody calling me the "Mafia Guy" [:)].

We started checking for everything in the place: the microphones, the projectors, the demos, the business card, etc. We were worried: Only Hossam Zain, Mohammad Hossam & Mohammad Meligy gave presentation in the previous demo day. For the rest of us, this was the first time to present to a large audience. The size of the croud is large this time: almost 400 people.

The action started at 10:00 PM with the keynote, where Taher - our CEO - introduced Silverkey & why we are making a second demo day.

The first technical session was about WCF, by Mohammad Hossam. People liked the session & how he presented it.

After that, we had 2 parallel tracks. The problem with this is that you cannot attend all the sessions you like. So I'm describing only the sessions I attended. We are going to upload the video sessions very soon.

I attended the Jasper, by Ahmad Ali. Jasper is an ORM based on Microsoft Entity Framework for dynamic languages. I liked this session & Ahmad style was really good.

The next session was about WF, by Mohammad Nour. He presented it well, but he was frustrated a little bit at the end because he felt that people didn't get it, but the questions at the end showed that some people were really interested.

The next session was LINQ to XML, by Mai Soliman. She presented the material very well & she answered a lot of questions.

The next session was by me & Mohammad Hossam about comparing IronPython with C# 3. I was worried as hell about this one. AFAIK, this is the first time somebody talks about Python in Egypt. What scared me more is that it was a dialog, not a one-sided presentation. I thought that this would be the best or the worst session in demo day. The audience were interested & some of them were already using Python, so this will be a good start for a Python community here in Egypt.

We had an open-mic session after that. The people took the mic & started discussing their ideas. We started by asking this question "What do you think will be the next big thing?". As usual, it turned into the boring java-vs-.net discussion, sometimes mentioning PHP. We heard the usual argument: Java is more suitable than .net for enterprise applications. We tried to move it to another subject, but to no avail.

Finally, I attended the Blackbelt Javascript by Mohammad Meligy. Though Meligy can always keep the audience interested, he always takes more time that he should :).

A final note: we are not Microsoft. We are not a Microsoft partner or a training company. We made this only because we love it. It's a chance for all of us to share what we know. Being the presenter doesn't mean that I'm the smartest guy. By the way, we are not the only company which shares knowledge with the community. It's just that we have the biggest event.

We really appreciate everyone who came, specially people who came from places far-aways as Alexandria. It was a great chance to meet all of these people. We are waiting for your suggestion

Silverkey demo day 2

Dear Pythoneers Silverkey is going to hold its second demo day on 7/7/2007 in Cairo, Egypt. You can see the demo day agenda here. We are going to make a discussion about static vs. dynamic languages, using C# and Python as examples. I'm going to represent Python side, and Mohammad Hossam is going to represent C# side Waiting for you there

IronPython Cookbook

Michael Foord (a.k.a. Fuzzyman) made "IronPython Cookbook". It is essential for every IronPython programmer, whether you are working on Windows Forms, Direct3Dor network protocols

Next IronPython talks at Teched 2007

Here http://blogs.msdn.com/ironpython/archive/2007/05/25/our-talks-at-teched-2007-june-4-8th-in-orlando.aspx This is going to be more in-depth than the talks at MIX. I just hope they release the screencasts like they did to the screencast

Why you should use Python

Dynamic languages are very productive. This is why they are very popular in the UNIX community, because they form an essential part of their culture. In the Windows community very few people used them. People believed that dynamic languages are slow. In 2006, the situation changed dramatically. I think there are two reasons for this:

  1. Ruby on rails: Rails was created to optimize programmer's happiness, thus leading to much higher productivity.
  2. C# 3.0: A lot of the new features in C# 3.0 are inspired by dynamic languages like Python.

I will try to explain what makes Python unique. Almost everything I mention here applies for other dynamic languages as well.

This is not meant to be a Python tutorial. A lot of Python tutorials and free books are available and easy to find and the syntax is very clear that you don't need a tutorial to read the examples here.

Interactive You can just launch the interpreter, write code and see the result immediately. No need for a lengthy compile-run-debug loop, thus reducing developing time.

Strongly typed: Python is

  1. Interpreted: It is parsed and executed at runtime.
  2. Strongly typed: It does type checking.
  3. Dynamic: Everything happens at runtime (including type checking).

For example the following function

>>> def add(x, y):
...   return x + y

will work if

  1. x and y are of the same type (or compatible type).
  2. This type provides the + operation.

If one of the above conditions is broken, Python will raise an exception at runtime, stating the exact error.

>>> add(3, 5)
8
>>> add("hello", " world")
'hello world'
>>> add(3, " world")
Traceback (most recent call last): 
File "<stdin>", line 1, in ? 
File "<stdin>", line 2, in add
TypeError: unsupported operand type(s) for +: 'int' and 'str'

Readability Python is known for its readability. You can learn the syntax of Python in a day.

if x in (1, 2, 3, 7, 4): 
  print 'Not found'
else: 
  print 'found'

Rich data types Python has a lot of data-types built-in, which makes your life a lot easier. Take a dictionary for example

>>> d = {'name': 'Bond. James Bond!!', 'car': 'Aston Martin'}

You can use any hashable object as a dictionary key. To access a value just use

>>> d['name']
'Bond, James Bond!!'

For example, how to implement a graph in Python? Very easy, just use a 2D dictionary

graph = {'A': {'B': 14}, 'B': {'C': 3, 'D': 9}, 'C': None, 'D': None}

which represents this graph

graph

To get the value of the edge from B-C, use

>>> graph['B']['C']
3

This was simple, right?

The story doesn't end here. You have also built-in data structures: list, tuple, set, etc. Learn how to use them instead of building your own inefficient variants.

Objects have types, variables don't!! As I mentioned before, Python is a strongly typed language, which means that you cannot treat one type as another. For example

>>> x = 0
>>> x.keys()
Traceback (most recent call last):
File "<stdin>", line 1, in ?
AttributeError: 'int' object has no attribute 'keys'

But, you can do the following

>>> x = 0
>>> x = {'name': 'Bond, James Bond!!'}

The variable x has no type, but the object that x points to has a type. You can change the object that x points to using the assignment operator. This simple fact may be a little hard to understand at first, but to clarify it I will show a counter example. In C# you can write

class Base {}
class Derived : Base{
  public void MyMethod() {}
}

Base b = new Derived();
b.MethodCall();

This will not work because the reference b is of type Base, though the object itself has this method. You have to rewrite the last line to become

((Derived)b).MethodCall();

OK, how this can be useful? How many times you used 2 variables to point to the same piece of information? Like

string personIdString = context.Request.Params["personId"];
int personId = int.Parse(personIdString);

In Python, this can be written as

personId = context.Request.Params['personId']
personId = int(personId)

Returning multiple values This is a stupid problem: If you want to return more than one value, you have to use out parameters.

Python solves this by using tuples. Tuples are simply constant lists, so how can we use them?

def return_many_values():  
  return (1, 2, 4, 8)

The above function returns a single object: The tuple object. The caller can unpack the tuple using this

(a, b, c, d) = return_many_values()

After executing the last statement a = 1, b = 2, c = 4, d = 8.

Because this is a very common idiom, you can ignore the braces.

def return_many_values():  
  return 1, 2, 4, 8
a, b, c, d = return_many_values()

Keyword arguments Don't you wish that you can pass parameters by name? Something like

Factorial(x=10)
  1. It is much easier to read code: No need to search on MSDN to know what the parameters mean.
  2. Much less errors: You remember the parameters by name, not by order.
  3. The parameters can have default values, so you can send only the needed parameters.
  4. They can be send out-of-order: CreateWindow(x=0, y=10) is the same as CreateWindow(y=10, x=0)

Batteries included An essential part of Python's philosophy is the Battaries included concept: The default installation should provide most of the libraries need for common tasks: Threading, Mail (SMTP, IMAP, POP3), Regex, GUI, Complex numbers, compression (Tar, Zip, ...) and a lot of other useful libraries.

Not limited If you are a Java programmer, you have suffered difficulties using platform-specific features, for example COM components. It is an essential part of Python culture that the programmers are consenting adults: they know what they should do, so the language must help them doing what they want. This is why Python is not isolated from the platform. For example, you have

  1. CPython: The default Python implementation, written in C.
  2. Jython: Implementation on top of JVM.
  3. IronPython: Implementation on top of CLR.
  4. win32all: A library for CPython to use Win32 APIs & COM components.
  5. Carbon: MacOS X specific APIs.

You can write cross-platform code in Python, but you can also write platform-specific components for best use of your platform.

Everything is an object Classes are objects. Functions are objects. This makes your life easier for 2 reasons

  1. You can add members at runtime:
  2. You can add members to an existing class : and all new instances will have this member.
  3. You can add members to an existing object : and this member will be specific to this object. This can be useful in GUI applications if you want to attach a data item to an existing widget.
  4. You can add members to a function: I will explain how to use this in a minute how to do this.
  5. You can change objects at runtime: I will explain this with an example.

You are required to implement the factorial function with caching. If you are doing it in C#, it will look like

public class AdvancedMath{  
  static SortedDictionary<int, int> _cache = new SortedDictionary<int, int>();
  static int Factorial(int x)  {
    if (_cache.ContainsKey(x))
      return _cache[x];
    if (x == 0)
      return 1;
    int result = x * Factorial(x - 1);    
    _cache.Add(x, result);    
    return result;  
  }
}

What is wrong with this code?

  1. It couples the caching to the calculation.
  2. The cache contains all intermediate values: This can be good or bad, depending on your usage.
  3. Factorial(100) = 0. Overflow.

We can solve the first problem by separating the caching & the calculation into 2 different functions

static SortedDictionary<int, int> _cache = new SortedDictionary<int, int>();
static int Factorial(int x)
{
  return Caching(x, _FactorialImpl);
}

delegate int MathDelegate(int x);
static int Caching(int x, MathDelegate mathDelegate)
{
  if (_cache.ContainsKey(x))
    return _cache[x];
  int result = mathDelegate(x);
  _cache.Add(x, result);
  return result;
}

static int _FactorialImpl(int x)
{
  if (x == 0)
    return 1;
  return x * _FactorialImpl(x - 1);
}

This solves the first 2 problems, but not the third. Besides, the Caching() function is not generic enough: It handles only integers! Of course, you can use objects instead of integers, but how can you cache functions with more than 1 parameter! I will be happy if you send me the generic solution in C#, but I like the generic solution in Python

# This function takes any function as a parameter & returns an 
# equivalent function, but with caching
def cached(old_fn):  
  def new_fn(*args):# *args means that it can accept any
                    # number of arguments. They will                    
                    # be contained in the tuple `args`    
    if new_fn.cache.has_key(args):      
      return new_fn.cache[args]    
    result = old_fn(*args)  # We are passing all the                           
                            # arguments to the original                           
                            # function. If the number of                           
                            # arguments is not correct,                           
                            # it will throw an exception    
    new_fn.cache[args] = result    
    return result  
  new_fn.cache = {} # the cache is a member of the                     
                    # function itself  
  return new_fn

  def factorial(n):  
    if n == 0:    
      return 1  
    return n * factorial(n - 1)

  factorial = cached(factorial)

Python solution has many advantages over the C# solution

  1. The caching is decoupled from the calculation.
  2. The caching contains only final values.
  3. The cache is not coupled to the function itself and we are not using a global cache, which is a cleaner design.
  4. factorial(100) = 93326215443944152681699238856266700490715968264381621468592963895217599993229915608941463976156518286253697920827223758251185210916864000000000000000000000000L This is due to the fact that an integer recognizes an overflow (because it is an object, not just stupid 4 bytes) and converts itself to a long, which can represent large numbers.

  5. It can handle any number of arguments.

The power of introspection You can call a function at runtime by its name. This allows us to call yet undefined functions. I will illustrate this with an example.

This is the standard C# idiom for SAX parsing of an XML document

try{  
  XmlTextReader rdr = new XmlTextReader();  
  rdr.WhitespaceHandling = WhitespaceHandling.None;  
  while(rdr.Read())  
  {    
    switch (rdr.Name)    
    {      
      case "scoresheet":      
        if (rdr.IsStartElement())      
        {      
          // handle element start      
        }      
        else      
        {      
          // handle element end      
        }      
        break;      
      // handle other cases here      
      default:      
      // handle 'unexpected element' error    
      }  
    }
  }
  catch (XmlException ex)
  {  
    // handle error
  }

You have to write a huge switch statement with a lot of nesting to read a complex XML document, or you can modify it a little bit to forward to an observer class.

The problem with this design is inflexibility: you have to maintain the mapping yourself within the switch statement. With Python, you can make a more extensible solution

This is the main driver

from xml.sax import parse as sax_parser
parser = MySaxParser()
sax_parse(file_name, parser)

The parser will be something like

# This is the base class that you will inherit
class BaseSaxHandler(xml.sax.handler.ContentHandler):
  def startElement(self, tag, attributes):
    tag = str(tag) # convert unicode -> str

    # get a method in this object named 'start_' + tag, or
    # return None if the method doesn't exist
    handler = getattr(self, 'start_' + tag.lower(), None)
    if handler:
      handler(attributes)
    else:
      self.error_unknow_start_tag(tag, attributes)

  def endElement(self, tag):
    tag = str(tag)
    handler = getattr(self, 'end_' + tag.lower(), None)
    if handler:
      handler()
    else:
      self.error_unknown_end_tag(tag)

  def error_unknown_start_tag(self, tag, attributes):
    print 'Unknown start tag:', tag

  def error_unknown_end_tag(self, tag):
    print 'Unknown end tag:', tag

class MySaxParser(BaseSaxHandler):
  def start_channel(self, attributes):
    # Look Ma, no switch  
    print '<channel>'

  def end_channel(self):
    print '</channel>'

What are the benefits?

  1. No need to repeat the switch statement.
  2. Isolated error handling.
  3. Extensions are easy to do: You can make MySaxParserV2 which inherits MySaxParser and add/override methods to handle new/existing tags.

Intropection can make your life easier when implementing proxies and web services. I suggest you read the book Dive Into Python_ for more in-depth explanation.

Used by the most successul sites

  1. Google
  2. Industrial Light & Magic: Makers of 'Star Wars' movies.
  3. YouTube.com
  4. Reddit.com: One of the most popular social bookmarking sites.
  5. YouOs.com: Online OS.
  6. And many others

References

Some advantages of scripted web applications

This is an article by Clinton Forbes explaining why scripting languages are popular for web applications.

As far as performance goes, both the ASP and ASP.NET systems hold up well in times of high-traffic (usually around the time of major sporting events). However the performance of our systems is not due to any inherent characteristics of the ASP or ASP.NET environments, it is due to careful consideration of which parts of the applications are critical for good performance and which pieces of content absolutely must be cached to have any hope of coping with high-traffic.

Go read it (dead link)

How to solve Symbian problems?

In a previous post, I mentioned a lot of reasons why I hate Symbian, but not everyone has the choice of choosing which OS to work on. In this post I will try to mention what are the available solutions to this (according to my own experience).

  1. J2ME: J2ME is available on all Smart Phones. It is the most widely used environment for writing mobile software. Unfortunately, it has a lot of limitations. You cannot write C++ extensions easily with it & a lot of the functionality is dependent on the device itself. Most of these limitations are removed from newer phones (e.g. Now you can access the file system of your phones), but if you want to write programs for older phones, you are stuck
  1. Python: Python is available for S60 phones only. The biggest advantage is that you can extend it using C++, but it is not available on other Symbian phones.
  2. Flash: You can use Macromedia Flash to write Symbian programs. It also has some limitations; the most important is not being extensible easily with C++. The limitations are much less than J2ME limitations, though. I didn’t use it myself so I don’t know more about it. I think it’s available on S60 phones only.
  3. OPL: A Basic-like language, which was created in mid-80s. It’s available now as an Open Source Software, but its development is very slow.
  4. AppForge: They provided VB6 & .net environments for Symbian, Palm, BlackBerry, etc. I didn’t use this myself so I cannot make a decision about it.
  5. Write your own libraries in C++: Don’t ever think you can extend Symbian libraries. They say that it’s very flexible & extensible, but to extend anything you need more than just object-orientation or design patterns. You need to understand how it works.

A colleague of mine tried to extend the default List Box to provide an easy, flexible & portable version of it. He spent more than 4 months trying to do so. He wrote it, but it was unstable – it panicked at random times.

The above mentioned solutions are the most popular solutions. You may find less popular tools to solve this problem.

So write your own widgets. Use your own data structures. Your programs will be much cleaner, easier to understand & port to other platforms.

I know you cannot replace everything. There are times that you have to use Symbian APIs, but try to reduce this to a minimum if you want to get something done.

© 2014 Mohammad Tayseer

Theme by Anders NorenUp ↑