On Oct 31, 2008, at 10:46 AM, Stephane DROUARD wrote: > Robert Bradshaw wrote: > >>> In the documentation it is written that Cython defaults to the >>> built-in scope when it can't determine the scope of a variable, >>> which is different from Python, which defaults to the module scope. >> >> The documentation needs to be fixed then. If the scope of a variable >> can't be determined, then it actually raises a compile-time error. > > No, the example given in the documentation does not generate a > compile-time > error. > > foo.py: > print __name__ > > But under Python it returns "foo", "__builtin__" when cython'ized. > > As the documentation specifies, this can be fixed by: > > foo.py: > global __name__ > print __name__ > > Then both return "foo".
Ah, good catch. Cython (and, incidentally I) didn't know that __name__ is an already declared module-level variable, hence it looked it up as a builtin (and found it there, so no error). This is easily fixed by always having __name__ in the module namespace (what other magic variables are there?) > >>> Would it be possible to implement a compatibility mode, where >>> Cython would behave as much as possible like Python? >> >> This is certainly possible, but would have a significant performance >> hit. > > I agree, but would it be better to be faster or compatible? I would > be in > favour to be compatible by default and set compiler options to > optimize. > This is then the responsibility of the developper to check that the > optimizations are compatible with the use of the module. It seems the current community values speed more, otherwise they would just be using Python directly. However, this is something we should continue to evaluate. >>> During the tests, I remarked that: >>> >>> import __builtin__ >>> print __builtin__.__name__ >>> >>> __name__ is not cached. A possible improvement >> >> But what if I did >> >> import __builtin__ >> print __builtin__.__name__ >> foo() >> print __builtin__.__name__ >> >> where foo (defined elsewhere) is >> >> def foo(): >> import __builtin__ >> __builtin__.__name__ = "something else" > > OK. But if I do: > > print __name__ > foo() > print __name__ > >>>> import __builtin__ >>>> __builtin__.__name__ > '__builtin__' >>>> __builtin__.__name__ = "blah" >>>> import foo > blah ## confirms that Cython considers __name__ in > __builtin__ > blah ## update not reflected >>>> __builtin__.__name__ > 'something else' ## whereas it is > > I assume this is because Cython has cached __name__ at module > creation. > (unfortunately I was not able to validate, setting > Options.cache_builtins to > 0 raises an exception) I just tried this, I get __builtin__ something else as expected. Cython does not "know" about __builtin__ being special, and treats it as any other module (no caching). This allows one to get "non-cached" versions of the builtins. The caching only happens when builtin names are used directly in the source, not when looked up as attributes. We should delete that option, as now builtins are much more integrated into the compiler. - Robert _______________________________________________ Cython-dev mailing list [email protected] http://codespeak.net/mailman/listinfo/cython-dev
