ParTecs Weblog

Two algorithms to sort a dictionary by it’s value

February 27th, 2006

Here are 2 algorithms that I’ve use to sort dictionaries by their values. I have yet to profile both algorithms to see what works best in a senario. Personnally I feel the first method is more cognitive to Python developers.
Method 1 – Here I have converted the dictionary to a list of tuple (key, value) pairs. Further I have sorted the list by comparing the tuples second element.

>>> a = {1: 4, 2: 5, 4: 6, 7: 4} >>> sorted_dict = list(a.iteritems()) >>> sorted_dict.sort(lambda i1, i2: cmp(i1[1], i2[1])) >>> for key, value in sorted_dict: ... print key, value ... 1 4 7 4 2 5 4 6

Method 2 – In this case I have constructed a dictionary whose keys are the values of the dictionary I wanted sorted. The values of newly constructed dictionary is composed of a list of all the keys with the same value.

>>> for key, value in a.iteritems(): ... if sorted_dict.has_key(value): ... sorted_dict[value].append(key) ... continue ... sorted_dict[value] = [key] ... >>> for value, keys in sorted_dict.iteritems(): ... for key in keys: ... print key, value ... 1 4 7 4 2 5 4 6

Undo more than 20 transactions in Zope

February 27th, 2006

Some time ago I need to undo more that 20 transactions in one go. The zope interface displayed only 20 transactions per page. I did the unthinkable and tried to undo the transactions by opening the Zope database on the interpreter. There is a much simpler solution that skipped my mind. All one needed to do was manipulate the URL like so.

http://localhost:8080/manage_UndoForm ?first_transaction:int=20&last_transaction:int=100& PrincipiaUndoBatchSize:int=80

This might seem really obvious but it skipped my mind. And if you were still wondering how one would go about viewing the undo log of the Zope database. I have a small code snippet that will help you get started.

>>> from ZODB import FileStorage, DB
>>> storage = FileStorage.FileStorage('Data.fs')
>>> root=DB(storage).open().root()
>>> print storage.undoLog(0, 10)

Source inspector

February 27th, 2006

The is the script that executes when interactive interpreter starts up. You need to unsure that an environment variable PYTHONSTARTUP contains the path to that file.

export PYTHONSTARTUP=/home/partecs/

Here is a handy code snippet that one could add into your file.

import pydoc
import inspect
import rlcompleter, readline

readline.parse_and_bind('tab: complete')

def source(obj):
"""source of the obj."""
pydoc.pipepager(inspect.getsource(obj), 'less')
except IOError:

Now for the fun part, run the Python interpreter and hit the tab button twice. You have the tab complete feature. Also try out the following statements.

>>> import os

>>> source(os)

You should be able to view the source of the os module.

You can also use your file in Zope’s debug mode. To start up Zope’s debug mode run the following statement.

./zope/instancehome/bin/zopectl debug

On the interpreter run the following statement.

>>> execfile('/path/to/')

If you don’t like running execfile everytime you run Zope in the debug mode you could simply edit and modify

lib/python/Zope2/Startup/ and replace the line
"import Zope2;" with
"import Zope2;; execfile('/home/partecs/')".

AHAH (Asynchronous HTML and HTTP) and Plone

February 22nd, 2006

Recently I have tried working with AHAH along with Plone and found myself reaping the benefits of AJAX and the Zope framework. And what impressed me the most is that I wrote very little JavaScript.

I am going to run through an example of using AHAH with Controller Page Templates.

eg: form.cpt
<script language="JavaScript" type="text/javascript"
xsrc="MochiKit.js" mce_src="MochiKit.js"  ></script>
<script language="JavaScript" type="text/javascript">
function LoadManager() {

LoadManager.prototype.postFormData = function(theform) {
var data = {}
for (var i in theform.elements) {
var formelement = theform.elements[i];
data[] = formelement.value;
var d  = doSimpleXMLHttpRequest(theform.action, data);

LoadManager.prototype.updateDOM = function(dom) {
var text = dom.responseText;

LoadManager.prototype.fetchError = function(err) {

function postForm(theform, replacediv) {
loadManager = new LoadManager();
loadManager.div = $(replacediv);
This text will not reload on form submission.
<div id="reloadme">
<div metal:use-macro="here/comment_form/macros/view">

eg: form.cpt.metadata

title=Reply to Comment

validators..Save = validate_comment

action.success = traverse_to:string:comment_reply
action.success..Save = traverse_to:string:comment_reply
action.failure = traverse_to:string:comment_form

eg: comment_form.cpt

<metal:block use-macro="here/global_defines/macros/defines" />

<div metal:define-macro="view">

<form  action=""   method="post"
tal:define="errors options/state/getErrors">
<input type="hidden" name="form.submitted" value="1" />

<div class="field"
tal:define="error python:errors.get('comment', None)"
tal:attributes="class python:test(error, 'field error', 'field')">

<label for="title" i18n:translate="label_subject">Comment</label>

<div tal:content="error">Validation error output</div>
<input name="comment"
tal:attributes="value request/comment|nothing;tabindex tabindex/next" />

<input onClick="postForm(this.form, 'comments')"
name="form.button.Save" />


You must ensure that the response after the form submission is only the contents that you replaced in you macro and not an entire HTML file.

Feedburner RSS

Enter your email address:

Delivered by FeedBurner



RSS Telematics Freedom

February 2006
    Mar »


Sky Sponsored by Web Hosting