views:

387

answers:

3

Why (for example web2py) you return data from a controller in a dictionary instead (see Rails) in variables?

For example:

return dict(sape=4139, guido=4127, jack=4098)

instead of (that's the way Rails does it)

@var1 = "jello" 
@var2 = "hihi"

Is there any advantage using dictionaries over plain variables (speed-wise/code-wise)?

Update: The above way is actually a correct way for creating a dictionary (at least in Puthon 2.6.1). The other way (that many people say it's the correct one)

return {"var1": "jello", "var2": "hihi"}

is not used a lot by python frameworks.

From Python's documentation: "When the keys are simple strings, it is sometimes easier to specify pairs using keyword arguments:"

dict(sape=4139, guido=4127, jack=4098)
+4  A: 

The main advantage is that this is the only way in python to return a) more than a single value and b) give that value a name. Other options would be to use a class (extra code), return a tuple (no names, so you'd have to use indexes to access the values) or allow to return only a single value which would probably mean that everyone would return a dictionary since that's the most simple solution.

It also allows to wrap several methods and join/merge their results. Lastly, it allows to return different sets of value/name pairs for each call easily, for example, omit optional values or return additional hints.

Aaron Digulla
In Python 2.6+ `collections.namedtuple` allows both to return multiple values and to give names to these values.
J.F. Sebastian
So, why in rails the @variable is chosen to export variables to views? Why the same approach is not followed by other python frameworks?
Jon Romero
I don't know about rails but maybe they try to prevent to leak internal information (which is why most frameworks don't use local()). As for other frameworks: I know that TurboGears and web2py use this approach. From my point of view, that's "all". Dunno about Django.
Aaron Digulla
Or maybe the Rails syntax would make this approach "ugly".
Aaron Digulla
A: 

The nice thing is that a template engine like Jinja2 treats an object and a dict similarly, so if:

d = {'color': 'red'}
o = Color(red)

then these all work in the template syntax:

d.color d['color'] o.color o['color']
Ali A
+3  A: 

You can use local variables if you'd like:

def hello():
    var1 = "whatever you like"
    var2 = "another value"
    return locals() # or vars()

hello.html:

<html><body>
 <p>var1 {{=var1}}</p>
 <p>var2 {{=var2}}</p>
</body></html>

from PHP to web2py:

In web2py an HTTP request for "/app/c/f" is mapped into a call to the function f() in file (controller) c.py in the application "app". The file c.py is written in Python. The output of the function f() can be a string (in this case it is returned), or a set of variables (implemented as a python dictionary). In the latter case the variables are rendered into HTML by a file c/f.html, called a view.

J.F. Sebastian
Not really a recommended approach, though, as it's an easy way to end up passing data to your templates that you never intended to pass.
Carl Meyer
@Carl Meyer: I agree. Explicit dictionary is better.
J.F. Sebastian
for small functions like that I would just return locals() to same space
Plumo