Celebs of Reddit

One reason I prefer Reddit to Digg is because it seems people know each other better in the comment sections, especially in the section I hang out the most in, the programming section. More than that, some known developers hang there and shoot the breeze with the rest of us. Here’s an incomplete list of those developers:

What other celebrities hang on reddit?

Update:
Contributed by others:

Page navigation in Django

Django is cool, it gives you free pagination: you say “I just want 20 articles per page” and it’ll split your result set in sets of 20 objects. The thing that’s missing is a template tag to add navigation between these pages. I wrote a small sub-template, which depends on two of my own template tags, to automatically add page navigation. First, here are the template tags needed:


@register.simple_tag
def pagination_get_string(get_dict, page_num):
    import copy
    get = copy.deepcopy(get_dict)
    get['page'] = page_num
    return '?' + get.urlencode()


@register.filter
def range1(n):
    try:
        return range(1, int(n) + 1)
    except ValueError:
        return []

Quick note about these two. pagination_get_string copies the current GET string and adds page=x to it. This ensures that if your pagination occurs in a search view with several parameters, moving between pages keeps the same parameters. range1 is pretty self-documenting, it returns a list from 1 to n (inclusively). Now, here is the sub-template:


{% load wsftags %}
Page:
{% for page_num in pages|range1 %}
    {% ifequal page_num page %}
        {{ page_num }}
    {% else %}
        <a href="{% pagination_get_string request.GET page_num %}">{{ page_num }}</a>
    {% endifequal %}
{% endfor %}

Just save this in a template directory and be sure to change the {% load %} statement to reflect the name of your own custom template tag file. You know, I think I should make this an inclusion_tag… Bah, another day. Anyway, to use it, just add this line to the template you wish to be paginated:


{% include "pagination.html" %}

Et voilĂ !

Perl vs Lisp

Yesterday, a redditor judged important to resurrect a 7 year-old post by the colorful Usenet troll, Erik Naggum. The post itself is about Perl vs. Lisp and isn’t very interesting because Mr. Naggum is probably the most biased person to post on comp.lang.lisp.

This post generated a significant amount of comments on Reddit and I found one comment particularly interesting

Perl vs. Lisp? Seriously? They aren’t even remotely similar languages. Why not Basic vs. Assembly? Sheesh.

He has a point: syntactically, Perl and (Common) Lisp are probably the languages least similar. They do however share a significant amount of semantics, and those similarities are certainly more important than syntax. Both languages are garbage collected, are dynamically typed, can treat code as data, are lexically scoped, have closures, and many other less important features or features I am forgetting about. In fact, I think the only thing that Lisp has that Perl lacks are macros (even then, Perl 6 will have macros.)

Let’s look at some simple examples of Perl and Common Lisp code. Here is a counter function. It takes a starting value as a parameter and returns a function that increments the counter by one and returns the new value (actually, that’s not quite exact for the Perl version.)


# Perl
sub counter {
    my $start = shift;
    return sub {
        return $start++;
    }
}

my $counter = counter(0);
for (1..10) {
    print $counter->(), "\\n";
}

; Common Lisp
(defun make-counter (start)
  (decf start)
  #'(lambda ()
      (incf start)))

(let ((counter (make-counter 0)))
  (dotimes (_ 10)
    (format t "~a~%" (funcall counter))))

When you run these two programs, they return the exact same output. Now of course, you could write a program that returns the same output in any language. The real interest of these programs is that they use the same, exact method to accomplish their task. Because functions are data just like strings or numbers in both languages, a function can return another function. The solutions also depend on the language having lexical scoping, so that the values are kept around between each call. You can convert the Common Lisp code to Emacs Lisp and you’ll see that it doesn’t work, Emacs Lisp will complain that the start variable does not exist.

I could give plenty more examples of how Perl and Lisp are similar but Mark-Jason Dominus has done a better job than I could ever hope to with his Perl book, Higher-Order Perl.

Knowing a language

Adam Barr talks about what is “knowing” a language on his blog. He argues that knowing a language does not involve knowing the built-in functions (or the standard library.) I must strongly disagree with this view, because if you deal with the lowest level of a language — in this case Python — you don’t write idiomatic code, which means that people who know the language cannot easily understand your code.

Let’s look at a simple Python example, determining the largest element of a list. The person who doesn’t know Python would write:


max = my_list[0]
for my element in my_list[1:]:
    if element > max:
        max = element
print max

This works (sort of; it would fail for an empty list), but no Python programmer is ever going to use that. The proper way is to use the built-in max() function:


print max(my_list)

There are many other core functions that should be known before one can claim he/she knows Python and a lot of modules too. Don’t try to create your own temporary files, just use the tempfile module! If you try to do it yourself, you expose yourself to a bunch of problems that have already been solved.

Knowing a language is more than just knowing the syntax and the reserved keywords, it’s knowing the core library, the standard library, it’s knowing which features to use and which to avoid. Otherwise, I could claim that I know Java, although my lack of knowledge of the libraries would make me extremely unproductive.