The Domain Name Not Taken

July 29th, 2007

It appears that all the domain names have been taken - 90% of them by crappy domain name sitting companies. This really ticks me off because I have an idea for an Ajaxy Web 2.0 type site that will make me obscenely wealthy, until the next bubble bursts. Naturally I can't give out details of the site I have in mind, suffice to say it is on the subject of debating. So I would love to get a simple, catchy domain, that says debating, arguing, duscusion or similar. If anyone can suggest such a domain that isn't taken, I would be happy to give you 100 shares when I float on the stock market. And if you are thinking of reserving said domain name and selling it to me, be aware that I have no money - at least until I get venture capital.

To get you started, here are some good domains that are taken...


I particularily like the last one, because visitors that did well on the side could be called master-debaters.


Transparently Recording Game Demos

July 27th, 2007

I have many ideas in the course of any given day. They are dredged up from the depths of my subconscious and placed on my mental in-tray, to be sorted in to mental heaps. Most are placed on to the "that'll never work" heap, others are thrown on the "better not, that's probably illegal" heap or the "plutonium isn't available at every corner drug store you know" heap. Occasionally though, some make it to my mental out-tray.

One recent idea was about recording demos in a game written with PyGame, which is something that is not that hard to do, but requires a bit of forethought to reliably record and play back sequences of events. It would be nice if there were some way of transparently recording the on-screen action and playing it back like a movie. Recording a video file on the fly is possible, but it would probably be too processor intensive. What would be better, is the ability to store and time-stamp the function calls used to create the display/audio so that they could later be streamed back in from a file. There are actualy some commercial tools that do this with OpenGL, by providing a proxy DLL that hooks in to the GL function calls - but I figured it could be done in straight Python, given its highly dynamic nature.

A little coding convinced me that this is the case. I wrote a script that can be used to replace every callable in a module or class with a proxy callable that can record the name of the function that has been called and the parameters that it was called with. I tried it with one of my OpenGL demonstrations and it worked perfectly, the demo ran as normal, but it streamed details about every GL function call. All it took in the OpenGL code was replacing two imports with a proxy_import function I had written (see below).

#from OpenGL.GL import *
#from OpenGL.GLU import *

import pystream
pystream.proxy_import('OpenGL.GL', '*')
pystream.proxy_import('OpenGL.GLU', '*')

I'm reasonably satisfied that recording the OpenGL output of a game is practical, but I'm in no hurry to implement it in full since I have plenty of work to do on other projects. The code I wrote to hook in to a module strikes me as something that could have a number of potential uses - beyond OpenGL and games. For instance, it could be used to turn a class in to a remotely callable object. The code is below.

class FunctionProxy(object):

    def __init__(self, name, function):

        self.__name = name
        self.__function = function

    def __call__(self, *args, **kwargs):

        print self.__name
        return self.__function(*args, **kwargs)

class ObjectProxy(object):

    def __init__(self, my_object, name=None, scope=None):

        self.__object = my_object
        self.__dir = self.__object.__dict__.keys()
        self.__name = name

        for symbol in self.__dir:

            attr = getattr(self.__object, symbol)

            func_name = symbol
            if self.__name is not None:
                func_name = self.__name + '.' + func_name

            if hasattr(attr, '__call__'):

                function_proxy = FunctionProxy(func_name, attr)
                setattr(self, symbol, function_proxy)

                if scope is not None:
                    scope[func_name] = function_proxy


                setattr(self, symbol, attr)
                if scope is not None and not func_name.startswith('__'):
                    scope[func_name] = attr

def proxy_import(module_name, from_list=None, scope=None):

    if from_list is not None:
        from_list = [f.strip() for f in from_list.split(',')]

    if scope is None:
        import sys
        scope = sys._getframe().f_back.f_globals

    module = __import__(module_name, scope, None, from_list)

    if from_list is None:
        proxy = ObjectProxy(module, name=module_name)
        scope[module_name] = proxy
    elif from_list and from_list[0]=='*':
        proxy = ObjectProxy(module, scope=scope)
        proxy = ObjectProxy(module)
        for symbol in from_list:
            scope[symbol] = getattr(proxy, symbol, scope=scope)
    return proxy

if __name__ == "__main__":

    #from math import *
    proxy_import('math', '*')
    print abs(sin(radians(60)))
Download this code Update: Fixed some nonsense code in the FunctionProxy class (never code after midnight).

Analysis paralysis

July 18th, 2007

I pride myself in my ability to make decisions. If I have all the variables and criteria then I can typically select the best course of action, or at least a good choice of action. As an engineer, this is invaluable because most problems in software development are of this type; you have all the facts and a desired outcome. If you meet the desired outcome, then you can safely say that you made the right decision. If not you can go back and try again.

If only all decisions where as clear as the kind you have to make in programming! In the real world - which I'm forced to occasionally visit - most decisions I have to make definitely aren't like this. Generally I don't have all the facts, the criteria aren't clear and the outcome is a scalar, rather than a simple Boolean. And when faced with a problem that is too fuzzy, I tend to not make any decision at all, rather than risk making a bad one.

Purchasing a mobile phone is a case in point. I've been using a pay-as-you-go phone, which was a good deal originally but had become expensive because I use it a lot more now. I've known this for months but every time I considered which combination of phone and plan to go for I ended up deferring the decision for while because there were so many variables (vendor, phone price, monthly fee, contract length, add-ons, phone features etc). Annoyingly, of all the choices I could have made, deferring the decision to later was the worst, because it cost me money.

You may consider this to be a personality flaw that I should work on, but I say it is the universe that is at fault. What I need is a formal way of patching this flaw, or at least working around it. A piece of software could be written that allows the user to enter a number of possible choices and criteria. For the phone example the choices would be the various plans on offer and the criteria would in the form of graphs with a variable on the x-axis and a desirability rating on the y-axis. Each criteria could also be weighted for importance in the final decision, and given a confidence scale that reflects how sure you are of that criteria. The output of this program would be the list of choices, sorted by rank, with corresponding confidence ratings. The best choice would be the first in the list, but by setting the cut-off point for confidence it would include the possibility of inaction as the best choice.

I figure this software could be used to handle pretty much any major life decision, such as "which girlfriend should I marry?", "can my spouse have my kidney?" or "who should we eat first"? It could also replace many of today's world-leaders, who seem to make fairly arbitrary decisions anyway. I'm tempted to implement it in the form of a Python script, and perhaps put a nice graphical interface on it. I kind of like the idea of governments being replaced by Python code. I for one welcome... you know the rest.

Excuse me, its lunch time. Now do I want pickles, olives or sauerkraut on my sandwich?


Food File is now Open Source

July 14th, 2007
Food FileFood File is one of the first moderately sized wxPython applications I wrote. It is a rich interface to the US Department of Agriculture nutrition database, with html output and neat 3D pie-charts (everyone loves a good pie-chart)! For a while I was selling it commercially, but it didn't do so well - probably because I'm not a great business man. I'm an engineer. I make things, I just can't seem to sell them! So I gave it away for free and tried to make money from Google Ads, which worked for a while, but it became so popular that my bandwidth bills overtook the pittance I got from the ads.

The consequence of this tale of woe is that I have released Food File as open source, so that I can collect on karma rather than hard cash. The source and Win32 installer is now available on Google Code, so those nice folks at Google can pick up the bandwidth bill. I hear they are not short of a few cents.

Food File downloads

Food File was written quite hastily, and then tweaked and enhanced over a few months. The code could be better, but I'm fairly pleased with the end result. It does some pretty cool things, like updating the search as you type and rendering neat 3D pie-charts. The nutrition database is actually stored as a large flat-file, which is how it is shipped. I did investigate using an SQL solution, but it turns out that a brute-force search of 7000+ items on a list can be done in the blink of an eye. Go Python. The source may be useful to anyone interested in writing a wxWindows application, there are a few gems that could be ripped out.

I probably wont be maintaining this project, which is a shame because there are many enhancements that could be done. I'm hoping that somebody will offer to take over the project and add some polish and new features. Installers for other platforms would also be appreciated. If you would like to help, let me know!


Postmarkup 1.0.5

July 10th, 2007

Just uploaded a new version of Postmarkup (1.0.5), my bbcode parsing engine. The only significant change was a fix to a potential thread safety issue. It would only have occurred if you used the [list] tag, and even then only rarely (if at all). I figured it would be worthwhile since many people are using it in the context of a multi-threaded web application.

I decided not to bother with a win32 installer since its only a single Python file, and can be installed with easy_install. Use the following command line to install, or upgrade, Postmarkup.

easy_install -U postmarkup

If anyone really wants a win32 installer then let me know, I'll probably oblige.

See the Postmarkup homepage on Google Code for more information.


Happy New Year!

July 5th, 2007

What do you mean its not the new year? Yesterday was 32 AW, today is 33 AW. That's After Will. Which also makes it my birthday.

Last year was pretty good, career-wise and on a personal level. I use the term 'career' rather loosely because it implies some kind of direction. I don't learn skills because they are commercial - it's just blind luck that I manage to make a living out of them. And it seems like the skills I do learn can be a little niche, but that can often work to my advantage. For instance, my first 2 jobs involved writing software polygon rasterizers for games, at a time when 3D graphics cards were becoming popular. Even Python is a little niche, it certainly was when I started using it. But I'm now working full time with Python, and writing a book about it. I'm confident that it is a skill-set that is on the rise, and wont go the way of software polygon rasterizers!

On a personal level, last year was pretty good. I met my girlfriend last year, and I'm planning to move to London with her. Which may be quite a culture shock for someone raised in a small town in North East Scotland! I suspect it will be kind of like Crocodile Dundee, only without the boomerang.

Sorry for the self-indulgent post. I don't do it very often. All the best for 33 AW.


Profiling bit-twiddling in Python

July 1st, 2007

After my previous post regarding the the is_power_of_2 and next_power_of_2 functions, Richard Jones pointed out that Pyglet has an implementation that used the bit-twiddling method. Since I had something to do a direct comparison with, I wrote a script to test the run time of the two methods.

#!/usr/bin/env python

setup_1 = """
from math import log, ceil

def is_power_of_2(n):
    return log(n, 2) % 1.0 == 0.0

def next_power_of_2(n):
    return (2 ** ceil(log(n, 2)))

setup_2 = """
def next_power_of_2(v):
    v -= 1
    v |= v >> 1
    v |= v >> 2
    v |= v >> 4
    v |= v >> 8
    v |= v >> 16
    return v + 1

def is_power_of_2(v):
    return (v & (v - 1)) == 0

from timeit import Timer

t1 = Timer("is_power_of_2(128)", setup_1)
t2 = Timer("is_power_of_2(128)", setup_2)
t3 = Timer("next_power_of_2(125)", setup_1)
t4 = Timer("next_power_of_2(125)", setup_2)

print "float math is_power_of_2:", t1.timeit()
print "bit-tiwddling is_power_of_2:", t2.timeit()
print "float math next power of 2:", t3.timeit()
print "bit-twiddling next power of 2:", t4.timeit()

This produced the following results on my humble PC.

float math is_power_of_2: 3.79312203087
bit-tiwddling is_power_of_2: 1.11348704933

float math next power of 2: 4.90055467944
bit-twiddling next power of 2: 2.99615733285

The results are conclusive - bit-twiddling is still a big win in Python. I figured that the bit-twiddling is_power_of_2 function would be faster than the float math version, but I was surprised by the next_power_of_2 result. It pays to profile!

I also tested it with Psyco, and got the following results.

float math is_power_of_2: 4.33070460072
bit-tiwddling is_power_of_2: 0.037652550813

float math next power of 2: 5.66786840227
bit-twiddling next power of 2: 0.0600607060395

Wow! The bit-twidding times improved astronomically with Psyco - almost 50 times faster, by my calculations. What is surprising is that the float versions are actually a little slower with Psyco.

Conclusion? If you need to calculate the nearest power of 2 for billions of numbers in a hurry, use Psyco.

Search for Posts
© 2008 Will McGugan.

A technoblog blog, design by Will McGugan